Code:
/ Net / Net / 3.5.50727.3053 / DEVDIV / depot / DevDiv / releases / Orcas / SP / wpf / src / Framework / MS / Internal / Annotations / Anchoring / PathNode.cs / 1 / PathNode.cs
#pragma warning disable 1634, 1691 //------------------------------------------------------------------------------ // //// Copyright (C) Microsoft Corporation. All rights reserved. // // // Description: // PathNode represents a node in a path (a subset of the element tree). // PathNodes can have other PathNodes as children. Each refers to a // single element in the element tree. // Spec: http://team/sites/ag/Specifications/Anchoring%20Namespace%20Spec.doc // // History: // 01/01/2003: magedz: Created - based on architectural discussions and design // by axelk, rruiz, magedz // 07/23/2003: rruiz: Ported to WCP // 08/18/2003: rruiz: Updated as per spec: made the class public. // //----------------------------------------------------------------------------- using System; using System.Diagnostics; using System.Collections; using System.ComponentModel; using System.Windows; using System.Windows.Annotations; using System.Windows.Media; using System.Windows.Markup; using MS.Utility; namespace MS.Internal.Annotations.Anchoring { ////// PathNode represents a node in a path (a subset of the element tree). /// PathNodes can have other PathNodes as children. Each refers to a /// single element in the element tree. /// internal sealed class PathNode { //----------------------------------------------------- // // Constructors // //----------------------------------------------------- #region Constructors ////// Creates an instance of PathNode that refers to the specified tree node. /// /// the tree node represented by this instance ///node is null internal PathNode(DependencyObject node) { if (node == null) throw new ArgumentNullException("node"); _node = node; } #endregion Constructors //------------------------------------------------------ // // Public Methods // //----------------------------------------------------- #region Public Methods ////// Determines if obj is a PathNode and refers to the same tree node /// as this instance. /// /// the Object to test for equality ///true if obj refers to the same tree node as this instance public override bool Equals(Object obj) { PathNode otherNode = obj as PathNode; if (otherNode == null) return false; return _node.Equals(otherNode.Node); } ////// Generates a hash value for this PathNode based on the tree node /// it refers to. /// ///a hash value for this instance based on its tree node public override int GetHashCode() { if (_node == null) return base.GetHashCode(); return _node.GetHashCode(); } #endregion Public Methods //------------------------------------------------------ // // Public Operators // //------------------------------------------------------ //----------------------------------------------------- // // Public Events // //------------------------------------------------------ //----------------------------------------------------- // // Public Properties // //----------------------------------------------------- #region Public Properties ////// Returns the tree node referred to by this instance of PathNode. /// ///the tree node referred to by this instance public DependencyObject Node { get { return _node; } } ////// Returns a list of PathNodes that are children of this instance. /// This set of children is a subset of the children of the tree node /// referred to by this PathNode. /// ///list of PathNodes that are children of this instance public IList Children { get { return _children; } } #endregion Public Properties //----------------------------------------------------- // // Internal Methods // //------------------------------------------------------ #region Internal Methods ////// Builds a path of PathNodes representing the nodes between all of /// the nodes and the root of the tree. /// ///the instance referring to the root of the tree; its /// children/descendants only include the nodes between the root and /// all of the nodes ///nodes is null internal static PathNode BuildPathForElements(ICollection nodes) { if (nodes == null) throw new ArgumentNullException("nodes"); PathNode firstPathNode = null; foreach (DependencyObject node in nodes) { PathNode branch = BuildPathForElement(node); if (firstPathNode == null) firstPathNode = branch; else AddBranchToPath(firstPathNode, branch); } // make all the children readonly so we do not need to // lock the PathNode when getting the children if (firstPathNode != null) firstPathNode.FreezeChildren(); return firstPathNode; } #endregion Internal Methods //----------------------------------------------------- // // Internal Operators // //------------------------------------------------------ //------------------------------------------------------ // // Internal Events // //----------------------------------------------------- //------------------------------------------------------ // // Internal Properties // //----------------------------------------------------- #region Internal Properties ////// Property used to point content tree root's to their 'parent'. /// For instance, the root of a PageViewer's content tree would point /// to the DocumentPaginator that is holding on to the tree. /// #pragma warning suppress 7009 internal static readonly DependencyProperty HiddenParentProperty = DependencyProperty.RegisterAttached("HiddenParent", typeof(DependencyObject), typeof(PathNode)); #endregion Internal Properties //----------------------------------------------------- // // Private Methods // //----------------------------------------------------- #region Private Methods ////// Get the parent of the passed in object. /// /// the node whose parent is requested ///the parent of this node where parent is defined to be the /// first FrameworkElement/FrameworkContentElemnt found walking up the /// node's parent chain, with a preference for the visual tree vs the /// logical tree internal static DependencyObject GetParent(DependencyObject node) { Debug.Assert(node != null, "node can not be null"); DependencyObject current = node; DependencyObject parent = null; while (true) { // Try for hidden parent first above all others parent = (DependencyObject)current.GetValue(PathNode.HiddenParentProperty); if (parent == null) { // Try for Visual parent Visual visual = current as Visual; if (visual != null) { // This is a Visual node, get parent parent = VisualTreeHelper.GetParent(visual); } } if (parent == null) { // Try for Model parent parent = LogicalTreeHelper.GetParent(current); } // Check if located a parent, if so, check if it's the correct type if ((parent == null) || FrameworkElement.DType.IsInstanceOfType(parent) || FrameworkContentElement.DType.IsInstanceOfType(parent)) { break; } // Parent found but not of correct type, continue current = parent; parent = null; } return parent; } ////// Builds a path from an element to the root of its tree. Every /// element in between the element and the root is added to the /// path. /// /// the element to build a path for ///the PathNode instance referring to the root of the tree; its /// children/descendants only include the nodes between the root and /// node private static PathNode BuildPathForElement(DependencyObject node) { Debug.Assert(node != null, "node can not be null"); PathNode childNode = null; while (node != null) { PathNode pathNode = new PathNode(node); if (childNode != null) pathNode.AddChild(childNode); childNode = pathNode; // If we find a node that has the service set on it, we should stop // after processing it. For cases without a service like unit tests, // this node won't be found and we'll continue to the root. if (node.ReadLocalValue(AnnotationService.ServiceProperty) != DependencyProperty.UnsetValue) break; node = PathNode.GetParent(node); } return childNode; } ////// Adds a branch to an existing path, removing any duplicate /// nodes as necessary. Assumes that both paths are full paths /// up to the root of the same tree. If the paths are not full, /// the method will give incorrect results. If the paths are /// full but belong to different trees (and therefore have /// different roots) the method will throw. /// /// path to add branch to /// branch to be added; should be a linear path /// (no more than one child for any node) ///the path with branch having been added in and duplicate /// nodes pruned private static PathNode AddBranchToPath(PathNode path, PathNode branch) { Debug.Assert(path != null, "path can not be null"); Debug.Assert(branch != null, "branch can not be null"); // The paths must be in the same tree and therefore have the // same root. Debug.Assert(path.Node.Equals(branch.Node), "path.Node is not equal to branch.Node"); PathNode fp = path; PathNode sp = branch; // Continue down while (fp.Node.Equals(sp.Node) && sp._children.Count > 0) { // if the firstpath component equals the second path component // then we try to find the second path child component // inside the first path children bool found = false; PathNode branchNode = (PathNode)sp._children[0]; foreach (PathNode fpn in fp._children) { if (fpn.Equals(branchNode)) { // if we found one we keep moving along both the first path and the second path found = true; sp = branchNode; fp = fpn; break; } } if (found) continue; // if we can not find the second path child in the first // path child, we then just add the second path child // to the set of first path children fp.AddChild(branchNode); break; } return path; } private void AddChild(object child) { _children.Add(child); } ////// Once the node has been constructed via BuildPathForElements /// we can not modify any more the childeren. We make the /// children trough the entire PathNode tree readonly /// private void FreezeChildren() { foreach (PathNode node in _children) { node.FreezeChildren(); } _children = ArrayList.ReadOnly(_children); } #endregion Private Methods //------------------------------------------------------ // // Private Fields // //----------------------------------------------------- #region Private Fields // The element pointed to by this PathNode private DependencyObject _node; // The array of children of this PathNode private ArrayList _children = new ArrayList(1); #endregion Private Fields } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved. #pragma warning disable 1634, 1691 //------------------------------------------------------------------------------ // //// Copyright (C) Microsoft Corporation. All rights reserved. // // // Description: // PathNode represents a node in a path (a subset of the element tree). // PathNodes can have other PathNodes as children. Each refers to a // single element in the element tree. // Spec: http://team/sites/ag/Specifications/Anchoring%20Namespace%20Spec.doc // // History: // 01/01/2003: magedz: Created - based on architectural discussions and design // by axelk, rruiz, magedz // 07/23/2003: rruiz: Ported to WCP // 08/18/2003: rruiz: Updated as per spec: made the class public. // //----------------------------------------------------------------------------- using System; using System.Diagnostics; using System.Collections; using System.ComponentModel; using System.Windows; using System.Windows.Annotations; using System.Windows.Media; using System.Windows.Markup; using MS.Utility; namespace MS.Internal.Annotations.Anchoring { ////// PathNode represents a node in a path (a subset of the element tree). /// PathNodes can have other PathNodes as children. Each refers to a /// single element in the element tree. /// internal sealed class PathNode { //----------------------------------------------------- // // Constructors // //----------------------------------------------------- #region Constructors ////// Creates an instance of PathNode that refers to the specified tree node. /// /// the tree node represented by this instance ///node is null internal PathNode(DependencyObject node) { if (node == null) throw new ArgumentNullException("node"); _node = node; } #endregion Constructors //------------------------------------------------------ // // Public Methods // //----------------------------------------------------- #region Public Methods ////// Determines if obj is a PathNode and refers to the same tree node /// as this instance. /// /// the Object to test for equality ///true if obj refers to the same tree node as this instance public override bool Equals(Object obj) { PathNode otherNode = obj as PathNode; if (otherNode == null) return false; return _node.Equals(otherNode.Node); } ////// Generates a hash value for this PathNode based on the tree node /// it refers to. /// ///a hash value for this instance based on its tree node public override int GetHashCode() { if (_node == null) return base.GetHashCode(); return _node.GetHashCode(); } #endregion Public Methods //------------------------------------------------------ // // Public Operators // //------------------------------------------------------ //----------------------------------------------------- // // Public Events // //------------------------------------------------------ //----------------------------------------------------- // // Public Properties // //----------------------------------------------------- #region Public Properties ////// Returns the tree node referred to by this instance of PathNode. /// ///the tree node referred to by this instance public DependencyObject Node { get { return _node; } } ////// Returns a list of PathNodes that are children of this instance. /// This set of children is a subset of the children of the tree node /// referred to by this PathNode. /// ///list of PathNodes that are children of this instance public IList Children { get { return _children; } } #endregion Public Properties //----------------------------------------------------- // // Internal Methods // //------------------------------------------------------ #region Internal Methods ////// Builds a path of PathNodes representing the nodes between all of /// the nodes and the root of the tree. /// ///the instance referring to the root of the tree; its /// children/descendants only include the nodes between the root and /// all of the nodes ///nodes is null internal static PathNode BuildPathForElements(ICollection nodes) { if (nodes == null) throw new ArgumentNullException("nodes"); PathNode firstPathNode = null; foreach (DependencyObject node in nodes) { PathNode branch = BuildPathForElement(node); if (firstPathNode == null) firstPathNode = branch; else AddBranchToPath(firstPathNode, branch); } // make all the children readonly so we do not need to // lock the PathNode when getting the children if (firstPathNode != null) firstPathNode.FreezeChildren(); return firstPathNode; } #endregion Internal Methods //----------------------------------------------------- // // Internal Operators // //------------------------------------------------------ //------------------------------------------------------ // // Internal Events // //----------------------------------------------------- //------------------------------------------------------ // // Internal Properties // //----------------------------------------------------- #region Internal Properties ////// Property used to point content tree root's to their 'parent'. /// For instance, the root of a PageViewer's content tree would point /// to the DocumentPaginator that is holding on to the tree. /// #pragma warning suppress 7009 internal static readonly DependencyProperty HiddenParentProperty = DependencyProperty.RegisterAttached("HiddenParent", typeof(DependencyObject), typeof(PathNode)); #endregion Internal Properties //----------------------------------------------------- // // Private Methods // //----------------------------------------------------- #region Private Methods ////// Get the parent of the passed in object. /// /// the node whose parent is requested ///the parent of this node where parent is defined to be the /// first FrameworkElement/FrameworkContentElemnt found walking up the /// node's parent chain, with a preference for the visual tree vs the /// logical tree internal static DependencyObject GetParent(DependencyObject node) { Debug.Assert(node != null, "node can not be null"); DependencyObject current = node; DependencyObject parent = null; while (true) { // Try for hidden parent first above all others parent = (DependencyObject)current.GetValue(PathNode.HiddenParentProperty); if (parent == null) { // Try for Visual parent Visual visual = current as Visual; if (visual != null) { // This is a Visual node, get parent parent = VisualTreeHelper.GetParent(visual); } } if (parent == null) { // Try for Model parent parent = LogicalTreeHelper.GetParent(current); } // Check if located a parent, if so, check if it's the correct type if ((parent == null) || FrameworkElement.DType.IsInstanceOfType(parent) || FrameworkContentElement.DType.IsInstanceOfType(parent)) { break; } // Parent found but not of correct type, continue current = parent; parent = null; } return parent; } ////// Builds a path from an element to the root of its tree. Every /// element in between the element and the root is added to the /// path. /// /// the element to build a path for ///the PathNode instance referring to the root of the tree; its /// children/descendants only include the nodes between the root and /// node private static PathNode BuildPathForElement(DependencyObject node) { Debug.Assert(node != null, "node can not be null"); PathNode childNode = null; while (node != null) { PathNode pathNode = new PathNode(node); if (childNode != null) pathNode.AddChild(childNode); childNode = pathNode; // If we find a node that has the service set on it, we should stop // after processing it. For cases without a service like unit tests, // this node won't be found and we'll continue to the root. if (node.ReadLocalValue(AnnotationService.ServiceProperty) != DependencyProperty.UnsetValue) break; node = PathNode.GetParent(node); } return childNode; } ////// Adds a branch to an existing path, removing any duplicate /// nodes as necessary. Assumes that both paths are full paths /// up to the root of the same tree. If the paths are not full, /// the method will give incorrect results. If the paths are /// full but belong to different trees (and therefore have /// different roots) the method will throw. /// /// path to add branch to /// branch to be added; should be a linear path /// (no more than one child for any node) ///the path with branch having been added in and duplicate /// nodes pruned private static PathNode AddBranchToPath(PathNode path, PathNode branch) { Debug.Assert(path != null, "path can not be null"); Debug.Assert(branch != null, "branch can not be null"); // The paths must be in the same tree and therefore have the // same root. Debug.Assert(path.Node.Equals(branch.Node), "path.Node is not equal to branch.Node"); PathNode fp = path; PathNode sp = branch; // Continue down while (fp.Node.Equals(sp.Node) && sp._children.Count > 0) { // if the firstpath component equals the second path component // then we try to find the second path child component // inside the first path children bool found = false; PathNode branchNode = (PathNode)sp._children[0]; foreach (PathNode fpn in fp._children) { if (fpn.Equals(branchNode)) { // if we found one we keep moving along both the first path and the second path found = true; sp = branchNode; fp = fpn; break; } } if (found) continue; // if we can not find the second path child in the first // path child, we then just add the second path child // to the set of first path children fp.AddChild(branchNode); break; } return path; } private void AddChild(object child) { _children.Add(child); } ////// Once the node has been constructed via BuildPathForElements /// we can not modify any more the childeren. We make the /// children trough the entire PathNode tree readonly /// private void FreezeChildren() { foreach (PathNode node in _children) { node.FreezeChildren(); } _children = ArrayList.ReadOnly(_children); } #endregion Private Methods //------------------------------------------------------ // // Private Fields // //----------------------------------------------------- #region Private Fields // The element pointed to by this PathNode private DependencyObject _node; // The array of children of this PathNode private ArrayList _children = new ArrayList(1); #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
- Html32TextWriter.cs
- StructuralType.cs
- PersonalizationStateInfoCollection.cs
- String.cs
- ModuleBuilderData.cs
- ExpressionDumper.cs
- Hex.cs
- CodeCompileUnit.cs
- GlyphShapingProperties.cs
- DropShadowEffect.cs
- StringCollection.cs
- StyleXamlTreeBuilder.cs
- StrongBox.cs
- RuntimeHandles.cs
- HostingEnvironment.cs
- HtmlListAdapter.cs
- SmtpNtlmAuthenticationModule.cs
- BamlLocalizabilityResolver.cs
- MethodBuilder.cs
- XmlWrappingWriter.cs
- ForwardPositionQuery.cs
- UnlockCardRequest.cs
- RoleGroupCollection.cs
- ParagraphResult.cs
- BooleanToVisibilityConverter.cs
- SelectedCellsCollection.cs
- LinkedResourceCollection.cs
- ProviderMetadataCachedInformation.cs
- XmlWriterTraceListener.cs
- GeneratedCodeAttribute.cs
- CultureTable.cs
- SafeEventHandle.cs
- DataListItemCollection.cs
- SQLDouble.cs
- ProtocolViolationException.cs
- XmlSchemaIdentityConstraint.cs
- NewExpression.cs
- SchemaImporterExtensionsSection.cs
- FixedSOMTableCell.cs
- ThemeDirectoryCompiler.cs
- WebServiceHostFactory.cs
- PolicyManager.cs
- Parsers.cs
- CodeAttributeDeclarationCollection.cs
- DrawingDrawingContext.cs
- SoapHeaderAttribute.cs
- LogEntrySerializer.cs
- CompositionDesigner.cs
- DataServiceHost.cs
- DesignerSerializerAttribute.cs
- UnionExpr.cs
- DbConnectionFactory.cs
- TagMapCollection.cs
- ConfigurationLockCollection.cs
- PresentationTraceSources.cs
- CopyCodeAction.cs
- BrowserDefinitionCollection.cs
- _NestedSingleAsyncResult.cs
- PropertyBuilder.cs
- GeneralTransformGroup.cs
- AffineTransform3D.cs
- StateMachine.cs
- WebPartVerb.cs
- TypeDescriptionProvider.cs
- ArgumentValidation.cs
- TextElementCollection.cs
- InvokeProviderWrapper.cs
- KeyboardNavigation.cs
- NameValueConfigurationElement.cs
- SocketInformation.cs
- SecurityTokenSpecification.cs
- XmlSchemaParticle.cs
- StringSorter.cs
- ExpressionBuilderCollection.cs
- ContentValidator.cs
- UnsafeNativeMethods.cs
- EntityViewGenerator.cs
- _LocalDataStore.cs
- ScrollItemPatternIdentifiers.cs
- SimpleExpression.cs
- Parameter.cs
- SafeTokenHandle.cs
- XmlSchemaGroupRef.cs
- UriTemplateCompoundPathSegment.cs
- HttpConfigurationSystem.cs
- DataGridViewLinkCell.cs
- HtmlLink.cs
- GorillaCodec.cs
- DataGridViewColumnCollection.cs
- WpfXamlType.cs
- PrefixHandle.cs
- EntityDataSourceViewSchema.cs
- ConfigurationPropertyAttribute.cs
- TransportSecurityHelpers.cs
- SafeNativeMethodsCLR.cs
- TypeToArgumentTypeConverter.cs
- XPathNavigatorReader.cs
- VisualBasicReference.cs
- XPathNavigator.cs
- AnimationTimeline.cs