예제 #1
0
        /// <summary> 
        ///     Invalidate this property if 
        ///     - It is not locally set and
        ///     - It is not acquired from a style/template 
        /// </summary>
        private static bool InvalidateTreeDependentProperty(
            TreeChangeInfo              info,
            DependencyObject            d, 
        ref FrameworkObject             fo,
            DependencyProperty          dp, 
            FrameworkPropertyMetadata   fMetadata, 
            Style                       selfStyle,
            Style                       selfThemeStyle, 
            ref ChildRecord             childRecord,
            bool                        isChildRecordValid,
            bool                        hasStyleChanged,
            bool                        isSelfInheritanceParent) 
        {
            Debug.Assert(d != null, "Must have non-null current node"); 
 
            // This must be an inherited dependency property
            Debug.Assert(fMetadata.IsInherited == true, "This must be an inherited dependency property"); 

            // Children do not need to inherit properties across a tree boundary
            // unless the property is set to override this behavior.
 
            if (!SkipNext(fo.InheritanceBehavior) || fMetadata.OverridesInheritanceBehavior)
            { 
                InheritablePropertyChangeInfo rootInfo = info.GetRootInheritableValue(dp); 

                EffectiveValueEntry oldEntry = rootInfo.OldEntry; 
                EffectiveValueEntry newEntry = info.IsAddOperation ? rootInfo.NewEntry : new EffectiveValueEntry(dp, BaseValueSourceInternal.Inherited);

                bool isForceInheritedProperty = IsForceInheritedProperty(dp);
 
                if (d != info.Root)
                { 
                    if (isSelfInheritanceParent) 
                    {
                        oldEntry = d.GetValueEntry( 
                                d.LookupEntry(dp.GlobalIndex),
                                dp,
                                fMetadata,
                                RequestFlags.DeferredReferences); 
                    }
                    else 
                    { 
                        oldEntry = oldEntry.GetFlattenedEntry(RequestFlags.FullyResolved);
                        oldEntry.BaseValueSourceInternal = BaseValueSourceInternal.Inherited; 
                    }
                }

                OperationType operationType = info.IsAddOperation ? OperationType.AddChild : OperationType.RemoveChild; 
                if (BaseValueSourceInternal.Inherited >= oldEntry.BaseValueSourceInternal)
                { 
                    // If the oldValueSource is of lower precedence than Inheritance 
                    // only then do we need to Invalidate the property. Examples of
                    // values with higher precedence are those that are locally set 
                    // or set via a style/template.
                    return (d.UpdateEffectiveValue(
                                d.LookupEntry(dp.GlobalIndex),
                                dp, 
                                fMetadata,
                                oldEntry, 
                                ref newEntry, 
                                false /* coerceWithDeferredReference */,
                                false /* coerceWithCurrentValue */, 
                                operationType)
                            & (UpdateResult.ValueChanged | UpdateResult.InheritedValueOverridden))
                            == UpdateResult.ValueChanged;
                        // return false if either the value didn't change or 
                        // it changed because the inherited value was overridden by coercion or animation.
                } 
                else if (isForceInheritedProperty) 
                {
                    // IsCoerced == true && value == UnsetValue indicates that we need to re-coerce this value 
                    newEntry = new EffectiveValueEntry(dp, FullValueSource.IsCoerced);

                    // Re-coerce a force inherited property because it's coersion depends on treeness
                    return (d.UpdateEffectiveValue( 
                                d.LookupEntry(dp.GlobalIndex),
                                dp, 
                                fMetadata, 
                                oldEntry,
                                ref newEntry, 
                                false /* coerceWithDeferredReference */,
                                false /* coerceWithCurrentValue */,
                                operationType)
                            & (UpdateResult.ValueChanged | UpdateResult.InheritedValueOverridden)) 
                            == UpdateResult.ValueChanged;
                        // return false if either the value didn't change or 
                        // it changed because the inherited value was overridden by coercion or animation. 
                }
            } 

            return false;
        }
예제 #2
0
        // Invalidate all the properties that may have changed as a result of
        //  changing this element's parent in the logical (and sometimes visual tree.)
        internal FrugalObjectList <DependencyProperty> InvalidateTreeDependentProperties(TreeChangeInfo parentTreeState, bool isSelfInheritanceParent, bool wasSelfInheritanceParent)
        {
            AncestorChangeInProgress = true;

            InVisibilityCollapsedTree = false;  // False == we don't know whether we're in a visibility collapsed tree.

            if (parentTreeState.TopmostCollapsedParentNode == null)
            {
                // There is no ancestor node with Visibility=Collapsed.
                //  See if "fe" is the root of a collapsed subtree.
                if (Visibility == Visibility.Collapsed)
                {
                    // This is indeed the root of a collapsed subtree.
                    //  remember this information as we proceed on the tree walk.
                    parentTreeState.TopmostCollapsedParentNode = this;

                    // Yes, this FE node is in a visibility collapsed subtree.
                    InVisibilityCollapsedTree = true;
                }
            }
            else
            {
                // There is an ancestor node somewhere above us with
                //  Visibility=Collapsed.  We're in a visibility collapsed subtree.
                InVisibilityCollapsedTree = true;
            }


            try
            {
                // Style property is a special case of a non-inherited property that needs
                // invalidation for parent changes. Invalidate StyleProperty if it hasn't been
                // locally set because local value takes precedence over implicit references
                if (IsInitialized && !HasLocalStyle && (this != parentTreeState.Root))
                {
                    UpdateStyleProperty();
                }

                Style            selfStyle       = null;
                Style            selfThemeStyle  = null;
                DependencyObject templatedParent = null;

                int         childIndex         = -1;
                ChildRecord childRecord        = new ChildRecord();
                bool        isChildRecordValid = false;

                selfStyle       = Style;
                selfThemeStyle  = ThemeStyle;
                templatedParent = TemplatedParent;
                childIndex      = TemplateChildIndex;

                // StyleProperty could have changed during invalidation of ResourceReferenceExpressions if it
                // were locally set or during the invalidation of unresolved implicitly referenced style
                bool hasStyleChanged = HasStyleChanged;

                // Fetch selfStyle, hasStyleChanged and childIndex for the current node
                FrameworkElement.GetTemplatedParentChildRecord(templatedParent, childIndex, out childRecord, out isChildRecordValid);

                FrameworkElement        parentFE;
                FrameworkContentElement parentFCE;
                bool hasParent = FrameworkElement.GetFrameworkParent(this, out parentFE, out parentFCE);

                DependencyObject    parent = null;
                InheritanceBehavior parentInheritanceBehavior = InheritanceBehavior.Default;
                if (hasParent)
                {
                    if (parentFE != null)
                    {
                        parent = parentFE;
                        parentInheritanceBehavior = parentFE.InheritanceBehavior;
                    }
                    else
                    {
                        parent = parentFCE;
                        parentInheritanceBehavior = parentFCE.InheritanceBehavior;
                    }
                }

                if (!TreeWalkHelper.SkipNext(InheritanceBehavior) && !TreeWalkHelper.SkipNow(parentInheritanceBehavior))
                {
                    // Synchronize InheritanceParent
                    this.SynchronizeInheritanceParent(parent);
                }
                else if (!IsSelfInheritanceParent)
                {
                    // Set IsSelfInheritanceParet on the root node at a tree boundary
                    // so that all inheritable properties are cached on it.
                    SetIsSelfInheritanceParent();
                }

                // Loop through all cached inheritable properties for the parent to see if they should be invalidated.
                return(TreeWalkHelper.InvalidateTreeDependentProperties(parentTreeState, /* fe = */ this, /* fce = */ null, selfStyle, selfThemeStyle,
                                                                        ref childRecord, isChildRecordValid, hasStyleChanged, isSelfInheritanceParent, wasSelfInheritanceParent));
            }
            finally
            {
                AncestorChangeInProgress  = false;
                InVisibilityCollapsedTree = false;  // 'false' just means 'we don't know' - see comment at definition of the flag.
            }
        }
예제 #3
0
        // Invalidate all the properties that may have changed as a result of
        //  changing this element's parent in the logical (and sometimes visual tree.)
        internal FrugalObjectList <DependencyProperty> InvalidateTreeDependentProperties(TreeChangeInfo parentTreeState, bool isSelfInheritanceParent, bool wasSelfInheritanceParent)
        {
            AncestorChangeInProgress = true;


            try
            {
                // Style property is a special case of a non-inherited property that needs
                // invalidation for parent changes. Invalidate StyleProperty if it hasn't been
                // locally set because local value takes precedence over implicit references
                if (!HasLocalStyle && (this != parentTreeState.Root))
                {
                    UpdateStyleProperty();
                }

                Style            selfStyle       = null;
                Style            selfThemeStyle  = null;
                DependencyObject templatedParent = null;

                int         childIndex         = -1;
                ChildRecord childRecord        = new ChildRecord();
                bool        isChildRecordValid = false;

                selfStyle       = Style;
                selfThemeStyle  = ThemeStyle;
                templatedParent = TemplatedParent;
                childIndex      = TemplateChildIndex;

                // StyleProperty could have changed during invalidation of ResourceReferenceExpressions if it
                // were locally set or during the invalidation of unresolved implicitly referenced style
                bool hasStyleChanged = HasStyleChanged;

                // Fetch selfStyle, hasStyleChanged and childIndex for the current node
                FrameworkElement.GetTemplatedParentChildRecord(templatedParent, childIndex, out childRecord, out isChildRecordValid);

                FrameworkElement        parentFE;
                FrameworkContentElement parentFCE;
                bool hasParent = FrameworkElement.GetFrameworkParent(this, out parentFE, out parentFCE);

                DependencyObject    parent = null;
                InheritanceBehavior parentInheritanceBehavior = InheritanceBehavior.Default;
                if (hasParent)
                {
                    if (parentFE != null)
                    {
                        parent = parentFE;
                        parentInheritanceBehavior = parentFE.InheritanceBehavior;
                    }
                    else
                    {
                        parent = parentFCE;
                        parentInheritanceBehavior = parentFCE.InheritanceBehavior;
                    }
                }

                if (!TreeWalkHelper.SkipNext(InheritanceBehavior) && !TreeWalkHelper.SkipNow(parentInheritanceBehavior))
                {
                    // Synchronize InheritanceParent
                    this.SynchronizeInheritanceParent(parent);
                }
                else if (!IsSelfInheritanceParent)
                {
                    // Set IsSelfInheritanceParet on the root node at a tree boundary
                    // so that all inheritable properties are cached on it.
                    SetIsSelfInheritanceParent();
                }

                // Loop through all cached inheritable properties for the parent to see if they should be invalidated.
                return(TreeWalkHelper.InvalidateTreeDependentProperties(parentTreeState, /* fe = */ null, /* fce = */ this, selfStyle, selfThemeStyle,
                                                                        ref childRecord, isChildRecordValid, hasStyleChanged, isSelfInheritanceParent, wasSelfInheritanceParent));
            }
            finally
            {
                AncestorChangeInProgress = false;
            }
        }
예제 #4
0
        /// <summary> 
        ///     Invalidate all the properties in the given
        ///     collection of inheritable properties 
        /// </summary> 
        /// <remarks>
        ///     This method is called during an [FE/FCE].OnAncestorChange 
        /// </remarks>
        internal static FrugalObjectList<DependencyProperty> InvalidateTreeDependentProperties(
            TreeChangeInfo                       info,
            FrameworkElement                     fe, 
            FrameworkContentElement              fce,
            Style                                selfStyle, 
            Style                                selfThemeStyle, 
            ref ChildRecord                      childRecord,
            bool                                 isChildRecordValid, 
            bool                                 hasStyleChanged,
            bool                                 isSelfInheritanceParent)
        {
            Debug.Assert(fe != null || fce != null, "Must have non-null current node"); 
            DependencyObject d = fe != null ? (DependencyObject)fe : (DependencyObject)fce;
            FrameworkObject fo = new FrameworkObject(fe, fce); 
 
            // Pull up the parent's InheritableProperties cache
            FrugalObjectList<DependencyProperty> parentInheritableProperties = info.InheritablePropertiesStack.Peek(); 

            // Loop through all cached inheritable
            // to see if they should be invalidated.
            int inheritablePropertiesCount = parentInheritableProperties  != null ? parentInheritableProperties.Count : 0; 

            FrugalObjectList<DependencyProperty> currentInheritableProperties = null; 
            if (HasChildren(fe, fce)) 
            {
                currentInheritableProperties = new FrugalObjectList<DependencyProperty>(inheritablePropertiesCount); 
            }

            info.ResetInheritableValueIndexer();
 
            for (int i = 0; i < inheritablePropertiesCount; i++)
            { 
                DependencyProperty inheritableProperty = parentInheritableProperties[i]; 

                Debug.Assert(inheritableProperty.IsPotentiallyInherited, "if we got here, it means that this property is inheritable by someone"); 

                PropertyMetadata metadata = inheritableProperty.GetMetadata(d);

                // Invalidate only properties that are marked as inheritable. 
                // These are the ones that will be affected by an ancestor changes.
                if (metadata.IsInherited) 
                { 
                    FrameworkPropertyMetadata fMetadata = (FrameworkPropertyMetadata)metadata;
 
                    bool changed = InvalidateTreeDependentProperty(info, d, ref fo, inheritableProperty, fMetadata,
                        selfStyle, selfThemeStyle, ref childRecord, isChildRecordValid, hasStyleChanged, isSelfInheritanceParent);

                    // If a change is detected then add the inheritable property to 
                    // the current list so that it can be used to invalidate further children
                    if (changed && currentInheritableProperties != null) 
                    { 
                        Debug.Assert(!currentInheritableProperties.Contains(inheritableProperty), "InheritableProperties list should not have duplicates");
 
                        // Children do not need to inherit properties across a tree boundary
                        // unless the property is set to override this behavior.

                        if (!SkipNow(fo.InheritanceBehavior) || fMetadata.OverridesInheritanceBehavior) 
                        {
                            currentInheritableProperties.Add(inheritableProperty); 
                        } 
                    }
                } 
            }

            return currentInheritableProperties;
        } 
예제 #5
0
        // Token: 0x06000C65 RID: 3173 RVA: 0x0002E3C0 File Offset: 0x0002C5C0
        internal static FrugalObjectList <DependencyProperty> InvalidateTreeDependentProperties(TreeChangeInfo info, FrameworkElement fe, FrameworkContentElement fce, Style selfStyle, Style selfThemeStyle, ref ChildRecord childRecord, bool isChildRecordValid, bool hasStyleChanged, bool isSelfInheritanceParent, bool wasSelfInheritanceParent)
        {
            DependencyObject dependencyObject = (fe != null) ? fe : fce;
            FrameworkObject  frameworkObject  = new FrameworkObject(fe, fce);
            FrugalObjectList <DependencyProperty> frugalObjectList = info.InheritablePropertiesStack.Peek();
            int num = (frugalObjectList != null) ? frugalObjectList.Count : 0;
            FrugalObjectList <DependencyProperty> frugalObjectList2 = null;

            if (TreeWalkHelper.HasChildren(fe, fce))
            {
                frugalObjectList2 = new FrugalObjectList <DependencyProperty>(num);
            }
            info.ResetInheritableValueIndexer();
            for (int i = 0; i < num; i++)
            {
                DependencyProperty dependencyProperty = frugalObjectList[i];
                PropertyMetadata   metadata           = dependencyProperty.GetMetadata(dependencyObject);
                if (metadata.IsInherited)
                {
                    FrameworkPropertyMetadata frameworkPropertyMetadata = (FrameworkPropertyMetadata)metadata;
                    bool flag = TreeWalkHelper.InvalidateTreeDependentProperty(info, dependencyObject, ref frameworkObject, dependencyProperty, frameworkPropertyMetadata, selfStyle, selfThemeStyle, ref childRecord, isChildRecordValid, hasStyleChanged, isSelfInheritanceParent, wasSelfInheritanceParent);
                    if (flag && frugalObjectList2 != null && (!TreeWalkHelper.SkipNow(frameworkObject.InheritanceBehavior) || frameworkPropertyMetadata.OverridesInheritanceBehavior))
                    {
                        frugalObjectList2.Add(dependencyProperty);
                    }
                }
            }
            return(frugalObjectList2);
        }
예제 #6
0
 // Token: 0x06000C66 RID: 3174 RVA: 0x0002E490 File Offset: 0x0002C690
 private static bool InvalidateTreeDependentProperty(TreeChangeInfo info, DependencyObject d, ref FrameworkObject fo, DependencyProperty dp, FrameworkPropertyMetadata fMetadata, Style selfStyle, Style selfThemeStyle, ref ChildRecord childRecord, bool isChildRecordValid, bool hasStyleChanged, bool isSelfInheritanceParent, bool wasSelfInheritanceParent)
 {
     if (!TreeWalkHelper.SkipNext(fo.InheritanceBehavior) || fMetadata.OverridesInheritanceBehavior)
     {
         InheritablePropertyChangeInfo rootInheritableValue = info.GetRootInheritableValue(dp);
         EffectiveValueEntry           oldEntry             = rootInheritableValue.OldEntry;
         EffectiveValueEntry           effectiveValueEntry  = info.IsAddOperation ? rootInheritableValue.NewEntry : new EffectiveValueEntry(dp, BaseValueSourceInternal.Inherited);
         bool flag = TreeWalkHelper.IsForceInheritedProperty(dp);
         if (d != info.Root)
         {
             if (wasSelfInheritanceParent)
             {
                 oldEntry = d.GetValueEntry(d.LookupEntry(dp.GlobalIndex), dp, fMetadata, RequestFlags.DeferredReferences);
             }
             else if (isSelfInheritanceParent)
             {
                 EffectiveValueEntry valueEntry = d.GetValueEntry(d.LookupEntry(dp.GlobalIndex), dp, fMetadata, RequestFlags.DeferredReferences);
                 if (valueEntry.BaseValueSourceInternal <= BaseValueSourceInternal.Inherited)
                 {
                     oldEntry = oldEntry.GetFlattenedEntry(RequestFlags.FullyResolved);
                     oldEntry.BaseValueSourceInternal = BaseValueSourceInternal.Inherited;
                 }
                 else
                 {
                     oldEntry = valueEntry;
                 }
             }
             else
             {
                 oldEntry = oldEntry.GetFlattenedEntry(RequestFlags.FullyResolved);
                 oldEntry.BaseValueSourceInternal = BaseValueSourceInternal.Inherited;
             }
         }
         else if (info.IsAddOperation && (flag || oldEntry.BaseValueSourceInternal <= BaseValueSourceInternal.Inherited))
         {
             EffectiveValueEntry valueEntry2 = d.GetValueEntry(d.LookupEntry(dp.GlobalIndex), dp, fMetadata, RequestFlags.DeferredReferences);
             if (valueEntry2.BaseValueSourceInternal > BaseValueSourceInternal.Inherited)
             {
                 oldEntry = valueEntry2;
             }
         }
         OperationType operationType = info.IsAddOperation ? OperationType.AddChild : OperationType.RemoveChild;
         if (BaseValueSourceInternal.Inherited >= oldEntry.BaseValueSourceInternal)
         {
             return((d.UpdateEffectiveValue(d.LookupEntry(dp.GlobalIndex), dp, fMetadata, oldEntry, ref effectiveValueEntry, false, false, operationType) & (UpdateResult)5) == UpdateResult.ValueChanged);
         }
         if (flag)
         {
             effectiveValueEntry = new EffectiveValueEntry(dp, FullValueSource.IsCoerced);
             return((d.UpdateEffectiveValue(d.LookupEntry(dp.GlobalIndex), dp, fMetadata, oldEntry, ref effectiveValueEntry, false, false, operationType) & (UpdateResult)5) == UpdateResult.ValueChanged);
         }
     }
     return(false);
 }
예제 #7
0
        // Fetchs the specified childRecord for the given template.  Returns true if successful.
        internal static void GetTemplatedParentChildRecord( 
            DependencyObject templatedParent,
            int childIndex, 
            out ChildRecord childRecord, 
            out bool isChildRecordValid)
        { 
            FrameworkTemplate templatedParentTemplate = null;
            isChildRecordValid = false;
            childRecord = new ChildRecord();    // CS0177
 
            if (templatedParent != null)
            { 
                FrameworkObject foTemplatedParent = new FrameworkObject(templatedParent, true); 

                Debug.Assert( foTemplatedParent.IsFE ); 

                // This node is the result of a style expansion

                // Pick the owner for the VisualTree that generated this node 
                templatedParentTemplate = foTemplatedParent.FE.TemplateInternal;
 
                Debug.Assert(templatedParentTemplate != null , 
                    "If this node is the result of a VisualTree expansion then it should have a parent template");
 
                // Check if this Child Index is represented in FrameworkTemplate
                if (templatedParentTemplate != null && ((0 <= childIndex) && (childIndex < templatedParentTemplate.ChildRecordFromChildIndex.Count)))
                {
                    childRecord = templatedParentTemplate.ChildRecordFromChildIndex[childIndex]; 
                    isChildRecordValid = true;
                } 
 
            }
        } 
예제 #8
0
 internal FrugalObjectList<DependencyProperty> InvalidateTreeDependentProperties(TreeChangeInfo parentTreeState, bool isSelfInheritanceParent)
 {
     this.AncestorChangeInProgress = true;
       this.InVisibilityCollapsedTree = false;
       if (parentTreeState.TopmostCollapsedParentNode == null)
       {
     if (this.Visibility == Visibility.Collapsed)
     {
       parentTreeState.TopmostCollapsedParentNode = (object) this;
       this.InVisibilityCollapsedTree = true;
     }
       }
       else
     this.InVisibilityCollapsedTree = true;
       try
       {
     if (this.IsInitialized && !this.HasLocalStyle && this != parentTreeState.Root)
       this.UpdateStyleProperty();
     ChildRecord childRecord = new ChildRecord();
     bool isChildRecordValid = false;
     Style style = this.Style;
     Style themeStyle = this.ThemeStyle;
     DependencyObject templatedParent = this.TemplatedParent;
     int templateChildIndex = this.TemplateChildIndex;
     bool hasStyleChanged = this.HasStyleChanged;
     FrameworkElement.GetTemplatedParentChildRecord(templatedParent, templateChildIndex, out childRecord, out isChildRecordValid);
     FrameworkElement feParent;
     FrameworkContentElement fceParent;
     bool frameworkParent = FrameworkElement.GetFrameworkParent(this, out feParent, out fceParent);
     DependencyObject parent = (DependencyObject) null;
     InheritanceBehavior inheritanceBehavior = InheritanceBehavior.Default;
     if (frameworkParent)
     {
       if (feParent != null)
       {
     parent = (DependencyObject) feParent;
     inheritanceBehavior = feParent.InheritanceBehavior;
       }
       else
       {
     parent = (DependencyObject) fceParent;
     inheritanceBehavior = fceParent.InheritanceBehavior;
       }
     }
     if (!TreeWalkHelper.SkipNext(this.InheritanceBehavior) && !TreeWalkHelper.SkipNow(inheritanceBehavior))
       this.SynchronizeInheritanceParent(parent);
     else if (!this.IsSelfInheritanceParent)
       this.SetIsSelfInheritanceParent();
     return TreeWalkHelper.InvalidateTreeDependentProperties(parentTreeState, this, (FrameworkContentElement) null, style, themeStyle, ref childRecord, isChildRecordValid, hasStyleChanged, isSelfInheritanceParent);
       }
       finally
       {
     this.AncestorChangeInProgress = false;
     this.InVisibilityCollapsedTree = false;
       }
 }
예제 #9
0
 internal static void GetTemplatedParentChildRecord(DependencyObject templatedParent, int childIndex, out ChildRecord childRecord, out bool isChildRecordValid)
 {
     isChildRecordValid = false;
       childRecord = new ChildRecord();
       if (templatedParent == null)
     return;
       FrameworkTemplate templateInternal = new FrameworkObject(templatedParent, true).FE.TemplateInternal;
       if (templateInternal == null || 0 > childIndex || childIndex >= templateInternal.ChildRecordFromChildIndex.Count)
     return;
       childRecord = templateInternal.ChildRecordFromChildIndex[childIndex];
       isChildRecordValid = true;
 }
예제 #10
0
        // Invalidate all the properties that may have changed as a result of
        //  changing this element's parent in the logical (and sometimes visual tree.)
        internal FrugalObjectList<DependencyProperty> InvalidateTreeDependentProperties(TreeChangeInfo parentTreeState, bool isSelfInheritanceParent)
        {
            AncestorChangeInProgress = true;


            try
            {
                // Style property is a special case of a non-inherited property that needs
                // invalidation for parent changes. Invalidate StyleProperty if it hasn't been
                // locally set because local value takes precedence over implicit references
                if (!HasLocalStyle && (this != parentTreeState.Root))
                {
                    UpdateStyleProperty();
                }

                Style selfStyle = null;
                Style selfThemeStyle = null;
                DependencyObject templatedParent = null;

                int childIndex = -1;
                ChildRecord childRecord = new ChildRecord();
                bool isChildRecordValid = false;

                selfStyle = Style;
                selfThemeStyle = ThemeStyle;
                templatedParent = TemplatedParent;
                childIndex = TemplateChildIndex;

                // StyleProperty could have changed during invalidation of ResourceReferenceExpressions if it
                // were locally set or during the invalidation of unresolved implicitly referenced style
                bool hasStyleChanged = HasStyleChanged;

                // Fetch selfStyle, hasStyleChanged and childIndex for the current node
                FrameworkElement.GetTemplatedParentChildRecord(templatedParent, childIndex, out childRecord, out isChildRecordValid);

                FrameworkElement parentFE;
                FrameworkContentElement parentFCE;
                bool hasParent = FrameworkElement.GetFrameworkParent(this, out parentFE, out parentFCE);

                DependencyObject parent = null;
                InheritanceBehavior parentInheritanceBehavior = InheritanceBehavior.Default;
                if (hasParent)
                {
                    if (parentFE != null)
                    {
                        parent = parentFE;
                        parentInheritanceBehavior = parentFE.InheritanceBehavior;
                    }
                    else
                    {
                        parent = parentFCE;
                        parentInheritanceBehavior = parentFCE.InheritanceBehavior;
                    }
                }

                if (!TreeWalkHelper.SkipNext(InheritanceBehavior) && !TreeWalkHelper.SkipNow(parentInheritanceBehavior))
                {
                    // Synchronize InheritanceParent
                    this.SynchronizeInheritanceParent(parent);
                }
                else if (!IsSelfInheritanceParent)
                {
                    // Set IsSelfInheritanceParet on the root node at a tree boundary 
                    // so that all inheritable properties are cached on it.
                    SetIsSelfInheritanceParent();
                }

                // Loop through all cached inheritable properties for the parent to see if they should be invalidated.
                return TreeWalkHelper.InvalidateTreeDependentProperties(parentTreeState, /* fe = */ null, /* fce = */ this, selfStyle, selfThemeStyle,
                    ref childRecord, isChildRecordValid, hasStyleChanged, isSelfInheritanceParent);
            }
            finally
            {
                AncestorChangeInProgress = false;

            }
        }
        // Invalidate all the properties that may have changed as a result of
        //  changing this element's parent in the logical (and sometimes visual tree.)
        internal FrugalObjectList<DependencyProperty> InvalidateTreeDependentProperties(TreeChangeInfo parentTreeState, bool isSelfInheritanceParent)
        {
            AncestorChangeInProgress = true;

            InVisibilityCollapsedTree = false;  // False == we don't know whether we're in a visibility collapsed tree.

            if (parentTreeState.TopmostCollapsedParentNode == null)
            {
                // There is no ancestor node with Visibility=Collapsed.
                //  See if "fe" is the root of a collapsed subtree.
                if (Visibility == Visibility.Collapsed)
                {
                    // This is indeed the root of a collapsed subtree.
                    //  remember this information as we proceed on the tree walk.
                    parentTreeState.TopmostCollapsedParentNode = this;

                    // Yes, this FE node is in a visibility collapsed subtree.
                    InVisibilityCollapsedTree = true;
                }
            }
            else
            {
                // There is an ancestor node somewhere above us with
                //  Visibility=Collapsed.  We're in a visibility collapsed subtree.
                InVisibilityCollapsedTree = true;
            }


            try
            {
                // Style property is a special case of a non-inherited property that needs
                // invalidation for parent changes. Invalidate StyleProperty if it hasn't been
                // locally set because local value takes precedence over implicit references
                if (IsInitialized && !HasLocalStyle && (this != parentTreeState.Root))
                {
                    UpdateStyleProperty();
                }

                Style selfStyle = null;
                Style selfThemeStyle = null;
                DependencyObject templatedParent = null;

                int childIndex = -1;
                ChildRecord childRecord = new ChildRecord();
                bool isChildRecordValid = false;

                selfStyle = Style;
                selfThemeStyle = ThemeStyle;
                templatedParent = TemplatedParent;
                childIndex = TemplateChildIndex;

                // StyleProperty could have changed during invalidation of ResourceReferenceExpressions if it
                // were locally set or during the invalidation of unresolved implicitly referenced style
                bool hasStyleChanged = HasStyleChanged;

                // Fetch selfStyle, hasStyleChanged and childIndex for the current node
                FrameworkElement.GetTemplatedParentChildRecord(templatedParent, childIndex, out childRecord, out isChildRecordValid);

                FrameworkElement parentFE;
                FrameworkContentElement parentFCE;
                bool hasParent = FrameworkElement.GetFrameworkParent(this, out parentFE, out parentFCE);

                DependencyObject parent = null;
                InheritanceBehavior parentInheritanceBehavior = InheritanceBehavior.Default;
                if (hasParent)
                {
                    if (parentFE != null)
                    {
                        parent = parentFE;
                        parentInheritanceBehavior = parentFE.InheritanceBehavior;
                    }
                    else
                    {
                        parent = parentFCE;
                        parentInheritanceBehavior = parentFCE.InheritanceBehavior;
                    }
                }

                if (!TreeWalkHelper.SkipNext(InheritanceBehavior) && !TreeWalkHelper.SkipNow(parentInheritanceBehavior))
                {
                    // Synchronize InheritanceParent
                    this.SynchronizeInheritanceParent(parent);
                }
                else if (!IsSelfInheritanceParent)
                {
                    // Set IsSelfInheritanceParet on the root node at a tree boundary 
                    // so that all inheritable properties are cached on it.
                    SetIsSelfInheritanceParent();
                }

                // Loop through all cached inheritable properties for the parent to see if they should be invalidated.
                return TreeWalkHelper.InvalidateTreeDependentProperties(parentTreeState, /* fe = */ this, /* fce = */ null, selfStyle, selfThemeStyle,
                    ref childRecord, isChildRecordValid, hasStyleChanged, isSelfInheritanceParent);
            }
            finally
            {
                AncestorChangeInProgress = false;
                InVisibilityCollapsedTree = false;  // 'false' just means 'we don't know' - see comment at definition of the flag.
            }
        }