예제 #1
0
        protected override bool OnRead <T>(IXReadOperation reader, XType <T> xType, XAttribute attribute, Func <object, bool> assign,
                                           XObjectArgs args)
        {
            Type type = typeof(T);

            if (Identifier.CanId(type))
            {
                string text = attribute.Value;
                if (!string.IsNullOrWhiteSpace(text) && text.Length > 0)
                {
                    reader.AddTask(this, () =>
                    {
                        if (referenceObjects.TryGetValue(text, out object refObject))
                        {
                            if (refObject == null || refObject.GetType() == type)
                            {
                                return(assign(refObject));
                            }
                            else
                            {
                                throw new InvalidOperationException(
                                    $"Possible collision: the reference object with ID {text} was of expected type {type.Name}, " +
                                    $"but that ID resolved to an object of type {refObject.GetType().Name}.");
                            }
                        }
                        return(false);
                    });
                    return(true);
                }
            }

            return(false);
        }
예제 #2
0
 /// <summary>
 /// Create a new instance of <see cref="XCollectionArgs"/> with the given field settings.
 /// </summary>
 /// <param name="hints">The setting for <see cref="XObjectArgs.Hints"/>.</param>
 /// <param name="itemsAsElements">The setting for <see cref="ItemsAsElements"/>.</param>
 /// <param name="itemName">The setting for <see cref="ItemName"/>.</param>
 /// <param name="itemArgs">The setting for <see cref="ItemArgs"/>.</param>
 public XCollectionArgs(ObjectHints hints    = ObjectHints.None, bool itemsAsElements = false, XName itemName = null,
                        XObjectArgs itemArgs = null) : base(hints)
 {
     ItemsAsElements = itemsAsElements;
     ItemName        = itemName;
     ItemArgs        = itemArgs;
 }
 protected override void OnBuild(IXReadOperation reader, XElement element, ObjectBuilder <ReadOnlyDictionary <TKey, TValue> > objectBuilder,
                                 XObjectArgs args) =>
 reader.Read <Dictionary <TKey, TValue> >(element, x =>
 {
     objectBuilder.Object = new ReadOnlyDictionary <TKey, TValue>(x);
     return(true);
 },
                                          args ?? XObjectArgs.DefaultIgnoreElementName);
예제 #4
0
 protected override void OnBuild(IXReadOperation reader, XElement element, ObjectBuilder <LinkedListNode <T> > objectBuilder,
                                 XObjectArgs args) =>
 reader.Read <T>(element, x =>
 {
     objectBuilder.Object = new LinkedListNode <T>(x);
     return(true);
 },
                 args ?? XObjectArgs.DefaultIgnoreElementName);
예제 #5
0
        protected override bool OnWrite(XType <DictionaryEntry> xType, IXWriteOperation writer,
                                        DictionaryEntry obj, XElement element, XObjectArgs args)
        {
            XName keyName   = XComponents.Component <XAutoCollections>().KeyName,
                  valueName = XComponents.Component <XAutoCollections>().ValueName;

            if (obj.Key != null)
            {
                element.Add(writer.WriteTo(new XElement(keyName), obj.Key));

                if (obj.Value != default)
                {
                    element.Add(writer.WriteTo(new XElement(valueName), obj.Value));
                }
            }

            return(true);
        }
예제 #6
0
        protected override void OnBuild(IXReadOperation reader, XElement element, ObjectBuilder <T[, ]> objectBuilder, XObjectArgs args)
        {
            // Read as a jagged array

            T[][] jagged = null;

            reader.Read <T[][]>(element, x =>
            {
                jagged = x;
                return(true);
            });

            // Convert to a multidimensional array once read

            reader.AddTask(this, () =>
            {
                if (jagged == null)
                {
                    return(false);
                }

                int lb0 = jagged.GetLowerBound(0), n0 = jagged.Length;

                int lb1, n1;
                if (n0 > 0)
                {
                    lb1 = jagged[0].GetLowerBound(0);
                    n1  = jagged[0].Length;
                }
                else
                {
                    lb1 = 0;
                    n1  = 0;
                }

                objectBuilder.Object = (T[, ])Array.CreateInstance(typeof(T), new int[2] {
                    n0, n1
                }, new int[2] {
                    lb0, lb1
                });

                for (int i = lb0, I = lb0 + n0; i < I; i++)
                {
                    for (int j = lb1, J = lb1 + n1; j < J; j++)
                    {
                        objectBuilder.Object[i, j] = jagged[i][j];
                    }
                }

                return(true);
            });
        }
예제 #7
0
        protected override bool OnWrite <T>(IXWriteOperation writer, T obj, XAttribute attribute, XObjectArgs args)
        {
            if (obj != null && Identifier.CanId(obj.GetType()))
            {
                object id = Identifier.GetId(obj);

                if (id != null && referenceObjects.ContainsKey(id))
                {
                    _ = writer.WriteTo(attribute, id);
                    return(true);
                }
            }

            return(false);
        }
예제 #8
0
        protected override void OnBuild(XType <DictionaryEntry> xType, IXReadOperation reader,
                                        XElement element, ObjectBuilder <DictionaryEntry> objectBuilder, XObjectArgs args)
        {
            XName keyName = XComponents.Component <XAutoCollections>().KeyName,
                                             valueName = XComponents.Component <XAutoCollections>().ValueName;

            XElement keyElement = element.Element(keyName);

            if (keyElement == null)
            {
                return;
            }

            bool   foundKey = false, foundValue = false;
            object key = null, value = null;

            reader.Read(keyElement, x =>
            {
                key = x;
                return(foundKey = true);
            },
                        XObjectArgs.DefaultIgnoreElementName);

            XElement valueElement = element.Element(valueName);

            if (valueElement != null)
            {
                reader.Read(valueElement, x =>
                {
                    value = x;
                    return(foundValue = true);
                },
                            XObjectArgs.DefaultIgnoreElementName);
            }
            else
            {
                foundValue = true;
            }

            reader.AddTask(this, () =>
            {
                if (foundKey && foundValue)
                {
                    objectBuilder.Object = new DictionaryEntry(key, value);
                    return(true);
                }
                return(false);
            });
        }
예제 #9
0
        protected override bool OnRead <T>(IXReadOperation reader, XType <T> xType, XElement element, Func <object, bool> assign,
                                           XObjectArgs args)
        {
            Type type = typeof(T);

            // A serialized reference has no attributes, no elements, some text, is of a type that can be ID'd,
            // and not of a type that has a registered XTexter

            string value = element.Value;

            if (!element.HasAttributes &&
                !element.HasElements &&
                !string.IsNullOrEmpty(value) &&
                xType.Component <XTexter <T> >() == null &&
                Identifier.CanId(type, out Type idType))
            {
                bool   idFound = false;
                object id      = null;

                reader.Read(element, idType, x =>
                {
                    idFound = true;
                    if (!Identifier.KeyComparer.Equals(x, ReflectionTools.GetDefaultValue(idType)))
                    {
                        id = x;
                    }
                    return(true);
                },
                            XObjectArgs.DefaultIgnoreElementName);

                // Schedule a task to assign the object if it shows up in the dictionary

                reader.AddTask(this, () =>
                {
                    if (!idFound)
                    {
                        return(false);
                    }
                    if (id == null)
                    {
                        return(true);
                    }
                    if (referenceObjects.TryGetValue(id, out object refObject))
                    {
                        if (refObject == null || type == refObject.GetType())
                        {
                            return(assign(refObject));
                        }
                        else
                        {
                            throw new InvalidOperationException(
                                $"Possible collision: the reference object with ID {id} was of expected type {type.Name}, " +
                                $"but that ID resolved to an object of type {refObject.GetType().Name}.");
                        }
                    }

                    return(false);
                });

                return(true);
            }

            return(false);
        }
예제 #10
0
 protected override bool OnWrite(IXWriteOperation writer, LinkedListNode <T> obj, XElement element, XObjectArgs args)
 {
     _ = writer.WriteTo(element, obj.Value);
     return(true);
 }
예제 #11
0
 internal void Build(XType <T> xType, IXReadOperation reader, XElement element, ObjectBuilder <T> objectBuilder, XObjectArgs args) =>
 OnBuild(xType, reader, element, objectBuilder, args);
예제 #12
0
 internal bool Write(XType <T> xType, IXWriteOperation writer, T obj, XElement element, XObjectArgs args) =>
 OnWrite(xType, writer, obj, element, args);
예제 #13
0
 /// <summary>
 /// Implement this method to build (read) an object of type <typeparamref name="T"/> from the <see cref="XElement"/>
 /// <paramref name="element"/> where it was serialized.
 /// </summary>
 /// <param name="xType">The <see cref="XType{T}"/> instance from the current <see cref="XDomain"/>.</param>
 /// <param name="reader">An <see cref="IXReadOperation"/> instance for deserializing XML and scheduling tasks.</param>
 /// <param name="element">The <see cref="XElement"/> to be read as an instance of <typeparamref name="T"/>.</param>
 /// <param name="objectBuilder">An <see cref="ObjectBuilder{T}"/> to contain the constructed <typeparamref name="T"/>.</param>
 /// <param name="args">Optional arguments with information about XML formatting.</param>
 protected abstract void OnBuild(XType <T> xType, IXReadOperation reader, XElement element, ObjectBuilder <T> objectBuilder, XObjectArgs args);
예제 #14
0
 /// <summary>
 /// Implement this method to write an object of type <typeparamref name="T"/> to the given <see cref="XElement"/>.
 /// </summary>
 /// <param name="xType">The <see cref="XType{T}"/> instance from the current <see cref="XDomain"/>.</param>
 /// <param name="writer">An <see cref="IXWriteOperation"/> instance for serializing XML.</param>
 /// <param name="obj">The <typeparamref name="T"/> to be serialized.</param>
 /// <param name="element">The <see cref="XElement"/> to which <paramref name="obj"/> is being written.</param>
 /// <param name="args">Optional arguments with information about XML formatting.</param>
 protected abstract bool OnWrite(XType <T> xType, IXWriteOperation writer, T obj, XElement element, XObjectArgs args);
예제 #15
0
        protected override bool OnWrite(IXWriteOperation writer, T[,] obj, XElement element, XObjectArgs args)
        {
            // Get lower bound and length

            int lb = obj.GetLowerBound(0), n = obj.GetLength(0);

            int[] lb1 = new int[1] {
                obj.GetLowerBound(1)
            }, n1 = new int[1] {
                obj.GetLength(1)
            };

            if (lb != 0)
            {
                element.SetAttributeValue(XComponents.Component <XAutoCollections>().ArrayLowerBoundName, XmlTools.Write(lb));
            }

            // Copy each second rank into a new array and write them as 1-dimensional arrays

            for (int i = lb, I = lb + n; i < I; i++)
            {
                T[] dim1 = (T[])Array.CreateInstance(typeof(T), n1, lb1);

                for (int j = lb1[0], J = n1[0]; j < J; j++)
                {
                    dim1[j] = obj[i, j];
                }

                XElement li = writer.WriteTo(new XElement(ItemName), dim1);
                if (lb1[0] != 0)
                {
                    li.SetAttributeValue(XComponents.Component <XAutoCollections>().ArrayLowerBoundName, XmlTools.Write(lb1[0]));
                }
                element.Add(li);
            }

            return(true);
        }
예제 #16
0
 protected override bool OnWrite(XType <T> xType, IXWriteOperation writer, T obj, XElement element, XObjectArgs args) =>
 writeMethod(xType, writer, obj, element, args);
예제 #17
0
 protected override void OnBuild(XType <T> xType, IXReadOperation reader, XElement element, ObjectBuilder <T> objectBuilder,
                                 XObjectArgs args) =>
 readMethod(xType, reader, element, objectBuilder, args);
예제 #18
0
 protected override void OnBuild(IXReadOperation reader, XElement element, ObjectBuilder <T[]> objectBuilder,
                                 XObjectArgs args)
 {
     XCollectionArgs collectionArgs = args as XCollectionArgs ?? new XCollectionArgs(default, ItemsAsElements, ItemName);
예제 #19
0
 internal XPropertyArgs(XObjectArgs args, Func <Tuple <object, bool> > getter) :
     base(args == null ? default : args.Hints) =>
     this.getter = getter ?? throw new ArgumentNullException(nameof(getter));