Code:
/ Dotnetfx_Vista_SP2 / Dotnetfx_Vista_SP2 / 8.0.50727.4016 / DEVDIV / depot / DevDiv / releases / Orcas / QFE / wpf / src / Core / CSharp / System / Windows / Media / Animation / AnimationLayer.cs / 1 / AnimationLayer.cs
// AnimationLayer.cs
using System.Collections.Generic;
using System.Diagnostics;
namespace System.Windows.Media.Animation
{
internal class AnimationLayer
{
private object _snapshotValue = DependencyProperty.UnsetValue;
private IList _animationClocks;
private AnimationStorage _ownerStorage;
private EventHandler _removeRequestedHandler;
private bool _hasStickySnapshotValue;
internal AnimationLayer(AnimationStorage ownerStorage)
{
Debug.Assert(ownerStorage != null);
_ownerStorage = ownerStorage;
_removeRequestedHandler = new EventHandler(OnRemoveRequested);
}
internal void ApplyAnimationClocks(
IList newAnimationClocks,
HandoffBehavior handoffBehavior,
object defaultDestinationValue)
{
Debug.Assert(
newAnimationClocks == null
|| (newAnimationClocks.Count > 0
&& !newAnimationClocks.Contains(null)));
if (handoffBehavior == HandoffBehavior.SnapshotAndReplace)
{
Debug.Assert(defaultDestinationValue != DependencyProperty.UnsetValue,
"We need a valid default destination value when peforming a snapshot and replace.");
EventHandler handler = new EventHandler(OnCurrentStateInvalidated);
// If we have a sticky snapshot value, the clock that would have
// unstuck it is being replaced, so we need to remove our event
// handler from that clock.
if (_hasStickySnapshotValue)
{
_animationClocks[0].CurrentStateInvalidated -= handler;
DetachAnimationClocks();
}
// Otherwise if we have at least one clock take a new snapshot
// value.
else if (_animationClocks != null)
{
_snapshotValue = GetCurrentValue(defaultDestinationValue);
DetachAnimationClocks();
}
// Otherwise we can use the defaultDestinationValue as the
// new snapshot value.
else
{
_snapshotValue = defaultDestinationValue;
}
// If we have a new clock in a stopped state, then the snapshot
// value will be sticky.
if (newAnimationClocks != null
&& newAnimationClocks[0].CurrentState == ClockState.Stopped)
{
_hasStickySnapshotValue = true;
newAnimationClocks[0].CurrentStateInvalidated += handler;
}
// Otherwise it won't be sticky.
else
{
_hasStickySnapshotValue = false;
}
SetAnimationClocks(newAnimationClocks);
}
else
{
Debug.Assert(handoffBehavior == HandoffBehavior.Compose,
"Unhandled handoffBehavior value.");
Debug.Assert(defaultDestinationValue == DependencyProperty.UnsetValue,
"We shouldn't take the time to calculate a default destination value when it isn't needed.");
if (newAnimationClocks == null)
{
return;
}
else if (_animationClocks == null)
{
SetAnimationClocks(newAnimationClocks);
}
else
{
AppendAnimationClocks(newAnimationClocks);
}
}
}
private void DetachAnimationClocks()
{
Debug.Assert(_animationClocks != null);
int count = _animationClocks.Count;
for (int i = 0; i < count; i++)
{
_ownerStorage.DetachAnimationClock(_animationClocks[i], _removeRequestedHandler);
}
_animationClocks = null;
}
private void SetAnimationClocks(
IList animationClocks)
{
Debug.Assert(animationClocks != null);
Debug.Assert(animationClocks.Count > 0);
Debug.Assert(!animationClocks.Contains(null));
Debug.Assert(_animationClocks == null);
_animationClocks = animationClocks;
int count = animationClocks.Count;
for (int i = 0; i < count; i++)
{
_ownerStorage.AttachAnimationClock(animationClocks[i], _removeRequestedHandler);
}
}
private void OnCurrentStateInvalidated(object sender, EventArgs args)
{
Debug.Assert(_hasStickySnapshotValue,
"_hasStickySnapshotValue should be set to true if OnCurrentStateInvalidated has been called.");
_hasStickySnapshotValue = false;
((AnimationClock)sender).CurrentStateInvalidated -= new EventHandler(OnCurrentStateInvalidated);
}
private void OnRemoveRequested(object sender, EventArgs args)
{
Debug.Assert(_animationClocks != null
&& _animationClocks.Count > 0,
"An AnimationClock no longer associated with a property should not have a RemoveRequested event handler.");
AnimationClock animationClock = (AnimationClock)sender;
int index = _animationClocks.IndexOf(animationClock);
Debug.Assert(index >= 0,
"An AnimationClock no longer associated with a property should not have a RemoveRequested event handler.");
if (_hasStickySnapshotValue
&& index == 0)
{
_animationClocks[0].CurrentStateInvalidated -= new EventHandler(OnCurrentStateInvalidated);
_hasStickySnapshotValue = false;
}
_animationClocks.RemoveAt(index);
_ownerStorage.DetachAnimationClock(animationClock, _removeRequestedHandler);
AnimationStorage tmpOwnerStorage = _ownerStorage;
if (_animationClocks.Count == 0)
{
_animationClocks = null;
_snapshotValue = DependencyProperty.UnsetValue;
_ownerStorage.RemoveLayer(this);
_ownerStorage = null;
}
// _ownerStorage may be null here.
tmpOwnerStorage.WritePostscript();
}
private void AppendAnimationClocks(
IList newAnimationClocks)
{
Debug.Assert(newAnimationClocks != null);
Debug.Assert(newAnimationClocks.Count > 0);
Debug.Assert(!newAnimationClocks.Contains(null));
// _animationClocks may be null or non-null here.
int newClocksCount = newAnimationClocks.Count;
List animationClockList = _animationClocks as List;
// If _animationClocks is not a List then make it one.
if (animationClockList == null)
{
int oldClocksCount = (_animationClocks == null) ? 0 : _animationClocks.Count;
animationClockList = new List(oldClocksCount + newClocksCount);
for (int i = 0; i < oldClocksCount; i++)
{
animationClockList.Add(_animationClocks[i]);
}
_animationClocks = animationClockList;
}
for (int i = 0; i < newClocksCount; i++)
{
AnimationClock clock = newAnimationClocks[i];
animationClockList.Add(clock);
_ownerStorage.AttachAnimationClock(clock, _removeRequestedHandler);
}
}
internal object GetCurrentValue(
object defaultDestinationValue)
{
Debug.Assert(defaultDestinationValue != DependencyProperty.UnsetValue);
// We have a sticky snapshot value if changes have been made to the
// animations in this layer since the last tick. This flag will be
// unset when the next tick starts.
//
// Since CurrentTimeInvaliated is raised before CurrentStateInvalidated
// we need to check the state of the first clock as well to avoid
// potential first frame issues. In this case _hasStickySnapshotValue
// will be updated to false shortly.
if ( _hasStickySnapshotValue
&& _animationClocks[0].CurrentState == ClockState.Stopped)
{
return _snapshotValue;
}
// This layer just contains a snapshot value or a fill value after
// all the clocks have been completed.
if (_animationClocks == null)
{
Debug.Assert(_snapshotValue != DependencyProperty.UnsetValue);
// In this case, we're using _snapshotValue to store the value,
// but the value here does not represent the snapshotValue. It
// represents the fill value of an animation clock that has been
// removed for performance reason because we know it will never
// be restarted.
return _snapshotValue;
}
object currentLayerValue = _snapshotValue;
bool hasUnstoppedClocks = false;
if (currentLayerValue == DependencyProperty.UnsetValue)
{
currentLayerValue = defaultDestinationValue;
}
int count = _animationClocks.Count;
Debug.Assert(count > 0);
for (int i = 0; i < count; i++)
{
AnimationClock clock = _animationClocks[i];
if (clock.CurrentState != ClockState.Stopped)
{
hasUnstoppedClocks = true;
currentLayerValue = clock.GetCurrentValue(
currentLayerValue,
defaultDestinationValue);
}
}
if (hasUnstoppedClocks)
{
return currentLayerValue;
}
else
{
return defaultDestinationValue;
}
}
}
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.
// AnimationLayer.cs
using System.Collections.Generic;
using System.Diagnostics;
namespace System.Windows.Media.Animation
{
internal class AnimationLayer
{
private object _snapshotValue = DependencyProperty.UnsetValue;
private IList _animationClocks;
private AnimationStorage _ownerStorage;
private EventHandler _removeRequestedHandler;
private bool _hasStickySnapshotValue;
internal AnimationLayer(AnimationStorage ownerStorage)
{
Debug.Assert(ownerStorage != null);
_ownerStorage = ownerStorage;
_removeRequestedHandler = new EventHandler(OnRemoveRequested);
}
internal void ApplyAnimationClocks(
IList newAnimationClocks,
HandoffBehavior handoffBehavior,
object defaultDestinationValue)
{
Debug.Assert(
newAnimationClocks == null
|| (newAnimationClocks.Count > 0
&& !newAnimationClocks.Contains(null)));
if (handoffBehavior == HandoffBehavior.SnapshotAndReplace)
{
Debug.Assert(defaultDestinationValue != DependencyProperty.UnsetValue,
"We need a valid default destination value when peforming a snapshot and replace.");
EventHandler handler = new EventHandler(OnCurrentStateInvalidated);
// If we have a sticky snapshot value, the clock that would have
// unstuck it is being replaced, so we need to remove our event
// handler from that clock.
if (_hasStickySnapshotValue)
{
_animationClocks[0].CurrentStateInvalidated -= handler;
DetachAnimationClocks();
}
// Otherwise if we have at least one clock take a new snapshot
// value.
else if (_animationClocks != null)
{
_snapshotValue = GetCurrentValue(defaultDestinationValue);
DetachAnimationClocks();
}
// Otherwise we can use the defaultDestinationValue as the
// new snapshot value.
else
{
_snapshotValue = defaultDestinationValue;
}
// If we have a new clock in a stopped state, then the snapshot
// value will be sticky.
if (newAnimationClocks != null
&& newAnimationClocks[0].CurrentState == ClockState.Stopped)
{
_hasStickySnapshotValue = true;
newAnimationClocks[0].CurrentStateInvalidated += handler;
}
// Otherwise it won't be sticky.
else
{
_hasStickySnapshotValue = false;
}
SetAnimationClocks(newAnimationClocks);
}
else
{
Debug.Assert(handoffBehavior == HandoffBehavior.Compose,
"Unhandled handoffBehavior value.");
Debug.Assert(defaultDestinationValue == DependencyProperty.UnsetValue,
"We shouldn't take the time to calculate a default destination value when it isn't needed.");
if (newAnimationClocks == null)
{
return;
}
else if (_animationClocks == null)
{
SetAnimationClocks(newAnimationClocks);
}
else
{
AppendAnimationClocks(newAnimationClocks);
}
}
}
private void DetachAnimationClocks()
{
Debug.Assert(_animationClocks != null);
int count = _animationClocks.Count;
for (int i = 0; i < count; i++)
{
_ownerStorage.DetachAnimationClock(_animationClocks[i], _removeRequestedHandler);
}
_animationClocks = null;
}
private void SetAnimationClocks(
IList animationClocks)
{
Debug.Assert(animationClocks != null);
Debug.Assert(animationClocks.Count > 0);
Debug.Assert(!animationClocks.Contains(null));
Debug.Assert(_animationClocks == null);
_animationClocks = animationClocks;
int count = animationClocks.Count;
for (int i = 0; i < count; i++)
{
_ownerStorage.AttachAnimationClock(animationClocks[i], _removeRequestedHandler);
}
}
private void OnCurrentStateInvalidated(object sender, EventArgs args)
{
Debug.Assert(_hasStickySnapshotValue,
"_hasStickySnapshotValue should be set to true if OnCurrentStateInvalidated has been called.");
_hasStickySnapshotValue = false;
((AnimationClock)sender).CurrentStateInvalidated -= new EventHandler(OnCurrentStateInvalidated);
}
private void OnRemoveRequested(object sender, EventArgs args)
{
Debug.Assert(_animationClocks != null
&& _animationClocks.Count > 0,
"An AnimationClock no longer associated with a property should not have a RemoveRequested event handler.");
AnimationClock animationClock = (AnimationClock)sender;
int index = _animationClocks.IndexOf(animationClock);
Debug.Assert(index >= 0,
"An AnimationClock no longer associated with a property should not have a RemoveRequested event handler.");
if (_hasStickySnapshotValue
&& index == 0)
{
_animationClocks[0].CurrentStateInvalidated -= new EventHandler(OnCurrentStateInvalidated);
_hasStickySnapshotValue = false;
}
_animationClocks.RemoveAt(index);
_ownerStorage.DetachAnimationClock(animationClock, _removeRequestedHandler);
AnimationStorage tmpOwnerStorage = _ownerStorage;
if (_animationClocks.Count == 0)
{
_animationClocks = null;
_snapshotValue = DependencyProperty.UnsetValue;
_ownerStorage.RemoveLayer(this);
_ownerStorage = null;
}
// _ownerStorage may be null here.
tmpOwnerStorage.WritePostscript();
}
private void AppendAnimationClocks(
IList newAnimationClocks)
{
Debug.Assert(newAnimationClocks != null);
Debug.Assert(newAnimationClocks.Count > 0);
Debug.Assert(!newAnimationClocks.Contains(null));
// _animationClocks may be null or non-null here.
int newClocksCount = newAnimationClocks.Count;
List animationClockList = _animationClocks as List;
// If _animationClocks is not a List then make it one.
if (animationClockList == null)
{
int oldClocksCount = (_animationClocks == null) ? 0 : _animationClocks.Count;
animationClockList = new List(oldClocksCount + newClocksCount);
for (int i = 0; i < oldClocksCount; i++)
{
animationClockList.Add(_animationClocks[i]);
}
_animationClocks = animationClockList;
}
for (int i = 0; i < newClocksCount; i++)
{
AnimationClock clock = newAnimationClocks[i];
animationClockList.Add(clock);
_ownerStorage.AttachAnimationClock(clock, _removeRequestedHandler);
}
}
internal object GetCurrentValue(
object defaultDestinationValue)
{
Debug.Assert(defaultDestinationValue != DependencyProperty.UnsetValue);
// We have a sticky snapshot value if changes have been made to the
// animations in this layer since the last tick. This flag will be
// unset when the next tick starts.
//
// Since CurrentTimeInvaliated is raised before CurrentStateInvalidated
// we need to check the state of the first clock as well to avoid
// potential first frame issues. In this case _hasStickySnapshotValue
// will be updated to false shortly.
if ( _hasStickySnapshotValue
&& _animationClocks[0].CurrentState == ClockState.Stopped)
{
return _snapshotValue;
}
// This layer just contains a snapshot value or a fill value after
// all the clocks have been completed.
if (_animationClocks == null)
{
Debug.Assert(_snapshotValue != DependencyProperty.UnsetValue);
// In this case, we're using _snapshotValue to store the value,
// but the value here does not represent the snapshotValue. It
// represents the fill value of an animation clock that has been
// removed for performance reason because we know it will never
// be restarted.
return _snapshotValue;
}
object currentLayerValue = _snapshotValue;
bool hasUnstoppedClocks = false;
if (currentLayerValue == DependencyProperty.UnsetValue)
{
currentLayerValue = defaultDestinationValue;
}
int count = _animationClocks.Count;
Debug.Assert(count > 0);
for (int i = 0; i < count; i++)
{
AnimationClock clock = _animationClocks[i];
if (clock.CurrentState != ClockState.Stopped)
{
hasUnstoppedClocks = true;
currentLayerValue = clock.GetCurrentValue(
currentLayerValue,
defaultDestinationValue);
}
}
if (hasUnstoppedClocks)
{
return currentLayerValue;
}
else
{
return defaultDestinationValue;
}
}
}
}
// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- XmlStringTable.cs
- DataGridViewCellLinkedList.cs
- SrgsGrammarCompiler.cs
- DataGridViewColumnConverter.cs
- SmiMetaData.cs
- OdbcParameterCollection.cs
- DataGrid.cs
- ListSortDescription.cs
- XmlSerializationWriter.cs
- IProvider.cs
- RoleManagerSection.cs
- ContextMenuAutomationPeer.cs
- ProgressiveCrcCalculatingStream.cs
- UxThemeWrapper.cs
- Delegate.cs
- DesignSurfaceEvent.cs
- TreeNodeStyleCollectionEditor.cs
- SortedDictionary.cs
- CompositeDuplexBindingElement.cs
- ColorEditor.cs
- DateTimeEditor.cs
- DynamicQueryableWrapper.cs
- OdbcCommand.cs
- ServicePoint.cs
- MonthCalendar.cs
- XmlSerializer.cs
- ToolBarPanel.cs
- MessageSecurityProtocolFactory.cs
- RemoteCryptoDecryptRequest.cs
- IgnoreSection.cs
- SHA1CryptoServiceProvider.cs
- EllipticalNodeOperations.cs
- FixUpCollection.cs
- NoClickablePointException.cs
- SqlResolver.cs
- cryptoapiTransform.cs
- _BaseOverlappedAsyncResult.cs
- SmiMetaDataProperty.cs
- WebSysDisplayNameAttribute.cs
- XmlDocumentType.cs
- JsonDeserializer.cs
- XmlSchemaAppInfo.cs
- ServiceModelConfigurationSectionCollection.cs
- _OSSOCK.cs
- XmlSchemaParticle.cs
- Padding.cs
- RegexCaptureCollection.cs
- MeshGeometry3D.cs
- CopyOfAction.cs
- EncryptedKeyHashIdentifierClause.cs
- ApplicationSettingsBase.cs
- XXXInfos.cs
- XmlEntityReference.cs
- webeventbuffer.cs
- RightsManagementInformation.cs
- WebPartAddingEventArgs.cs
- HttpResponseMessageProperty.cs
- XmlFormatMapping.cs
- CatalogZoneBase.cs
- SamlDoNotCacheCondition.cs
- WmlControlAdapter.cs
- CompoundFileStreamReference.cs
- WaitHandleCannotBeOpenedException.cs
- LineServices.cs
- HyperLink.cs
- XappLauncher.cs
- String.cs
- DesignerHost.cs
- TextFormatterHost.cs
- TypedDataSourceCodeGenerator.cs
- BevelBitmapEffect.cs
- TemplateControlParser.cs
- RestHandlerFactory.cs
- DataServiceConfiguration.cs
- AbstractSvcMapFileLoader.cs
- RelationshipEntry.cs
- SmtpFailedRecipientException.cs
- ToolStripInSituService.cs
- DataGrid.cs
- QuaternionAnimation.cs
- IDReferencePropertyAttribute.cs
- ProgressBarRenderer.cs
- XLinq.cs
- XmlSecureResolver.cs
- AssemblyResourceLoader.cs
- VisualStates.cs
- EllipseGeometry.cs
- BinaryReader.cs
- Oci.cs
- HostExecutionContextManager.cs
- CompileXomlTask.cs
- SamlAssertion.cs
- OdbcException.cs
- SyntaxCheck.cs
- StringFunctions.cs
- Vector3DCollectionValueSerializer.cs
- DataSourceControl.cs
- ButtonChrome.cs
- altserialization.cs
- ClientSponsor.cs