Code:
/ 4.0 / 4.0 / DEVDIV_TFS / Dev10 / Releases / RTMRel / wpf / src / Framework / System / Windows / Documents / AdornerLayer.cs / 1305600 / AdornerLayer.cs
//---------------------------------------------------------------------------- // //// Copyright (C) Microsoft Corporation. All rights reserved. // // // // Description: // // See spec at: http://avalon/uis/Specs/AdornerLayer%20Spec.htm // // History: // 9/20/2002 susia: Created (DecoratorContainer) // 6/11/2003 psarrett: Ported to WCP tree; merged DecoratorContainer and // AdornerContainerPresenter into AdornerLayer // 10/22/2003 psarrett: Updated as per current spec // //--------------------------------------------------------------------------- using System; using System.Windows.Media; using System.Diagnostics; using System.Collections; using System.Collections.Specialized; using System.Windows.Threading; using System.Windows.Controls; using MS.Utility; using MS.Internal; using MS.Internal.Controls; using MS.Internal.Media; using Microsoft.Internal.AlphaFlattener; // TransformGeometry() namespace System.Windows.Documents { ////// Visual decoration including but not limited to adornments, rubberband selection and /// non-live move feedback. /// /// AdornerLayer expects to be parented by an AdornerDecorator. /// public class AdornerLayer : FrameworkElement { ////// Adorner information /// internal class AdornerInfo { ////// Constructor /// internal AdornerInfo(Adorner adorner) { Invariant.Assert(adorner != null); _adorner = adorner; } ////// Adorner /// internal Adorner Adorner { get { return _adorner; } } ////// The RenderSize (bounding box) of the object we're adorning /// internal Size RenderSize { get { return _computedSize; } set { _computedSize = value; } } ////// Transform on the Visual /// internal GeneralTransform Transform { get { return _transform; } set { _transform = value; } } internal int ZOrder { get { return _zOrder; } set { _zOrder = value; } } internal Geometry Clip { get { return _clip; } set { _clip = value; } } private Adorner _adorner; private Size _computedSize; private GeneralTransform _transform; private int _zOrder; private Geometry _clip; } //----------------------------------------------------- // // Constructors // //----------------------------------------------------- #region Constructors ////// Constructor /// ////// Note that because we're setting up an event handler here, we won't be GC'd until /// our parent is GC'd. So the implicit assumption is that the AdornerLayer, once /// created, exists until its parent is deleted. /// internal AdornerLayer() : this(Dispatcher.CurrentDispatcher) { } ////// Constructor /// /// Dispatcher ////// Note that because we're setting up an event handler here, we won't be GC'd until /// our parent is GC'd. So the implicit assumption is that the AdornerLayer, once /// created, exists until its parent is deleted. /// internal AdornerLayer(Dispatcher context) { if (context == null) throw new ArgumentNullException("context"); LayoutUpdated += new EventHandler(OnLayoutUpdated); _children = new VisualCollection(this); } #endregion Constructors //------------------------------------------------------ // // Public Methods // //----------------------------------------------------- #region Public Methods ////// Add given Adorner to our children /// /// Adorner to add public void Add(Adorner adorner) { Add(adorner, DefaultZOrder); } ////// Remove given adorner. This method will not complain if the given adorner is not /// in the AdornerLayer. /// /// adorner to remove public void Remove(Adorner adorner) { if (adorner == null) throw new ArgumentNullException("adorner"); ArrayList adornerInfos = ElementMap[adorner.AdornedElement] as ArrayList; if (adornerInfos == null) { // We currently allow adorners to be added on elements that can't be adorned, then // throw those away later without notifying anyone. Consequently, Remove() shouldn't throw. return; } AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo == null) { // We currently allow adorners to be added on elements that can't be adorned, then // throw those away later without notifying anyone. Consequently, Remove() shouldn't throw. return; } RemoveAdornerInfo(ElementMap, adorner, adorner.AdornedElement); RemoveAdornerInfo(_zOrderMap, adorner, adornerInfo.ZOrder); _children.Remove(adorner); RemoveLogicalChild(adorner); } ////// Update (layout and render) all adorners. /// public void Update() { foreach (UIElement key in ElementMap.Keys) { ArrayList adornerInfos = (ArrayList)ElementMap[key]; int i = 0; if (adornerInfos != null) { while (i < adornerInfos.Count) { InvalidateAdorner((AdornerInfo)adornerInfos[i++]); } } } UpdateAdorner(null); } ////// Update (layout and render) all adorners for the given element. /// /// element key for redraw public void Update(UIElement element) { if (element == null) throw new ArgumentNullException("element"); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null) throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); int i = 0; while (i < adornerInfos.Count) { InvalidateAdorner((AdornerInfo)adornerInfos[i++]); } UpdateAdorner(element); } ////// Return a collection of all adorners adorning the given element /// /// Element for which adorners are to be retrieved ///array of adorners on given element, or null if /// no adorners exist public Adorner[] GetAdorners(UIElement element) { if (element == null) throw new ArgumentNullException("element"); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null || adornerInfos.Count == 0) return null; Adorner[] adorners = new Adorner[adornerInfos.Count]; for (int i = 0; i < adornerInfos.Count; i++) adorners[i] = ((AdornerInfo)adornerInfos[i]).Adorner; return adorners; } ////// Determine if the given point is on an adorner. /// /// point to test ///AdornerHitTestResult containing the hit visual and the adorner that visual /// is part of. If the no adorner was hit, null is returned public AdornerHitTestResult AdornerHitTest(Point point) { PointHitTestResult result = VisualTreeUtils.AsNearestPointHitTestResult(VisualTreeHelper.HitTest(this, point, false)); if (result != null && result.VisualHit != null) { Visual visual = result.VisualHit; while (visual != this) { if (visual is Adorner) return new AdornerHitTestResult(result.VisualHit, result.PointHit, visual as Adorner); // we intentionally separate adorners from spanning 3D boundaries // and if the parent is ever 3D there was a mistake visual = (Visual)VisualTreeHelper.GetParent(visual); } return null; } else { return null; } } ////// Walk up the visual tree to find the nearest AdornerLayer. /// /// Visual from which the treewalk begins ///First AdornerLayer above given element, or null static public AdornerLayer GetAdornerLayer(Visual visual) { if (visual == null) throw new ArgumentNullException("visual"); Visual parent = VisualTreeHelper.GetParent(visual) as Visual; while (parent != null) { if (parent is AdornerDecorator) return ((AdornerDecorator)parent).AdornerLayer; if (parent is ScrollContentPresenter) return ((ScrollContentPresenter)parent).AdornerLayer; parent = VisualTreeHelper.GetParent(parent) as Visual; } return null; } #endregion Public Methods //------------------------------------------------------ // // Public Properties // //------------------------------------------------------ #region Public Properties #endregion Public Properties //----------------------------------------------------- // // Public Events // //------------------------------------------------------ //----------------------------------------------------- // // Protected Methods // //----------------------------------------------------- #region Protected Methods ////// Derived classes override this property to enable the Visual code to enumerate /// the Visual children. Derived classes need to return the number of children /// from this method. /// /// By default a Visual does not have any children. /// /// Remark: /// During this virtual method the Visual tree must not be modified. /// protected override int VisualChildrenCount { get { //_children cannot be null as its initialized in the constructor return _children.Count; } } ////// Derived class must implement to support Visual children. The method must return /// the child at the specified index. Index must be between 0 and GetVisualChildrenCount-1. /// /// By default a Visual does not have any children. /// /// Remark: /// During this virtual call it is not valid to modify the Visual tree. /// protected override Visual GetVisualChild(int index) { //_children cannot be null as its initialized in the constructor // index range check done by VisualCollection return _children[index]; } ////// Returns enumerator to logical children. /// protected internal override IEnumerator LogicalChildren { get { if ((this.VisualChildrenCount == 0)) { return EmptyEnumerator.Instance; } return _children.GetEnumerator(); } } ////// AdornerLayer always returns a size of (0,0). /// The AdornerLayer's size should be the same as its parent, but not take up layout space. This means /// parents containing an AdornerLayer should stretch it to their own size. /// /// /// Sizing constraint. /// protected override Size MeasureOverride(Size constraint) { // Not using an enumerator because the list can be modified during the loop when we call out. DictionaryEntry[] zOrderMapEntries = new DictionaryEntry[_zOrderMap.Count]; _zOrderMap.CopyTo(zOrderMapEntries, 0); for (int i = 0; i < zOrderMapEntries.Length; i++) { ArrayList adornerInfos = (ArrayList)zOrderMapEntries[i].Value; Debug.Assert(adornerInfos != null, "No adorners found for element in AdornerLayer._zOrderMap"); int j = 0; while (j < adornerInfos.Count) { AdornerInfo adornerInfo = (AdornerInfo)adornerInfos[j++]; adornerInfo.Adorner.Measure(constraint); } } // Returning 0,0 prevents an invalidation of Measure for AdornerLayer from unnecessarily dirtying the parent. return new Size(); } ////// Override for ////// /// We need information from AdornerInfo. Since we keep one AdornerInfo per /// Adorner, and we expect a 1:1 mapping between Adorners and our visual children, /// it makes more sense for us to iterate across AdornerInfos instead of /// our visual children here. This means that if someone somehow adds a non-Adorner /// child to AdornerLayer, it will never render. /// /// The location reserved for this element by the parent protected override Size ArrangeOverride(Size finalSize) { // Not using an enumerator because the list can be modified during the loop when we call out. DictionaryEntry[] zOrderMapEntries = new DictionaryEntry[_zOrderMap.Count]; _zOrderMap.CopyTo(zOrderMapEntries, 0); for (int i = 0; i < zOrderMapEntries.Length; i++) { ArrayList adornerInfos = (ArrayList)zOrderMapEntries[i].Value; Debug.Assert(adornerInfos != null, "No adorners found for element in AdornerLayer._zOrderMap"); int j = 0; while (j < adornerInfos.Count) { AdornerInfo adornerInfo = (AdornerInfo)adornerInfos[j++]; if (!adornerInfo.Adorner.IsArrangeValid) // optimization { // We're dependent on Arrange to get the rendersize of the adorner, so Arrange before // doing our transform magic. adornerInfo.Adorner.Arrange(new Rect(new Point(), adornerInfo.Adorner.DesiredSize)); GeneralTransform proposedTransform = adornerInfo.Adorner.GetDesiredTransform(adornerInfo.Transform); GeneralTransform adornerTransform = GetProposedTransform(adornerInfo.Adorner, proposedTransform); int index = _children.IndexOf(adornerInfo.Adorner); if (index >= 0) { // Get the matrix transform out, skip all non affine transforms Transform transform = (adornerTransform != null) ? adornerTransform.AffineTransform : null; ((Adorner)(_children[index])).AdornerTransform = transform; } } if (adornerInfo.Adorner.IsClipEnabled) { adornerInfo.Adorner.AdornerClip = adornerInfo.Clip; } else if (adornerInfo.Adorner.AdornerClip != null) { adornerInfo.Adorner.AdornerClip = null; } } } return finalSize; } #endregion Protected Methods //----------------------------------------------------- // // Internal Methods // //------------------------------------------------------ #region Internal Methods ////// Add given Adorner to our children /// /// Adorner to add /// z-order internal void Add(Adorner adorner, int zOrder) { if (adorner == null) throw new ArgumentNullException("adorner"); AdornerInfo adornerInfo = new AdornerInfo(adorner); adornerInfo.ZOrder = zOrder; AddAdornerInfo(ElementMap, adornerInfo, adorner.AdornedElement); AddAdornerToVisualTree(adornerInfo, zOrder); AddLogicalChild(adorner); UpdateAdorner(adorner.AdornedElement); } ////// Clean all the dynamically-updated data from the Adorner /// /// AdornerInfo to scrub internal void InvalidateAdorner(AdornerInfo adornerInfo) { Debug.Assert(adornerInfo != null, "Adorner should not be null"); adornerInfo.Adorner.InvalidateMeasure(); adornerInfo.Adorner.InvalidateVisual(); adornerInfo.RenderSize = new Size(Double.NaN, Double.NaN); adornerInfo.Transform = null; } ////// OnLayoutUpdated event handler /// /// /// internal void OnLayoutUpdated(object sender, EventArgs args) { if (ElementMap.Count == 0) return; UpdateAdorner(null); } ////// Set the zOrder on the given adorner. /// /// /// internal void SetAdornerZOrder(Adorner adorner, int zOrder) { ArrayList adornerInfos = ElementMap[adorner.AdornedElement] as ArrayList; if (adornerInfos == null) { throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); } AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo == null) { throw new InvalidOperationException(SR.Get(SRID.AdornerNotFound)); } RemoveAdornerInfo(_zOrderMap, adorner, adornerInfo.ZOrder); _children.Remove(adorner); adornerInfo.ZOrder = zOrder; AddAdornerToVisualTree(adornerInfo, zOrder); InvalidateAdorner(adornerInfo); UpdateAdorner(adorner.AdornedElement); } ////// Query the zOrder on the given adorner. /// /// ///zOrder of given adorner internal int GetAdornerZOrder(Adorner adorner) { ArrayList adornerInfos = ElementMap[adorner.AdornedElement] as ArrayList; if (adornerInfos == null) { throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); } AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo == null) { throw new InvalidOperationException(SR.Get(SRID.AdornerNotFound)); } return adornerInfo.ZOrder; } #endregion Internal methods //----------------------------------------------------- // // Internal Properties // //------------------------------------------------------ #region Internal Properties internal HybridDictionary ElementMap { get { return this._elementMap; } } #endregion Internal Properties //------------------------------------------------------ // // Internal Events // //----------------------------------------------------- //------------------------------------------------------ // // Private Methods // //----------------------------------------------------- #region Private Methods ////// Adds the given adorner to the visual tree in the proper zOrder order. /// /// /// private void AddAdornerToVisualTree(AdornerInfo adornerInfo, int zOrder) { Adorner adorner = adornerInfo.Adorner; Debug.Assert(adorner != null); AddAdornerInfo(_zOrderMap, adornerInfo, zOrder); // We've already added the adorner to the zOrderMap, so we can't get null back ArrayList adornerInfos = (ArrayList)_zOrderMap[zOrder]; if (adornerInfos.Count > 1) { // The easy case. Find the index of the adorner immediately in front of the // new one and insert the new one after it. int index = adornerInfos.IndexOf(adornerInfo); int insertionIndex = _children.IndexOf(((AdornerInfo)adornerInfos[index - 1]).Adorner) + 1; _children.Insert(insertionIndex, adorner); } else { // The hard case. Find the set of adorners with the closest, but lower, zOrder. IList keys = _zOrderMap.GetKeyList(); int index = keys.IndexOf(zOrder) - 1; if (index < 0) { // nothing's lower than the new adorner. Make it the first child. _children.Insert(0, adorner); } else { // find the last adorner at this zOrder and add the new one after it. adornerInfos = (ArrayList)_zOrderMap[keys[index]]; int insertionIndex = _children.IndexOf(((AdornerInfo)adornerInfos[adornerInfos.Count - 1]).Adorner) + 1; _children.Insert(insertionIndex, adorner); } } } ////// Remove all adorners for the given element /// /// element key for removal private void Clear(UIElement element) { if (element == null) throw new ArgumentNullException("element"); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null) throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); while (adornerInfos.Count > 0) { AdornerInfo info = adornerInfos[0] as AdornerInfo; Remove(info.Adorner); } ElementMap.Remove(element); } ////// Update the Adorners for the given element /// /// UIElement for which we're updating AdornerSet private void UpdateElementAdorners(UIElement element) { Size size; // we intentionally do not ascend in to a 3D scene Visual adornerLayerParent = VisualTreeHelper.GetParent(this) as Visual; if (adornerLayerParent == null) { return; } Debug.Assert(element != null); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null) { return; } bool dirty = false; // // See if the adorners need to be rerendered due to object resizing // GeneralTransform transform = element.TransformToAncestor(adornerLayerParent); for (int i = 0; i < adornerInfos.Count; i++) { AdornerInfo adornerInfo = (AdornerInfo)adornerInfos[i]; size = element.RenderSize; Geometry clip = null; bool clipChanged = false; if (adornerInfo.Adorner.IsClipEnabled) { clip = GetClipGeometry(adornerInfo.Adorner.AdornedElement, adornerInfo.Adorner); if (adornerInfo.Clip == null && clip != null || adornerInfo.Clip != null && clip == null || (adornerInfo.Clip != null && clip != null && adornerInfo.Clip.Bounds != clip.Bounds)) { clipChanged = true; } } if (adornerInfo.Adorner.NeedsUpdate(adornerInfo.RenderSize) || adornerInfo.Transform == null || transform.AffineTransform == null || adornerInfo.Transform.AffineTransform == null || transform.AffineTransform.Value != adornerInfo.Transform.AffineTransform.Value || clipChanged) { InvalidateAdorner(adornerInfo); adornerInfo.RenderSize = size; adornerInfo.Transform = transform; if (adornerInfo.Adorner.IsClipEnabled) { adornerInfo.Clip = clip; } dirty = true; } } if (dirty) InvalidateMeasure(); } ////// Update the Adorner for the given element /// /// UIElement for which we're updating AdornerSet private void UpdateAdorner(UIElement element) { Visual adornerLayerParent = VisualTreeHelper.GetParent(this) as Visual; if (adornerLayerParent == null) { // Never update when the adorner layer is not part of a visual tree. return; } // We only expect one to have been removed on any one call. ArrayList removeList = new ArrayList(1); if (element != null) { // Make sure element is still beneath the adorner decorator if (!element.IsDescendantOf(adornerLayerParent)) { removeList.Add(element); } else { UpdateElementAdorners(element); } } else { ICollection keyCollection = ElementMap.Keys; UIElement[] keys = new UIElement[keyCollection.Count]; keyCollection.CopyTo(keys, 0); // make a static copy of the keys to prevent any possible enumerator exceptions for (int i = 0; i < keys.Length; i++) { UIElement elTemp = (UIElement)keys[i]; // Make sure element is still beneath the adorner decorator if (!elTemp.IsDescendantOf(adornerLayerParent)) { removeList.Add(elTemp); } else { UpdateElementAdorners(elTemp); } } } for (int i = 0; i < removeList.Count; i++) { Clear((UIElement)removeList[i]); } } ////// Walk up the tree from the adorned element to the AdornerLayer's parent, accumulating /// clip geometries as we go. Called when IsClipEnabled == true to allow an adorner /// to be clipped (which normally, it isn't). /// private CombinedGeometry GetClipGeometry(Visual element, Adorner adorner) { Visual oldElement = null; // we intentionally do not ascend in to a 3D scene Visual adornerLayerParent = VisualTreeHelper.GetParent(this) as Visual; if (adornerLayerParent == null) { return null; } CombinedGeometry combinedGeometry = null; // If the element has been removed from the tree and we've not yet had a chance // to remove the adorner, there's obviously no clipping if (!adornerLayerParent.IsAncestorOf(element)) { return null; } while (element != adornerLayerParent && element != null) { Geometry geometry = VisualTreeHelper.GetClip(element); if (geometry != null) { if (combinedGeometry == null) { combinedGeometry = new CombinedGeometry(geometry, null); } else { GeneralTransform transform = oldElement.TransformToAncestor(element); combinedGeometry.Transform = transform.AffineTransform; combinedGeometry = new CombinedGeometry(combinedGeometry, geometry); combinedGeometry.GeometryCombineMode = GeometryCombineMode.Intersect; } oldElement = element; } // we intentionally separate adorners from spanning 3D boundaries // and if the parent is ever 3D there was a mistake element = (Visual)VisualTreeHelper.GetParent(element); } if (combinedGeometry != null) { // transform the last combined geometry up to the top GeneralTransform transform = oldElement.TransformToAncestor(adornerLayerParent); if (transform == null) { combinedGeometry = null; } else { TransformGroup transformGroup = new TransformGroup(); transformGroup.Children.Add(transform.AffineTransform); // Now transform back down to the adorner transform = adornerLayerParent.TransformToDescendant(adorner); if (transform == null) { combinedGeometry = null; } else { transformGroup.Children.Add(transform.AffineTransform); combinedGeometry.Transform = transformGroup; } } } return combinedGeometry; } ////// Remove the given adorner's AdornerInfo from the given AdornerInfo list. /// /// dictionary of adornerInfo /// adorner /// key ///true if info was found and removed private bool RemoveAdornerInfo(IDictionary infoMap, Adorner adorner, object key) { ArrayList adornerInfos = infoMap[key] as ArrayList; if (adornerInfos != null) { AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo != null) { adornerInfos.Remove(adornerInfo); if (adornerInfos.Count == 0) { infoMap.Remove(key); } return true; } } return false; } private AdornerInfo GetAdornerInfo(ArrayList adornerInfos, Adorner adorner) { if (adornerInfos != null) { int i = 0; while (i < adornerInfos.Count) { if (((AdornerInfo)adornerInfos[i]).Adorner == adorner) { return (AdornerInfo)adornerInfos[i]; } i++; } } return null; } private void AddAdornerInfo(IDictionary infoMap, AdornerInfo adornerInfo, object key) { ArrayList adornerInfos; if (infoMap[key] == null) { adornerInfos = new ArrayList(1); infoMap[key] = adornerInfos; } else { adornerInfos = (ArrayList)infoMap[key]; } adornerInfos.Add(adornerInfo); } // // This property // 1. Finds the correct initial size for the _effectiveValues store on the current DependencyObject // 2. This is a performance optimization // internal override int EffectiveValuesInitialSize { get { return 4; } } GeneralTransform GetProposedTransform(Adorner adorner, GeneralTransform sourceTransform) { // Flip horizontally if Right to Left. if (adorner.FlowDirection != this.FlowDirection) { GeneralTransformGroup group; MatrixTransform matrixTransform; Matrix matrix; group = new GeneralTransformGroup(); matrix = new Matrix(-1.0, 0.0, 0.0, 1.0, adorner.RenderSize.Width, 0.0); matrixTransform = new MatrixTransform(matrix); group.Children.Add(matrixTransform); if (sourceTransform != null && sourceTransform != Transform.Identity) { group.Children.Add(sourceTransform); } return group; } return sourceTransform; } #endregion Private methods //----------------------------------------------------- // // Private Properties // //----------------------------------------------------- //------------------------------------------------------ // // Private Fields // //----------------------------------------------------- #region Private Fields private HybridDictionary _elementMap = new HybridDictionary(10); private SortedList _zOrderMap = new SortedList(10); private const int DefaultZOrder = System.Int32.MaxValue; private VisualCollection _children; #endregion Private Fields } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved. //---------------------------------------------------------------------------- // //// Copyright (C) Microsoft Corporation. All rights reserved. // // // // Description: // // See spec at: http://avalon/uis/Specs/AdornerLayer%20Spec.htm // // History: // 9/20/2002 susia: Created (DecoratorContainer) // 6/11/2003 psarrett: Ported to WCP tree; merged DecoratorContainer and // AdornerContainerPresenter into AdornerLayer // 10/22/2003 psarrett: Updated as per current spec // //--------------------------------------------------------------------------- using System; using System.Windows.Media; using System.Diagnostics; using System.Collections; using System.Collections.Specialized; using System.Windows.Threading; using System.Windows.Controls; using MS.Utility; using MS.Internal; using MS.Internal.Controls; using MS.Internal.Media; using Microsoft.Internal.AlphaFlattener; // TransformGeometry() namespace System.Windows.Documents { ////// Visual decoration including but not limited to adornments, rubberband selection and /// non-live move feedback. /// /// AdornerLayer expects to be parented by an AdornerDecorator. /// public class AdornerLayer : FrameworkElement { ////// Adorner information /// internal class AdornerInfo { ////// Constructor /// internal AdornerInfo(Adorner adorner) { Invariant.Assert(adorner != null); _adorner = adorner; } ////// Adorner /// internal Adorner Adorner { get { return _adorner; } } ////// The RenderSize (bounding box) of the object we're adorning /// internal Size RenderSize { get { return _computedSize; } set { _computedSize = value; } } ////// Transform on the Visual /// internal GeneralTransform Transform { get { return _transform; } set { _transform = value; } } internal int ZOrder { get { return _zOrder; } set { _zOrder = value; } } internal Geometry Clip { get { return _clip; } set { _clip = value; } } private Adorner _adorner; private Size _computedSize; private GeneralTransform _transform; private int _zOrder; private Geometry _clip; } //----------------------------------------------------- // // Constructors // //----------------------------------------------------- #region Constructors ////// Constructor /// ////// Note that because we're setting up an event handler here, we won't be GC'd until /// our parent is GC'd. So the implicit assumption is that the AdornerLayer, once /// created, exists until its parent is deleted. /// internal AdornerLayer() : this(Dispatcher.CurrentDispatcher) { } ////// Constructor /// /// Dispatcher ////// Note that because we're setting up an event handler here, we won't be GC'd until /// our parent is GC'd. So the implicit assumption is that the AdornerLayer, once /// created, exists until its parent is deleted. /// internal AdornerLayer(Dispatcher context) { if (context == null) throw new ArgumentNullException("context"); LayoutUpdated += new EventHandler(OnLayoutUpdated); _children = new VisualCollection(this); } #endregion Constructors //------------------------------------------------------ // // Public Methods // //----------------------------------------------------- #region Public Methods ////// Add given Adorner to our children /// /// Adorner to add public void Add(Adorner adorner) { Add(adorner, DefaultZOrder); } ////// Remove given adorner. This method will not complain if the given adorner is not /// in the AdornerLayer. /// /// adorner to remove public void Remove(Adorner adorner) { if (adorner == null) throw new ArgumentNullException("adorner"); ArrayList adornerInfos = ElementMap[adorner.AdornedElement] as ArrayList; if (adornerInfos == null) { // We currently allow adorners to be added on elements that can't be adorned, then // throw those away later without notifying anyone. Consequently, Remove() shouldn't throw. return; } AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo == null) { // We currently allow adorners to be added on elements that can't be adorned, then // throw those away later without notifying anyone. Consequently, Remove() shouldn't throw. return; } RemoveAdornerInfo(ElementMap, adorner, adorner.AdornedElement); RemoveAdornerInfo(_zOrderMap, adorner, adornerInfo.ZOrder); _children.Remove(adorner); RemoveLogicalChild(adorner); } ////// Update (layout and render) all adorners. /// public void Update() { foreach (UIElement key in ElementMap.Keys) { ArrayList adornerInfos = (ArrayList)ElementMap[key]; int i = 0; if (adornerInfos != null) { while (i < adornerInfos.Count) { InvalidateAdorner((AdornerInfo)adornerInfos[i++]); } } } UpdateAdorner(null); } ////// Update (layout and render) all adorners for the given element. /// /// element key for redraw public void Update(UIElement element) { if (element == null) throw new ArgumentNullException("element"); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null) throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); int i = 0; while (i < adornerInfos.Count) { InvalidateAdorner((AdornerInfo)adornerInfos[i++]); } UpdateAdorner(element); } ////// Return a collection of all adorners adorning the given element /// /// Element for which adorners are to be retrieved ///array of adorners on given element, or null if /// no adorners exist public Adorner[] GetAdorners(UIElement element) { if (element == null) throw new ArgumentNullException("element"); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null || adornerInfos.Count == 0) return null; Adorner[] adorners = new Adorner[adornerInfos.Count]; for (int i = 0; i < adornerInfos.Count; i++) adorners[i] = ((AdornerInfo)adornerInfos[i]).Adorner; return adorners; } ////// Determine if the given point is on an adorner. /// /// point to test ///AdornerHitTestResult containing the hit visual and the adorner that visual /// is part of. If the no adorner was hit, null is returned public AdornerHitTestResult AdornerHitTest(Point point) { PointHitTestResult result = VisualTreeUtils.AsNearestPointHitTestResult(VisualTreeHelper.HitTest(this, point, false)); if (result != null && result.VisualHit != null) { Visual visual = result.VisualHit; while (visual != this) { if (visual is Adorner) return new AdornerHitTestResult(result.VisualHit, result.PointHit, visual as Adorner); // we intentionally separate adorners from spanning 3D boundaries // and if the parent is ever 3D there was a mistake visual = (Visual)VisualTreeHelper.GetParent(visual); } return null; } else { return null; } } ////// Walk up the visual tree to find the nearest AdornerLayer. /// /// Visual from which the treewalk begins ///First AdornerLayer above given element, or null static public AdornerLayer GetAdornerLayer(Visual visual) { if (visual == null) throw new ArgumentNullException("visual"); Visual parent = VisualTreeHelper.GetParent(visual) as Visual; while (parent != null) { if (parent is AdornerDecorator) return ((AdornerDecorator)parent).AdornerLayer; if (parent is ScrollContentPresenter) return ((ScrollContentPresenter)parent).AdornerLayer; parent = VisualTreeHelper.GetParent(parent) as Visual; } return null; } #endregion Public Methods //------------------------------------------------------ // // Public Properties // //------------------------------------------------------ #region Public Properties #endregion Public Properties //----------------------------------------------------- // // Public Events // //------------------------------------------------------ //----------------------------------------------------- // // Protected Methods // //----------------------------------------------------- #region Protected Methods ////// Derived classes override this property to enable the Visual code to enumerate /// the Visual children. Derived classes need to return the number of children /// from this method. /// /// By default a Visual does not have any children. /// /// Remark: /// During this virtual method the Visual tree must not be modified. /// protected override int VisualChildrenCount { get { //_children cannot be null as its initialized in the constructor return _children.Count; } } ////// Derived class must implement to support Visual children. The method must return /// the child at the specified index. Index must be between 0 and GetVisualChildrenCount-1. /// /// By default a Visual does not have any children. /// /// Remark: /// During this virtual call it is not valid to modify the Visual tree. /// protected override Visual GetVisualChild(int index) { //_children cannot be null as its initialized in the constructor // index range check done by VisualCollection return _children[index]; } ////// Returns enumerator to logical children. /// protected internal override IEnumerator LogicalChildren { get { if ((this.VisualChildrenCount == 0)) { return EmptyEnumerator.Instance; } return _children.GetEnumerator(); } } ////// AdornerLayer always returns a size of (0,0). /// The AdornerLayer's size should be the same as its parent, but not take up layout space. This means /// parents containing an AdornerLayer should stretch it to their own size. /// /// /// Sizing constraint. /// protected override Size MeasureOverride(Size constraint) { // Not using an enumerator because the list can be modified during the loop when we call out. DictionaryEntry[] zOrderMapEntries = new DictionaryEntry[_zOrderMap.Count]; _zOrderMap.CopyTo(zOrderMapEntries, 0); for (int i = 0; i < zOrderMapEntries.Length; i++) { ArrayList adornerInfos = (ArrayList)zOrderMapEntries[i].Value; Debug.Assert(adornerInfos != null, "No adorners found for element in AdornerLayer._zOrderMap"); int j = 0; while (j < adornerInfos.Count) { AdornerInfo adornerInfo = (AdornerInfo)adornerInfos[j++]; adornerInfo.Adorner.Measure(constraint); } } // Returning 0,0 prevents an invalidation of Measure for AdornerLayer from unnecessarily dirtying the parent. return new Size(); } ////// Override for ////// /// We need information from AdornerInfo. Since we keep one AdornerInfo per /// Adorner, and we expect a 1:1 mapping between Adorners and our visual children, /// it makes more sense for us to iterate across AdornerInfos instead of /// our visual children here. This means that if someone somehow adds a non-Adorner /// child to AdornerLayer, it will never render. /// /// The location reserved for this element by the parent protected override Size ArrangeOverride(Size finalSize) { // Not using an enumerator because the list can be modified during the loop when we call out. DictionaryEntry[] zOrderMapEntries = new DictionaryEntry[_zOrderMap.Count]; _zOrderMap.CopyTo(zOrderMapEntries, 0); for (int i = 0; i < zOrderMapEntries.Length; i++) { ArrayList adornerInfos = (ArrayList)zOrderMapEntries[i].Value; Debug.Assert(adornerInfos != null, "No adorners found for element in AdornerLayer._zOrderMap"); int j = 0; while (j < adornerInfos.Count) { AdornerInfo adornerInfo = (AdornerInfo)adornerInfos[j++]; if (!adornerInfo.Adorner.IsArrangeValid) // optimization { // We're dependent on Arrange to get the rendersize of the adorner, so Arrange before // doing our transform magic. adornerInfo.Adorner.Arrange(new Rect(new Point(), adornerInfo.Adorner.DesiredSize)); GeneralTransform proposedTransform = adornerInfo.Adorner.GetDesiredTransform(adornerInfo.Transform); GeneralTransform adornerTransform = GetProposedTransform(adornerInfo.Adorner, proposedTransform); int index = _children.IndexOf(adornerInfo.Adorner); if (index >= 0) { // Get the matrix transform out, skip all non affine transforms Transform transform = (adornerTransform != null) ? adornerTransform.AffineTransform : null; ((Adorner)(_children[index])).AdornerTransform = transform; } } if (adornerInfo.Adorner.IsClipEnabled) { adornerInfo.Adorner.AdornerClip = adornerInfo.Clip; } else if (adornerInfo.Adorner.AdornerClip != null) { adornerInfo.Adorner.AdornerClip = null; } } } return finalSize; } #endregion Protected Methods //----------------------------------------------------- // // Internal Methods // //------------------------------------------------------ #region Internal Methods ////// Add given Adorner to our children /// /// Adorner to add /// z-order internal void Add(Adorner adorner, int zOrder) { if (adorner == null) throw new ArgumentNullException("adorner"); AdornerInfo adornerInfo = new AdornerInfo(adorner); adornerInfo.ZOrder = zOrder; AddAdornerInfo(ElementMap, adornerInfo, adorner.AdornedElement); AddAdornerToVisualTree(adornerInfo, zOrder); AddLogicalChild(adorner); UpdateAdorner(adorner.AdornedElement); } ////// Clean all the dynamically-updated data from the Adorner /// /// AdornerInfo to scrub internal void InvalidateAdorner(AdornerInfo adornerInfo) { Debug.Assert(adornerInfo != null, "Adorner should not be null"); adornerInfo.Adorner.InvalidateMeasure(); adornerInfo.Adorner.InvalidateVisual(); adornerInfo.RenderSize = new Size(Double.NaN, Double.NaN); adornerInfo.Transform = null; } ////// OnLayoutUpdated event handler /// /// /// internal void OnLayoutUpdated(object sender, EventArgs args) { if (ElementMap.Count == 0) return; UpdateAdorner(null); } ////// Set the zOrder on the given adorner. /// /// /// internal void SetAdornerZOrder(Adorner adorner, int zOrder) { ArrayList adornerInfos = ElementMap[adorner.AdornedElement] as ArrayList; if (adornerInfos == null) { throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); } AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo == null) { throw new InvalidOperationException(SR.Get(SRID.AdornerNotFound)); } RemoveAdornerInfo(_zOrderMap, adorner, adornerInfo.ZOrder); _children.Remove(adorner); adornerInfo.ZOrder = zOrder; AddAdornerToVisualTree(adornerInfo, zOrder); InvalidateAdorner(adornerInfo); UpdateAdorner(adorner.AdornedElement); } ////// Query the zOrder on the given adorner. /// /// ///zOrder of given adorner internal int GetAdornerZOrder(Adorner adorner) { ArrayList adornerInfos = ElementMap[adorner.AdornedElement] as ArrayList; if (adornerInfos == null) { throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); } AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo == null) { throw new InvalidOperationException(SR.Get(SRID.AdornerNotFound)); } return adornerInfo.ZOrder; } #endregion Internal methods //----------------------------------------------------- // // Internal Properties // //------------------------------------------------------ #region Internal Properties internal HybridDictionary ElementMap { get { return this._elementMap; } } #endregion Internal Properties //------------------------------------------------------ // // Internal Events // //----------------------------------------------------- //------------------------------------------------------ // // Private Methods // //----------------------------------------------------- #region Private Methods ////// Adds the given adorner to the visual tree in the proper zOrder order. /// /// /// private void AddAdornerToVisualTree(AdornerInfo adornerInfo, int zOrder) { Adorner adorner = adornerInfo.Adorner; Debug.Assert(adorner != null); AddAdornerInfo(_zOrderMap, adornerInfo, zOrder); // We've already added the adorner to the zOrderMap, so we can't get null back ArrayList adornerInfos = (ArrayList)_zOrderMap[zOrder]; if (adornerInfos.Count > 1) { // The easy case. Find the index of the adorner immediately in front of the // new one and insert the new one after it. int index = adornerInfos.IndexOf(adornerInfo); int insertionIndex = _children.IndexOf(((AdornerInfo)adornerInfos[index - 1]).Adorner) + 1; _children.Insert(insertionIndex, adorner); } else { // The hard case. Find the set of adorners with the closest, but lower, zOrder. IList keys = _zOrderMap.GetKeyList(); int index = keys.IndexOf(zOrder) - 1; if (index < 0) { // nothing's lower than the new adorner. Make it the first child. _children.Insert(0, adorner); } else { // find the last adorner at this zOrder and add the new one after it. adornerInfos = (ArrayList)_zOrderMap[keys[index]]; int insertionIndex = _children.IndexOf(((AdornerInfo)adornerInfos[adornerInfos.Count - 1]).Adorner) + 1; _children.Insert(insertionIndex, adorner); } } } ////// Remove all adorners for the given element /// /// element key for removal private void Clear(UIElement element) { if (element == null) throw new ArgumentNullException("element"); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null) throw new InvalidOperationException(SR.Get(SRID.AdornedElementNotFound)); while (adornerInfos.Count > 0) { AdornerInfo info = adornerInfos[0] as AdornerInfo; Remove(info.Adorner); } ElementMap.Remove(element); } ////// Update the Adorners for the given element /// /// UIElement for which we're updating AdornerSet private void UpdateElementAdorners(UIElement element) { Size size; // we intentionally do not ascend in to a 3D scene Visual adornerLayerParent = VisualTreeHelper.GetParent(this) as Visual; if (adornerLayerParent == null) { return; } Debug.Assert(element != null); ArrayList adornerInfos = ElementMap[element] as ArrayList; if (adornerInfos == null) { return; } bool dirty = false; // // See if the adorners need to be rerendered due to object resizing // GeneralTransform transform = element.TransformToAncestor(adornerLayerParent); for (int i = 0; i < adornerInfos.Count; i++) { AdornerInfo adornerInfo = (AdornerInfo)adornerInfos[i]; size = element.RenderSize; Geometry clip = null; bool clipChanged = false; if (adornerInfo.Adorner.IsClipEnabled) { clip = GetClipGeometry(adornerInfo.Adorner.AdornedElement, adornerInfo.Adorner); if (adornerInfo.Clip == null && clip != null || adornerInfo.Clip != null && clip == null || (adornerInfo.Clip != null && clip != null && adornerInfo.Clip.Bounds != clip.Bounds)) { clipChanged = true; } } if (adornerInfo.Adorner.NeedsUpdate(adornerInfo.RenderSize) || adornerInfo.Transform == null || transform.AffineTransform == null || adornerInfo.Transform.AffineTransform == null || transform.AffineTransform.Value != adornerInfo.Transform.AffineTransform.Value || clipChanged) { InvalidateAdorner(adornerInfo); adornerInfo.RenderSize = size; adornerInfo.Transform = transform; if (adornerInfo.Adorner.IsClipEnabled) { adornerInfo.Clip = clip; } dirty = true; } } if (dirty) InvalidateMeasure(); } ////// Update the Adorner for the given element /// /// UIElement for which we're updating AdornerSet private void UpdateAdorner(UIElement element) { Visual adornerLayerParent = VisualTreeHelper.GetParent(this) as Visual; if (adornerLayerParent == null) { // Never update when the adorner layer is not part of a visual tree. return; } // We only expect one to have been removed on any one call. ArrayList removeList = new ArrayList(1); if (element != null) { // Make sure element is still beneath the adorner decorator if (!element.IsDescendantOf(adornerLayerParent)) { removeList.Add(element); } else { UpdateElementAdorners(element); } } else { ICollection keyCollection = ElementMap.Keys; UIElement[] keys = new UIElement[keyCollection.Count]; keyCollection.CopyTo(keys, 0); // make a static copy of the keys to prevent any possible enumerator exceptions for (int i = 0; i < keys.Length; i++) { UIElement elTemp = (UIElement)keys[i]; // Make sure element is still beneath the adorner decorator if (!elTemp.IsDescendantOf(adornerLayerParent)) { removeList.Add(elTemp); } else { UpdateElementAdorners(elTemp); } } } for (int i = 0; i < removeList.Count; i++) { Clear((UIElement)removeList[i]); } } ////// Walk up the tree from the adorned element to the AdornerLayer's parent, accumulating /// clip geometries as we go. Called when IsClipEnabled == true to allow an adorner /// to be clipped (which normally, it isn't). /// private CombinedGeometry GetClipGeometry(Visual element, Adorner adorner) { Visual oldElement = null; // we intentionally do not ascend in to a 3D scene Visual adornerLayerParent = VisualTreeHelper.GetParent(this) as Visual; if (adornerLayerParent == null) { return null; } CombinedGeometry combinedGeometry = null; // If the element has been removed from the tree and we've not yet had a chance // to remove the adorner, there's obviously no clipping if (!adornerLayerParent.IsAncestorOf(element)) { return null; } while (element != adornerLayerParent && element != null) { Geometry geometry = VisualTreeHelper.GetClip(element); if (geometry != null) { if (combinedGeometry == null) { combinedGeometry = new CombinedGeometry(geometry, null); } else { GeneralTransform transform = oldElement.TransformToAncestor(element); combinedGeometry.Transform = transform.AffineTransform; combinedGeometry = new CombinedGeometry(combinedGeometry, geometry); combinedGeometry.GeometryCombineMode = GeometryCombineMode.Intersect; } oldElement = element; } // we intentionally separate adorners from spanning 3D boundaries // and if the parent is ever 3D there was a mistake element = (Visual)VisualTreeHelper.GetParent(element); } if (combinedGeometry != null) { // transform the last combined geometry up to the top GeneralTransform transform = oldElement.TransformToAncestor(adornerLayerParent); if (transform == null) { combinedGeometry = null; } else { TransformGroup transformGroup = new TransformGroup(); transformGroup.Children.Add(transform.AffineTransform); // Now transform back down to the adorner transform = adornerLayerParent.TransformToDescendant(adorner); if (transform == null) { combinedGeometry = null; } else { transformGroup.Children.Add(transform.AffineTransform); combinedGeometry.Transform = transformGroup; } } } return combinedGeometry; } ////// Remove the given adorner's AdornerInfo from the given AdornerInfo list. /// /// dictionary of adornerInfo /// adorner /// key ///true if info was found and removed private bool RemoveAdornerInfo(IDictionary infoMap, Adorner adorner, object key) { ArrayList adornerInfos = infoMap[key] as ArrayList; if (adornerInfos != null) { AdornerInfo adornerInfo = GetAdornerInfo(adornerInfos, adorner); if (adornerInfo != null) { adornerInfos.Remove(adornerInfo); if (adornerInfos.Count == 0) { infoMap.Remove(key); } return true; } } return false; } private AdornerInfo GetAdornerInfo(ArrayList adornerInfos, Adorner adorner) { if (adornerInfos != null) { int i = 0; while (i < adornerInfos.Count) { if (((AdornerInfo)adornerInfos[i]).Adorner == adorner) { return (AdornerInfo)adornerInfos[i]; } i++; } } return null; } private void AddAdornerInfo(IDictionary infoMap, AdornerInfo adornerInfo, object key) { ArrayList adornerInfos; if (infoMap[key] == null) { adornerInfos = new ArrayList(1); infoMap[key] = adornerInfos; } else { adornerInfos = (ArrayList)infoMap[key]; } adornerInfos.Add(adornerInfo); } // // This property // 1. Finds the correct initial size for the _effectiveValues store on the current DependencyObject // 2. This is a performance optimization // internal override int EffectiveValuesInitialSize { get { return 4; } } GeneralTransform GetProposedTransform(Adorner adorner, GeneralTransform sourceTransform) { // Flip horizontally if Right to Left. if (adorner.FlowDirection != this.FlowDirection) { GeneralTransformGroup group; MatrixTransform matrixTransform; Matrix matrix; group = new GeneralTransformGroup(); matrix = new Matrix(-1.0, 0.0, 0.0, 1.0, adorner.RenderSize.Width, 0.0); matrixTransform = new MatrixTransform(matrix); group.Children.Add(matrixTransform); if (sourceTransform != null && sourceTransform != Transform.Identity) { group.Children.Add(sourceTransform); } return group; } return sourceTransform; } #endregion Private methods //----------------------------------------------------- // // Private Properties // //----------------------------------------------------- //------------------------------------------------------ // // Private Fields // //----------------------------------------------------- #region Private Fields private HybridDictionary _elementMap = new HybridDictionary(10); private SortedList _zOrderMap = new SortedList(10); private const int DefaultZOrder = System.Int32.MaxValue; private VisualCollection _children; #endregion Private Fields } } // 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
- PriorityChain.cs
- DataColumnChangeEvent.cs
- BitmapEncoder.cs
- XmlChoiceIdentifierAttribute.cs
- RegisteredDisposeScript.cs
- MessageHeaderDescriptionCollection.cs
- ZeroOpNode.cs
- SHA384.cs
- IIS7WorkerRequest.cs
- BufferedWebEventProvider.cs
- ControlCachePolicy.cs
- ConnectionStringsSection.cs
- XmlChoiceIdentifierAttribute.cs
- KeyFrames.cs
- XPathNavigatorKeyComparer.cs
- SchemaImporter.cs
- CredentialCache.cs
- TerminatorSinks.cs
- DBConnection.cs
- GcSettings.cs
- SByte.cs
- AVElementHelper.cs
- MenuBindingsEditorForm.cs
- SourceItem.cs
- EdmValidator.cs
- IgnoreSectionHandler.cs
- XPathItem.cs
- EnumerableRowCollection.cs
- keycontainerpermission.cs
- TitleStyle.cs
- XPathNodeIterator.cs
- SafeNativeMethods.cs
- DataTableTypeConverter.cs
- Int32RectConverter.cs
- RawStylusActions.cs
- TaskFactory.cs
- SocketManager.cs
- HtmlEncodedRawTextWriter.cs
- ObjectMemberMapping.cs
- MembershipSection.cs
- DbProviderManifest.cs
- AttributeAction.cs
- BinaryUtilClasses.cs
- PageThemeParser.cs
- DynamicField.cs
- JavaScriptSerializer.cs
- BinaryFormatterWriter.cs
- validationstate.cs
- UserUseLicenseDictionaryLoader.cs
- Compiler.cs
- SmtpClient.cs
- CollectionBuilder.cs
- PropertyInformation.cs
- validationstate.cs
- Timeline.cs
- _SslStream.cs
- filewebresponse.cs
- LoginView.cs
- Activator.cs
- BufferBuilder.cs
- WindowsUserNameSecurityTokenAuthenticator.cs
- Matrix.cs
- OneOfElement.cs
- SessionIDManager.cs
- UIAgentRequest.cs
- DesignerDataView.cs
- CatalogPartCollection.cs
- BookmarkResumptionRecord.cs
- PersonalizableAttribute.cs
- _ConnectStream.cs
- XPathPatternParser.cs
- HttpCookiesSection.cs
- EnumerationRangeValidationUtil.cs
- TextDecorationCollectionConverter.cs
- Peer.cs
- SQLDouble.cs
- querybuilder.cs
- UInt32Storage.cs
- LogPolicy.cs
- ObservableDictionary.cs
- Exceptions.cs
- RectangleConverter.cs
- FilteredAttributeCollection.cs
- PerformanceCounter.cs
- DefaultHttpHandler.cs
- FormsAuthentication.cs
- UIElement.cs
- XNodeNavigator.cs
- GiveFeedbackEventArgs.cs
- SqlMultiplexer.cs
- MemoryRecordBuffer.cs
- CodeDelegateInvokeExpression.cs
- ObjectDataSourceChooseTypePanel.cs
- SliderAutomationPeer.cs
- Image.cs
- XmlSerializationWriter.cs
- ActivityDesignerAccessibleObject.cs
- CodeAttributeArgument.cs
- ApplicationFileCodeDomTreeGenerator.cs
- QuadraticBezierSegment.cs