/// <summary> /// An Animatable will return false from this method if there are any Clocks /// animating any of its properties. If the Animatable has persistent animations /// specified, but all of the Clocks have been removed, it may still return /// true from this method if the Timelines themselves can be frozen. /// </summary> /// <param name="isChecking"> /// True if the Freezable should actually Freeze itself; false if /// the Freezable should simply return whether it can be frozen.</param> /// <returns>True if this object can be frozen; otherwise false.</returns> protected override bool FreezeCore(bool isChecking) { if (IAnimatable_HasAnimatedProperties) { if (TraceFreezable.IsEnabled) { TraceFreezable.Trace( TraceEventType.Warning, TraceFreezable.UnableToFreezeAnimatedProperties, this); } return(false); } return(base.FreezeCore(isChecking)); }
private static bool DefaultFreezeValueCallback( DependencyObject d, DependencyProperty dp, EntryIndex entryIndex, PropertyMetadata metadata, bool isChecking) { // The expression check only needs to be done when isChecking is true // because if we return false here the Freeze() call will fail. if (isChecking) { if (d.HasExpression(entryIndex, dp)) { if (TraceFreezable.IsEnabled) { TraceFreezable.Trace( TraceEventType.Warning, TraceFreezable.UnableToFreezeExpression, d, dp, dp.OwnerType); } return(false); } } if (!dp.IsValueType) { object value = d.GetValueEntry( entryIndex, dp, metadata, RequestFlags.FullyResolved).Value; if (value != null) { Freezable valueAsFreezable = value as Freezable; if (valueAsFreezable != null) { if (!valueAsFreezable.Freeze(isChecking)) { if (TraceFreezable.IsEnabled) { TraceFreezable.Trace( TraceEventType.Warning, TraceFreezable.UnableToFreezeFreezableSubProperty, d, dp, dp.OwnerType); } return(false); } } else // not a Freezable { DispatcherObject valueAsDispatcherObject = value as DispatcherObject; if (valueAsDispatcherObject != null) { if (valueAsDispatcherObject.Dispatcher == null) { // The property is a free-threaded DispatcherObject; since it's // already free-threaded it doesn't prevent this Freezable from // becoming free-threaded too. // It is up to the creator of this type to ensure that the // DispatcherObject is actually immutable } else { // The value of this property derives from DispatcherObject and // has thread affinity; return false. if (TraceFreezable.IsEnabled) { TraceFreezable.Trace( TraceEventType.Warning, TraceFreezable.UnableToFreezeDispatcherObjectWithThreadAffinity, d, dp, dp.OwnerType, valueAsDispatcherObject); } return(false); } } // The property isn't a DispatcherObject. It may be immutable (such as a string) // or the user may have made it thread-safe. It's up to the creator of the type to // do the right thing; we return true as an extensibility point. } } } return(true); }