示例#1
0
        // takes a BamlCollectionHolder and its context and sets the value of the holder's collection to be
        // either the default collection instantiated by the holder's constructor or a newly created
        // collection created based on the expected type. 
        // *** Used when we do not have an explicit tag.
        private void InitPropertyCollection(BamlCollectionHolder holder, ReaderContextStackData context) 
        { 
            // this method should only be called to initialize the collection
            Debug.Assert (holder.Collection == null); 

            if (context.ContextType == ReaderFlags.PropertyArray)
            {
                // arrays are a little different than other collections, because we wrap them in an array extension. 
                // Here we create an array extension and assign the element type based on the property.
 
                ArrayExtension arrayExt = new ArrayExtension(); 
                arrayExt.Type = context.ExpectedType.GetElementType();
                holder.Collection = arrayExt; 
            }
            else if (holder.DefaultCollection != null)
            {
                // if we the property getter returned a default value, then we use that collection to insert 
                // as the property's collection.
 
                holder.Collection = holder.DefaultCollection; 
            }
            else 
            {
                ThrowException(SRID.ParserNullPropertyCollection, holder.PropertyDefinition.Name);
            }
 
            context.ExpectedType = null; // Don't want to receive any other values
        } 
示例#2
0
        // Start of an IList or IEnumerable property.  Get the IList value from the parent 
        // object and store it on the reader stack, so that records encountered under this 
        // list can be added to it.
        protected virtual void ReadPropertyIListStartRecord( 
            BamlPropertyIListStartRecord bamlPropertyIListStartRecord)
        {
            short attributeId = bamlPropertyIListStartRecord.AttributeId;
            object parent = GetCurrentObjectData(); 
            BamlCollectionHolder holder = new BamlCollectionHolder(this, parent, attributeId);
            Type expectedType = holder.PropertyType; 
 
            // If the property does not implement IList or IAddChild, see if the parent
            // (which is the current object on the top of the stack) implements IAddChild 
            // and try that for adding items later on.  First look at defined propertyType
            // obtained from the DP or PropertyInfo.  If that doesn't work, then look at
            // the actual type of object retrieved using GetValue.
            ReaderFlags flags = ReaderFlags.Unknown; 
            if (typeof(IList).IsAssignableFrom(expectedType))
            { 
                flags = ReaderFlags.PropertyIList; 
            }
            else if (BamlRecordManager.TreatAsIAddChild(expectedType)) 
            {
                flags = ReaderFlags.PropertyIAddChild;
                holder.Collection = holder.DefaultCollection;
                holder.ReadOnly = true; 
            }
            else if (typeof(IEnumerable).IsAssignableFrom(expectedType) && 
                     (BamlRecordManager.AsIAddChild(GetCurrentObjectData())) != null) 
            {
                flags = ReaderFlags.PropertyIAddChild; 
                holder.Collection = CurrentContext.ObjectData;
                holder.ReadOnly = true;
                expectedType = CurrentContext.ObjectData.GetType();
            } 
            else
            { 
                // if we reached this case, then we had a read-only IEnumerable property 
                // under a non-IAddChild element.  Throw an exception
                ThrowException(SRID.ParserReadOnlyProp, holder.PropertyDefinition.Name); 
            }

            PushContext(flags | ReaderFlags.CollectionHolder, holder, expectedType, 0);
 
            // Set the name of the property into the context
            CurrentContext.ElementNameOrPropertyName = holder.AttributeName; 
        } 
示例#3
0
        // Start of an IDictionary encountered.  Set up the BamlDictionaryHolder on the reader 
        // stack so that items can be added to it.
        protected virtual void ReadPropertyIDictionaryStartRecord(
            BamlPropertyIDictionaryStartRecord bamlPropertyIDictionaryStartRecord)
        { 
            short  attributeId = bamlPropertyIDictionaryStartRecord.AttributeId;
            object parent = GetCurrentObjectData(); 
            BamlCollectionHolder holder = new BamlCollectionHolder(this, parent, attributeId); 

            PushContext(ReaderFlags.PropertyIDictionary | ReaderFlags.CollectionHolder, holder, holder.PropertyType, 0); 

            // Set the name of the property into the context
            CurrentContext.ElementNameOrPropertyName = holder.AttributeName;
        } 
示例#4
0
        // Read the start of an array property.  Set up the BamlArrayHolder that is needed to
        // hold array contents. 
        protected void ReadPropertyArrayStartRecord(BamlPropertyArrayStartRecord bamlPropertyArrayStartRecord) 
        {
            short  attributeId = bamlPropertyArrayStartRecord.AttributeId; 
            object parent = GetCurrentObjectData();
            BamlCollectionHolder holder = new BamlCollectionHolder(this, parent, attributeId, false /*needDefault*/);

            if (!holder.PropertyType.IsArray) 
            {
                ThrowException(SRID.ParserNoMatchingArray, GetPropertyNameFromAttributeId(attributeId)); 
            } 

            Debug.Assert(!holder.ReadOnly); // this is being checked in XamlReaderHelper, just assert 

            PushContext(ReaderFlags.PropertyArray | ReaderFlags.CollectionHolder, holder, holder.PropertyType, 0);

            // Set the name of the property into the context 
            CurrentContext.ElementNameOrPropertyName = holder.AttributeName;
        }