Beispiel #1
0
        /// <summary>
        /// Sets the watch on a node that is not our document node, but a node lower in the hierarchy. We watch both the Changed event and the TunneledEvent of this node.
        /// </summary>
        /// <param name="node">The node to watch.</param>
        protected virtual void SetWatchOnNode(IDocumentLeafNode node)
        {
#if DOCNODEPROXY_CONCURRENTDEBUG
            int debugUsn = System.Threading.Interlocked.Increment(ref _debugUSN);
            _debug.Enqueue("START SetWatchOnNode " + debugUsn.ToString());
#endif

            if (null == node)
            {
                throw new ArgumentNullException(nameof(node));
            }

            if (null != _weakDocNodeChangedHandler)
            {
                _weakDocNodeChangedHandler.Remove();
                _weakDocNodeChangedHandler = null;
            }
            if (null != _weakDocNodeTunneledEventHandler)
            {
                _weakDocNodeTunneledEventHandler.Remove();
                _weakDocNodeTunneledEventHandler = null;
            }

            node.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler <object, object, TunnelingEventArgs>(EhWatchedNode_TunneledEvent, handler => node.TunneledEvent -= handler));
            node.Changed       += (_weakDocNodeChangedHandler = new WeakEventHandler(EhWatchedNode_Changed, handler => node.Changed -= handler));

#if DEBUG_DOCNODEPROXYLOGGING
            Current.Console.WriteLine("Start watching node <<{0}>> of total path <<{1}>>", AbsoluteDocumentPath.GetAbsolutePath(node), _docNodePath);
#endif

#if DOCNODEPROXY_CONCURRENTDEBUG
            _debug.Enqueue("STOP  SetWatchOnNode " + debugUsn.ToString() + (_docNodeRef == null).ToString());
#endif
        }
Beispiel #2
0
        /// <summary>
        /// Sets the watch on a node that is not our document node, but a node lower in the hierarchy. We watch both the Changed event and the TunneledEvent of this node.
        /// </summary>
        /// <param name="node">The node to watch.</param>
        protected virtual void SetWatchOnNode(IDocumentLeafNode node)
        {
            if (null == node)
            {
                throw new ArgumentNullException(nameof(node));
            }

            if (null != _weakDocNodeChangedHandler)
            {
                _weakDocNodeChangedHandler.Remove();
                _weakDocNodeChangedHandler = null;
            }
            if (null != _weakDocNodeTunneledEventHandler)
            {
                _weakDocNodeTunneledEventHandler.Remove();
                _weakDocNodeTunneledEventHandler = null;
            }

            node.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler <object, object, TunnelingEventArgs>(EhWatchedNode_TunneledEvent, handler => node.TunneledEvent -= handler));
            node.Changed       += (_weakDocNodeChangedHandler = new WeakEventHandler(EhWatchedNode_Changed, handler => node.Changed -= handler));

#if DEBUG_DOCNODEPROXYLOGGING
            Current.Console.WriteLine("Start watching node <<{0}>> of total path <<{1}>>", AbsoluteDocumentPath.GetAbsolutePath(node), _docNodePath);
#endif
        }
		/// <summary>
		/// Initializes a new instance of the <see cref="SimpleCollectionChangedEventArgs"/> class.
		/// </summary>
		/// <param name="originator">The originator.</param>
		/// <exception cref="System.ArgumentNullException">originator</exception>
		public SimpleCollectionChangedEventArgs(IDocumentLeafNode originator)
		{
			if (null == originator)
				throw new ArgumentNullException("originator");

			Originator = originator;
		}
        /// <summary>
        /// Fires the <see cref="TunneledEvent"/> event.
        /// </summary>
        /// <param name="originalSource">The original source of the tunneled event.</param>
        /// <param name="e">The <see cref="TunnelingEventArgs"/> instance containing the event data.</param>
        protected virtual void OnTunnelingEvent(IDocumentLeafNode originalSource, TunnelingEventArgs e)
        {
            var ev = TunneledEvent;

            if (null != ev)
            {
                ev(this, originalSource, e);
            }
        }
Beispiel #5
0
        public DocNodeProxy(IDocumentLeafNode docNode)
        {
            if (null == docNode)
            {
                throw new ArgumentNullException(nameof(docNode));
            }

            SetDocNode(docNode);
        }
Beispiel #6
0
        /// <summary>
        /// Initializes a new instance of the <see cref="SimpleCollectionChangedEventArgs"/> class.
        /// </summary>
        /// <param name="originator">The originator.</param>
        /// <exception cref="System.ArgumentNullException">originator</exception>
        public SimpleCollectionChangedEventArgs(IDocumentLeafNode originator)
        {
            if (null == originator)
            {
                throw new ArgumentNullException("originator");
            }

            Originator = originator;
        }
Beispiel #7
0
        /// <summary>
        /// Sets the document node that is held by this proxy.
        /// </summary>
        /// <param name="value">The document node. If <c>docNode</c> implements <see cref="Main.IDocumentLeafNode" />,
        /// the document path is stored for this object in addition to the object itself.</param>
        /// <param name="parentNode">The start point of the document path. Should be equal to the member _parent, but this might be not set now.</param>
        protected void InternalSetDocNode(Main.IDocumentLeafNode value, IDocumentLeafNode parentNode)
        {
            if (!IsValidDocument(value))
            {
                throw new ArgumentException("This type of document is not allowed for the proxy of type " + GetType().ToString());
            }
            if (null == parentNode)
            {
                throw new InvalidOperationException("Parent of this node must be set in order to set the docnode.");
            }

            var oldValue = InternalDocNode;

            if (object.ReferenceEquals(oldValue, value))
            {
                return; // Nothing to do
            }
            if (null != _weakDocNodeChangedHandler)
            {
                _weakDocNodeChangedHandler.Remove();
                _weakDocNodeChangedHandler = null;
            }
            if (null != _weakDocNodeTunneledEventHandler)
            {
                _weakDocNodeTunneledEventHandler.Remove();
                _weakDocNodeTunneledEventHandler = null;
            }

            if (null != oldValue)
            {
                ClearDocNode();
            }

            var newPath = RelativeDocumentPath.GetRelativePathFromTo(parentNode, value);

            if (null != newPath)
            {
                InternalDocumentPath = newPath; // especially in dispose situations, the new path can be null. In this case we leave the path as it was
            }
            _docNodeRef = new WeakReference(value);

#if DEBUG_DOCNODEPROXYLOGGING
            Current.Console.WriteLine("RelDocNodeProxy.SetDocNode, path is <<{0}>>", _docNodePath);
#endif

            value.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler <object, object, TunnelingEventArgs>(EhDocNode_TunneledEvent, handler => value.TunneledEvent -= handler));

            if (null != _docNodePath && !_docNodePath.IsIdentity) // it does not make sense to watch the changed event of our target node is our parent because the parent can handle the Changed event itself
            {
                value.Changed += (_weakDocNodeChangedHandler = new WeakEventHandler(EhDocNode_Changed, handler => value.Changed -= handler));
            }

            OnAfterSetDocNode();

            EhSelfChanged(new Main.InstanceChangedEventArgs(oldValue, value));
        }
Beispiel #8
0
        /// <summary>
        /// Resolves the path by first using startnode as starting point. If that failed, try using documentRoot as starting point.
        /// </summary>
        /// <param name="path">The path to resolve.</param>
        /// <param name="startnode">The node object which is considered as the starting point of the path.</param>
        /// <param name="documentRoot">An alternative node which is used as starting point of the path if the first try failed.</param>
        /// <returns>The resolved object. If the resolving process failed, the return value is null.</returns>
        public static IDocumentLeafNode GetObject(AbsoluteDocumentPath path, IDocumentLeafNode startnode, IDocumentNode documentRoot)
        {
            var retval = GetObject(path, startnode);

            if (null == retval && null != documentRoot)
            {
                retval = GetObject(path, documentRoot);
            }

            return(retval);
        }
 public string GetNameOfChildObject(IDocumentLeafNode o)
 {
     if (null != o)
     {
         return("Infrastructure object of type " + o.GetType().FullName);
     }
     else
     {
         return("<<null>>");
     }
 }
Beispiel #10
0
        /// <summary>
        /// Get the first parent node of the node <code>node</code> that implements the given type <code>type.</code>.
        /// </summary>
        /// <param name="node">The node from where the search begins.</param>
        /// <param name="type">The type to search for.</param>
        /// <returns>The first parental node that implements the type <code>type.</code>
        /// </returns>
        public static IDocumentLeafNode GetRootNodeImplementing(IDocumentLeafNode node, System.Type type)
        {
            if (null == node)
            {
                return(null);
            }

            node = node.ParentObject;
            while (node != null && !type.IsInstanceOfType(node))
            {
                node = node.ParentObject;
            }

            return(type.IsInstanceOfType(node) ? node : null);
        }
Beispiel #11
0
        /// <summary>
        /// Get the first parent node of the node <code>node</code> that implements the given type <code>type.</code>.
        /// </summary>
        /// <typeparam name="T">The type to search for.</typeparam>
        /// <param name="node">The node from where the search begins.</param>
        /// <returns>The first parental node that implements the type <code>T</code>.</returns>
        public static T GetRootNodeImplementing <T>(IDocumentLeafNode node)
        {
            if (null == node)
            {
                return(default(T));
            }

            node = node.ParentObject;
            while (node != null && !(node is T))
            {
                node = node.ParentObject;
            }

            return((node is T) ? (T)node : default(T));
        }
Beispiel #12
0
        /// <summary>
        /// Get the root node of the node <code>node</code>. The root node is defined as last node in the hierarchie that
        /// either has not implemented the <see cref="IDocumentLeafNode"/> interface or has no parent.
        /// </summary>
        /// <param name="node">The node from where the search begins.</param>
        /// <returns>The root node, i.e. the last node in the hierarchie that
        /// either has not implemented the <see cref="IDocumentLeafNode"/> interface or has no parent</returns>
        public static IDocumentLeafNode GetRootNode(IDocumentLeafNode node)
        {
            if (null == node)
            {
                throw new ArgumentNullException(nameof(node));
            }

            var parent = node.ParentObject;

            while (null != parent)
            {
                node   = parent;
                parent = node.ParentObject;
            }

            return(node);
        }
Beispiel #13
0
        /// <summary>
        /// Get the absolute path of the node <code>node</code> starting either from the root, or from the object in the depth
        /// <code>maxDepth</code>, whatever is reached first.
        /// </summary>
        /// <param name="node">The node for which the path is to be retrieved.</param>
        /// <param name="maxDepth">The maximal hierarchie depth (the maximal number of path elements returned).</param>
        /// <returns>The path from the root or from the node in the depth <code>maxDepth</code>, whatever is reached first. The path is <b>not</b> prepended
        /// by a "/".
        /// </returns>
        public static AbsoluteDocumentPath GetPath(IDocumentLeafNode node, int maxDepth)
        {
            if (null == node)
            {
                throw new ArgumentNullException("node");
            }
            if (maxDepth <= 0)
            {
                throw new ArgumentOutOfRangeException("maxDepth should be > 0");
            }

            var list = new List <string>();

            int depth  = 0;
            var parent = node.ParentObject;

            while (parent != null)
            {
                if (depth >= maxDepth)
                {
                    break;
                }

                string name = parent.GetNameOfChildObject(node);

                if (null == name) // an empty string is a valid name, e.g. for a folder text document located in the root folder
                {
                    throw new InvalidOperationException(string.Format("Parent node (type:{0}) of node (type: {1}) did not return a valid name for the child node!", parent.GetType(), node.GetType()));
                }

                list.Add(name);
                node   = parent;
                parent = node.ParentObject;
                ++depth;
            }

            if (maxDepth == int.MaxValue && node != null && !(node is IProject))
            {
                string msg = string.Format("Document {0} is not rooted. The path so far retrieved is {1}", node, list);
                throw new InvalidOperationException(msg);
            }

            return(new AbsoluteDocumentPath(list.TakeFromUpperIndexExclusiveDownToLowerIndexInclusive(list.Count, 0)));
        }
Beispiel #14
0
 public override string GetNameOfChildObject(IDocumentLeafNode o)
 {
     if (null == o)
     {
         return(null);
     }
     else if (object.ReferenceEquals(o, _dataTables))
     {
         return("Tables");
     }
     else if (object.ReferenceEquals(o, _graphs))
     {
         return("Graphs");
     }
     else if (object.ReferenceEquals(o, _graphs3D))
     {
         return("Graphs3D");
     }
     else if (object.ReferenceEquals(o, _textDocuments))
     {
         return("Texts");
     }
     else if (object.ReferenceEquals(o, _tableLayouts))
     {
         return("TableLayouts");
     }
     else if (object.ReferenceEquals(o, _fitFunctionScripts))
     {
         return("FitFunctionScripts");
     }
     else if (object.ReferenceEquals(o, _projectFolderProperties))
     {
         return("FolderProperties");
     }
     else if (object.ReferenceEquals(o, _projectFolders))
     {
         return("ProjectFolders");
     }
     else
     {
         return(null);
     }
 }
Beispiel #15
0
        public static IDocumentLeafNode GetObject(AbsoluteDocumentPath path, IDocumentLeafNode startnode)
        {
            if (null == path)
            {
                throw new ArgumentNullException("path");
            }
            if (null == startnode)
            {
                throw new ArgumentNullException("startnode");
            }

            var node = startnode;

            node = GetRootNode(node);

            for (int i = 0; i < path.Count; i++)
            {
                if (path[i] == "..")
                {
                    if (null != node)
                    {
                        node = node.ParentObject;
                    }
                    else
                    {
                        return(null);
                    }
                }
                else
                {
                    if (node is Main.IDocumentNode)
                    {
                        node = ((Main.IDocumentNode)node).GetChildObjectNamed(path[i]);
                    }
                    else
                    {
                        return(null);
                    }
                }
            } // end for
            return(node);
        }
Beispiel #16
0
        public static IDocumentLeafNode GetObject(RelativeDocumentPath path, IDocumentLeafNode startnode)
        {
            if (null == path)
            {
                throw new ArgumentNullException(nameof(path));
            }
            if (null == startnode)
            {
                throw new ArgumentNullException(nameof(startnode));
            }

            var node = startnode;

            for (int i = 0; i < path._numberOfLevelsDown && null != node; ++i)
            {
                node = node.ParentNode;
            }

            if (null == node)
            {
                return(null); // Path not resolveable
            }
            for (int i = 0; i < path._pathParts.Length; i++)
            {
                if (node is Main.IDocumentNode)
                {
                    node = ((Main.IDocumentNode)node).GetChildObjectNamed(path._pathParts[i]);
                }
                else
                {
                    return(null);
                }
            } // end for

            return(node);
        }
Beispiel #17
0
		/// <summary>
		/// Replaces parts of the part of the document node by another part. If the replacement was successful, the original document node is cleared.
		/// See <see cref="M:DocumentPath.ReplacePathParts"/> for details of the part replacement.
		/// </summary>
		/// <param name="partToReplace">Part of the path that should be replaced. This part has to match the beginning of this part. The last item of the part
		/// is allowed to be given only partially.</param>
		/// <param name="newPart">The new part to replace that piece of the path, that match the <c>partToReplace</c>.</param>
		/// <param name="rootNode">Any document node in the hierarchy that is used to find the root node of the hierarchy.</param>
		/// <returns>True if the path could be replaced. Returns false if the path does not fulfill the presumptions given above.</returns>
		/// <remarks>
		/// As stated above, the last item of the partToReplace can be given only partially. As an example, the path (here separated by space)
		/// <para>Tables Preexperiment1/WDaten Time</para>
		/// <para>should be replaced by </para>
		/// <para>Tables Preexperiment2\WDaten Time</para>
		/// <para>To make this replacement, the partToReplace should be given by</para>
		/// <para>Tables Preexperiment1/</para>
		/// <para>and the newPart should be given by</para>
		/// <para>Tables Preexperiment2\</para>
		/// <para>Note that Preexperiment1\ and Preexperiment2\ are only partially defined items of the path.</para>
		/// </remarks>
		public bool ReplacePathParts(AbsoluteDocumentPath partToReplace, AbsoluteDocumentPath newPart, IDocumentLeafNode rootNode)
		{
			if (!(_docNodePath != null || IsDisposeInProgress)) throw new InvalidProgramException();
			if (null == rootNode)
				throw new ArgumentNullException(nameof(rootNode));

			AbsoluteDocumentPath newPath;
			var success = _docNodePath.ReplacePathParts(partToReplace, newPart, out newPath);
			if (success)
			{
				_docNodePath = newPath;
				ClearDocNode();
				ResolveDocumentObject(rootNode);
			}

			return success;
		}
Beispiel #18
0
        /// <summary>
        /// Gets the node that is designated by the provided <paramref name="path"/>  or the least resolveable node.
        /// </summary>
        /// <param name="path">The document path to resolve.</param>
        /// <param name="startnode">The startnode.</param>
        /// <param name="pathWasCompletelyResolved">If set to <c>true</c> on return, the path was completely resolved. Otherwise, <c>false</c>.</param>
        /// <returns>The resolved node, or the least node on the path that could be resolved.</returns>
        /// <exception cref="System.ArgumentNullException">
        /// path
        /// or
        /// startnode
        /// </exception>
        public static IDocumentLeafNode GetNodeOrLeastResolveableNode(AbsoluteDocumentPath path, IDocumentLeafNode startnode, out bool pathWasCompletelyResolved)
        {
            if (null == path)
            {
                throw new ArgumentNullException("path");
            }
            if (null == startnode)
            {
                throw new ArgumentNullException("startnode");
            }

            var node = startnode;

            node = GetRootNode(node);
            if (null == node)
            {
                throw new InvalidProgramException("startnote is not rooted");
            }

            var prevNode = node;

            pathWasCompletelyResolved = true;

            for (int i = 0; i < path.Count; i++)
            {
                prevNode = node;
                if (path[i] == "..")
                {
                    node = node.ParentObject;
                }
                else
                {
                    if (node is Main.IDocumentNode)
                    {
                        node = ((Main.IDocumentNode)node).GetChildObjectNamed(path[i]);
                    }
                    else
                    {
                        node = null;
                    }
                }

                if (node == null)
                {
                    pathWasCompletelyResolved = false;
                    break;
                }
            } // end for

            return(node ?? prevNode);
        }
Beispiel #19
0
		/// <summary>
		/// Can be overriden by derived classes to ensure that the right type of document is stored in
		/// this proxy.
		/// </summary>
		/// <param name="obj">The object to test.</param>
		/// <returns>True if the <c>obj</c> has the right type to store in this proxy, false otherwise.</returns>
		protected virtual bool IsValidDocument(IDocumentLeafNode obj)
		{
			return true;
		}
Beispiel #20
0
		/// <summary>
		/// Sets the document node that is held by this proxy.
		/// </summary>
		/// <param name="value">The document node. If <c>docNode</c> implements <see cref="Main.IDocumentLeafNode" />,
		/// the document path is stored for this object in addition to the object itself.</param>
		/// <param name="parentNode">The start point of the document path. Should be equal to the member _parent, but this might be not set now.</param>
		protected void InternalSetDocNode(Main.IDocumentLeafNode value, IDocumentLeafNode parentNode)
		{
			if (!IsValidDocument(value))
				throw new ArgumentException("This type of document is not allowed for the proxy of type " + this.GetType().ToString());
			if (null == parentNode)
				throw new InvalidOperationException("Parent of this node must be set in order to set the docnode.");

			var oldValue = this.InternalDocNode;
			if (object.ReferenceEquals(oldValue, value))
				return; // Nothing to do

			if (null != _weakDocNodeChangedHandler)
			{
				_weakDocNodeChangedHandler.Remove();
				_weakDocNodeChangedHandler = null;
			}
			if (null != _weakDocNodeTunneledEventHandler)
			{
				_weakDocNodeTunneledEventHandler.Remove();
				_weakDocNodeTunneledEventHandler = null;
			}

			if (null != oldValue)
			{
				ClearDocNode();
			}

			var newPath = RelativeDocumentPath.GetRelativePathFromTo(parentNode, value);
			if (null != newPath)
				InternalDocumentPath = newPath; // especially in dispose situations, the new path can be null. In this case we leave the path as it was

			_docNodeRef = new WeakReference(value);

#if DEBUG_DOCNODEPROXYLOGGING
			Current.Console.WriteLine("RelDocNodeProxy.SetDocNode, path is <<{0}>>", _docNodePath);
#endif

			value.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler<object, object, TunnelingEventArgs>(EhDocNode_TunneledEvent, handler => value.TunneledEvent -= handler));

			if (null != _docNodePath && !_docNodePath.IsIdentity) // it does not make sense to watch the changed event of our target node is our parent because the parent can handle the Changed event itself
			{
				value.Changed += (_weakDocNodeChangedHandler = new WeakEventHandler(EhDocNode_Changed, handler => value.Changed -= handler));
			}

			OnAfterSetDocNode();

			EhSelfChanged(new Main.InstanceChangedEventArgs(oldValue, value));
		}
Beispiel #21
0
		/// <summary>
		/// Sets the watch on a node that is not our document node, but a node lower in the hierarchy. We watch both the Changed event and the TunneledEvent of this node.
		/// </summary>
		/// <param name="node">The node to watch.</param>
		protected virtual void SetWatchOnNode(IDocumentLeafNode node)
		{
			if (null == node)
				throw new ArgumentNullException(nameof(node));

			if (null != _weakDocNodeChangedHandler)
			{
				_weakDocNodeChangedHandler.Remove();
				_weakDocNodeChangedHandler = null;
			}
			if (null != _weakDocNodeTunneledEventHandler)
			{
				_weakDocNodeTunneledEventHandler.Remove();
				_weakDocNodeTunneledEventHandler = null;
			}

			node.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler<object, object, TunnelingEventArgs>(EhWatchedNode_TunneledEvent, handler => node.TunneledEvent -= handler));
			node.Changed += (_weakDocNodeChangedHandler = new WeakEventHandler(EhWatchedNode_Changed, handler => node.Changed -= handler));

#if DEBUG_DOCNODEPROXYLOGGING
			Current.Console.WriteLine("Start watching node <<{0}>> of total path <<{1}>>", AbsoluteDocumentPath.GetAbsolutePath(node), _docNodePath);
#endif
		}
Beispiel #22
0
		/// <summary>
		/// Retrieves the relative path from the node <code>startnode</code> to the node <code>endnode</code>.
		/// </summary>
		/// <param name="startnode">The node where the path begins.</param>
		/// <param name="endnode">The node where the path ends.</param>
		/// <returns>If the two nodes share a common root, the function returns the relative path from <code>startnode</code> to <code>endnode</code>.
		/// If the nodes have no common root, then the function returns the absolute path of the endnode.</returns>
		public static RelativeDocumentPath GetRelativePathFromTo(IDocumentLeafNode startnode, IDocumentLeafNode endnode)
		{
			return GetRelativePathFromTo(startnode, endnode, null);
		}
Beispiel #23
0
 /// <summary>
 /// Constructor by giving a numeric column.
 /// </summary>
 /// <param name="column">The numeric column to hold.</param>
 protected NumericColumnProxy(IDocumentLeafNode column)
     : base(column)
 {
 }
Beispiel #24
0
 public string GetNameOfChildObject(IDocumentLeafNode o)
 {
     throw new NotImplementedException();
 }
Beispiel #25
0
		public DocNodeProxy(IDocumentLeafNode docNode)
		{
			if (null == docNode)
				throw new ArgumentNullException(nameof(docNode));

			SetDocNode(docNode);
		}
Beispiel #26
0
        /// <summary>
        /// Gets the node that is designated by the provided <paramref name="path"/>  or the least resolveable node.
        /// </summary>
        /// <param name="path">The document path to resolve.</param>
        /// <param name="startnode">The startnode.</param>
        /// <param name="pathWasCompletelyResolved">If set to <c>true</c> on return, the path was completely resolved. Otherwise, <c>false</c>.</param>
        /// <returns>The resolved node, or the least node on the path that could be resolved.</returns>
        /// <exception cref="System.ArgumentNullException">
        /// path
        /// or
        /// startnode
        /// </exception>
        public static IDocumentLeafNode GetNodeOrLeastResolveableNode(RelativeDocumentPath path, IDocumentLeafNode startnode, out bool pathWasCompletelyResolved)
        {
            if (null == path)
            {
                throw new ArgumentNullException(nameof(path));
            }
            if (null == startnode)
            {
                throw new ArgumentNullException(nameof(startnode));
            }

            var node     = startnode;
            var prevNode = startnode;

            for (int i = 0; i < path._numberOfLevelsDown && null != node; ++i)
            {
                prevNode = node;
                node     = node.ParentNode;
            }

            if (null == node)
            {
                pathWasCompletelyResolved = false;
                return(prevNode);
            }

            pathWasCompletelyResolved = true;
            for (int i = 0; i < path._pathParts.Length && null != node; i++)
            {
                prevNode = node;

                if (node is Main.IDocumentNode)
                {
                    node = ((Main.IDocumentNode)node).GetChildObjectNamed(path._pathParts[i]);
                }
                else
                {
                    node = null;
                }
            } // end for

            pathWasCompletelyResolved = null != node;
            return(node ?? prevNode);
        }
Beispiel #27
0
        /// <summary>
        /// Retrieves the relative path from the node <code>startnode</code> to the node <code>endnode</code>.
        /// </summary>
        /// <param name="startnode">The node where the path begins.</param>
        /// <param name="endnode">The node where the path ends.</param>
        /// <param name="stoppernode">A object which is used as stopper. If the relative path would step down below this node in the hierarchie,
        /// not the relative path, but the absolute path of the endnode is returned. This is usefull for instance for serialization purposes.You can set the stopper node
        /// to the root object of serialization, so that path in the inner of the serialization tree are relative paths, whereas paths to objects not includes in the
        /// serialization tree are returned as absolute paths. The stoppernode can be null.</param>
        /// <returns>If the two nodes share a common root, the function returns the relative path from <code>startnode</code> to <code>endnode</code>.
        /// If the nodes have no common root, then the function returns the absolute path of the endnode.
        /// <para>If either startnode or endnode is null, then null is returned.</para></returns>
        public static RelativeDocumentPath GetRelativePathFromTo(IDocumentLeafNode startnode, IDocumentLeafNode endnode, IDocumentNode stoppernode)
        {
            if (startnode == null)
            {
                throw new ArgumentNullException(nameof(startnode));
            }
            if (endnode == null)
            {
                throw new ArgumentNullException(nameof(endnode));
            }

            if (object.ReferenceEquals(startnode, endnode))
            {
                return(IdentityPath); // Start node and end node are identical
            }
            var currStart = startnode;
            var currEnd   = endnode;

            var startNodesList = new List <IDocumentLeafNode>(Collections.TreeNodeExtensions.TakeFromHereToRoot(startnode));
            var endNodesList   = new List <IDocumentLeafNode>(Collections.TreeNodeExtensions.TakeFromHereToRoot(endnode));

            var commonNodes = new HashSet <IDocumentLeafNode>(startNodesList);

            commonNodes.IntersectWith(new HashSet <IDocumentLeafNode>(endNodesList));

            if (commonNodes.Count == 0)
            {
                return(null); // happens if either startnode or endnode are not rooted (this can happen temporarily during instance creation)
            }
            int numberOfNodesDown        = 0;
            IDocumentLeafNode commonNode = null;

            for (int i = 0; i < startNodesList.Count; ++i)
            {
                if (commonNodes.Contains(startNodesList[i]))
                {
                    commonNode = startNodesList[i];
                    break;
                }
                else
                {
                    numberOfNodesDown++;
                }
            }

            if (null == commonNodes)
            {
                throw new InvalidOperationException(nameof(commonNode) + " should always be != null");
            }

            var idx = endNodesList.IndexOf(commonNode);

            if (idx < 0)
            {
                throw new InvalidOperationException(nameof(idx) + " of commonNode in endNodesList should always be >=0");
            }
            else if (idx == 0)
            {
                throw new InvalidOperationException(nameof(idx) + "=0 should not happen because this means identical startnode and endnode");
            }

            return(new RelativeDocumentPath(numberOfNodesDown, endNodesList.TakeFromUpperIndexExclusiveDownToLowerIndexInclusive(idx, 0).Select(x => x.ParentObject.GetNameOfChildObject(x))));
        }
Beispiel #28
0
 /// <summary>
 /// Retrieves the relative path from the node <code>startnode</code> to the node <code>endnode</code>.
 /// </summary>
 /// <param name="startnode">The node where the path begins.</param>
 /// <param name="endnode">The node where the path ends.</param>
 /// <returns>If the two nodes share a common root, the function returns the relative path from <code>startnode</code> to <code>endnode</code>.
 /// If the nodes have no common root, then the function returns the absolute path of the endnode.</returns>
 public static RelativeDocumentPath GetRelativePathFromTo(IDocumentLeafNode startnode, IDocumentLeafNode endnode)
 {
     return(GetRelativePathFromTo(startnode, endnode, null));
 }
Beispiel #29
0
		/// <summary>
		/// Sets the watch on a node that is not our document node, but a node lower in the hierarchy. We watch both the Changed event and the TunneledEvent of this node.
		/// </summary>
		/// <param name="node">The node to watch.</param>
		protected virtual void SetWatchOnNode(IDocumentLeafNode node)
		{
#if DOCNODEPROXY_CONCURRENTDEBUG
			int debugUsn = System.Threading.Interlocked.Increment(ref _debugUSN);
			_debug.Enqueue("START SetWatchOnNode " + debugUsn.ToString());
#endif

			if (null == node)
				throw new ArgumentNullException(nameof(node));

			if (null != _weakDocNodeChangedHandler)
			{
				_weakDocNodeChangedHandler.Remove();
				_weakDocNodeChangedHandler = null;
			}
			if (null != _weakDocNodeTunneledEventHandler)
			{
				_weakDocNodeTunneledEventHandler.Remove();
				_weakDocNodeTunneledEventHandler = null;
			}

			node.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler<object, object, TunnelingEventArgs>(EhWatchedNode_TunneledEvent, handler => node.TunneledEvent -= handler));
			node.Changed += (_weakDocNodeChangedHandler = new WeakEventHandler(EhWatchedNode_Changed, handler => node.Changed -= handler));

#if DEBUG_DOCNODEPROXYLOGGING
			Current.Console.WriteLine("Start watching node <<{0}>> of total path <<{1}>>", AbsoluteDocumentPath.GetAbsolutePath(node), _docNodePath);
#endif

#if DOCNODEPROXY_CONCURRENTDEBUG
			_debug.Enqueue("STOP  SetWatchOnNode " + debugUsn.ToString() + (_docNodeRef == null).ToString());
#endif
		}
Beispiel #30
0
		/// <summary>
		/// Retrieves the relative path from the node <code>startnode</code> to the node <code>endnode</code>.
		/// </summary>
		/// <param name="startnode">The node where the path begins.</param>
		/// <param name="endnode">The node where the path ends.</param>
		/// <param name="stoppernode">A object which is used as stopper. If the relative path would step down below this node in the hierarchie,
		/// not the relative path, but the absolute path of the endnode is returned. This is usefull for instance for serialization purposes.You can set the stopper node
		/// to the root object of serialization, so that path in the inner of the serialization tree are relative paths, whereas paths to objects not includes in the
		/// serialization tree are returned as absolute paths. The stoppernode can be null.</param>
		/// <returns>If the two nodes share a common root, the function returns the relative path from <code>startnode</code> to <code>endnode</code>.
		/// If the nodes have no common root, then the function returns the absolute path of the endnode.
		/// <para>If either startnode or endnode is null, then null is returned.</para></returns>
		public static RelativeDocumentPath GetRelativePathFromTo(IDocumentLeafNode startnode, IDocumentLeafNode endnode, IDocumentNode stoppernode)
		{
			if (startnode == null)
				throw new ArgumentNullException(nameof(startnode));
			if (endnode == null)
				throw new ArgumentNullException(nameof(endnode));

			if (object.ReferenceEquals(startnode, endnode))
				return IdentityPath; // Start node and end node are identical

			var currStart = startnode;
			var currEnd = endnode;

			var startNodesList = new List<IDocumentLeafNode>(Altaxo.Collections.TreeNodeExtensions.TakeFromHereToRoot(startnode));
			var endNodesList = new List<IDocumentLeafNode>(Altaxo.Collections.TreeNodeExtensions.TakeFromHereToRoot(endnode));

			var commonNodes = new HashSet<IDocumentLeafNode>(startNodesList);
			commonNodes.IntersectWith(new HashSet<IDocumentLeafNode>(endNodesList));

			if (commonNodes.Count == 0)
				return null; // happens if either startnode or endnode are not rooted (this can happen temporarily during instance creation)

			int numberOfNodesDown = 0;
			IDocumentLeafNode commonNode = null;
			for (int i = 0; i < startNodesList.Count; ++i)
			{
				if (commonNodes.Contains(startNodesList[i]))
				{
					commonNode = startNodesList[i];
					break;
				}
				else
				{
					numberOfNodesDown++;
				}
			}

			if (null == commonNodes)
				throw new InvalidOperationException(nameof(commonNode) + " should always be != null");

			var idx = endNodesList.IndexOf(commonNode);

			if (idx < 0)
				throw new InvalidOperationException(nameof(idx) + " of commonNode in endNodesList should always be >=0");
			else if (idx == 0)
				throw new InvalidOperationException(nameof(idx) + "=0 should not happen because this means identical startnode and endnode");

			return new RelativeDocumentPath(numberOfNodesDown, endNodesList.TakeFromUpperIndexExclusiveDownToLowerIndexInclusive(idx, 0).Select(x => x.ParentObject.GetNameOfChildObject(x)));
		}
Beispiel #31
0
 public bool ReplacePathParts(AbsoluteDocumentPath partToReplace, AbsoluteDocumentPath newPart, IDocumentLeafNode rootNode)
 {
     return(false);
 }
Beispiel #32
0
		/// <summary>
		/// Constructor by giving a numeric column.
		/// </summary>
		/// <param name="column">The numeric column to hold.</param>
		protected NumericColumnProxy(IDocumentLeafNode column)
			: base(column)
		{
		}
		public bool ReplacePathParts(AbsoluteDocumentPath partToReplace, AbsoluteDocumentPath newPart, IDocumentLeafNode rootNode)
		{
			return false;
		}
Beispiel #34
0
		/// <summary>
		/// Gets the node that is designated by the provided <paramref name="path"/>  or the least resolveable node.
		/// </summary>
		/// <param name="path">The document path to resolve.</param>
		/// <param name="startnode">The startnode.</param>
		/// <param name="pathWasCompletelyResolved">If set to <c>true</c> on return, the path was completely resolved. Otherwise, <c>false</c>.</param>
		/// <returns>The resolved node, or the least node on the path that could be resolved.</returns>
		/// <exception cref="System.ArgumentNullException">
		/// path
		/// or
		/// startnode
		/// </exception>
		public static IDocumentLeafNode GetNodeOrLeastResolveableNode(RelativeDocumentPath path, IDocumentLeafNode startnode, out bool pathWasCompletelyResolved)
		{
			if (null == path)
				throw new ArgumentNullException(nameof(path));
			if (null == startnode)
				throw new ArgumentNullException(nameof(startnode));

			var node = startnode;
			var prevNode = startnode;

			for (int i = 0; i < path._numberOfLevelsDown && null != node; ++i)
			{
				prevNode = node;
				node = node.ParentNode;
			}

			if (null == node)
			{
				pathWasCompletelyResolved = false;
				return prevNode;
			}

			pathWasCompletelyResolved = true;
			for (int i = 0; i < path._pathParts.Length && null != node; i++)
			{
				prevNode = node;

				if (node is Main.IDocumentNode)
					node = ((Main.IDocumentNode)node).GetChildObjectNamed(path._pathParts[i]);
				else
					node = null;
			} // end for

			pathWasCompletelyResolved = null != node;
			return node ?? prevNode;
		}
Beispiel #35
0
		protected ReadableColumnProxy(IDocumentLeafNode column)
			: base(column)
		{
		}
Beispiel #36
0
        /// <summary>
        /// Sets the document node that is held by this proxy.
        /// </summary>
        /// <param name="value">The document node. If <c>docNode</c> implements <see cref="Main.IDocumentLeafNode" />,
        /// the document path is stored for this object in addition to the object itself.</param>
        public void SetDocNode(IDocumentLeafNode value)
        {
            if (null == value)
            {
                throw new ArgumentNullException(nameof(value));
            }

            var oldValue = InternalDocumentNode;

            if (object.ReferenceEquals(oldValue, value))
            {
                return;
            }

            if (!IsValidDocument(value))
            {
                throw new ArgumentException("This type of document is not allowed for the proxy of type " + GetType().ToString());
            }

#if DOCNODEPROXY_CONCURRENTDEBUG
            _debug.Enqueue("START SetDocNode");
#endif

            if (null != _weakDocNodeChangedHandler)
            {
                _weakDocNodeChangedHandler.Remove();
                _weakDocNodeChangedHandler = null;
            }
            if (null != _weakDocNodeTunneledEventHandler)
            {
                _weakDocNodeTunneledEventHandler.Remove();
                _weakDocNodeTunneledEventHandler = null;
            }

#if DOCNODEPROXY_CONCURRENTDEBUG
            _debug.Enqueue("MIDDL SetDocNode EventHandlers removed");
#endif

            if (oldValue != null)
            {
                ClearDocNode();
            }

            InternalDocumentPath = Main.AbsoluteDocumentPath.GetAbsolutePath(value);
            _docNodeRef          = new WeakReference(value);

#if DEBUG_DOCNODEPROXYLOGGING
            Current.Console.WriteLine("DocNodeProxy.SetDocNode, path is <<{0}>>", _docNodePath);
#endif

            InternalCheckAbsolutePath();

            value.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler <object, object, TunnelingEventArgs>(EhDocNode_TunneledEvent, handler => value.TunneledEvent -= handler));
            value.Changed       += (_weakDocNodeChangedHandler = new WeakEventHandler(EhDocNode_Changed, handler => value.Changed -= handler));

            OnAfterSetDocNode();

            EhSelfChanged(new Main.InstanceChangedEventArgs(oldValue, value));

#if DOCNODEPROXY_CONCURRENTDEBUG
            _debug.Enqueue("STOP  SetDocNode");
#endif
        }
Beispiel #37
0
        /// <summary>
        /// Get the absolute path of the node <code>node</code> starting from the root.
        /// </summary>
        /// <param name="node">The node for which the path is retrieved.</param>
        /// <returns>The absolute path of the node. The first element is a "/" to mark this as absolute path.</returns>
        public static AbsoluteDocumentPath GetAbsolutePath(IDocumentLeafNode node)
        {
            AbsoluteDocumentPath path = GetPath(node, int.MaxValue);

            return(path);
        }
Beispiel #38
0
        /// <summary>
        /// Replaces parts of the part of the document node by another part. If the replacement was successful, the original document node is cleared.
        /// See <see cref="M:DocumentPath.ReplacePathParts"/> for details of the part replacement.
        /// </summary>
        /// <param name="partToReplace">Part of the path that should be replaced. This part has to match the beginning of this part. The last item of the part
        /// is allowed to be given only partially.</param>
        /// <param name="newPart">The new part to replace that piece of the path, that match the <c>partToReplace</c>.</param>
        /// <param name="rootNode">Any document node in the hierarchy that is used to find the root node of the hierarchy.</param>
        /// <returns>True if the path could be replaced. Returns false if the path does not fulfill the presumptions given above.</returns>
        /// <remarks>
        /// As stated above, the last item of the partToReplace can be given only partially. As an example, the path (here separated by space)
        /// <para>Tables Preexperiment1/WDaten Time</para>
        /// <para>should be replaced by </para>
        /// <para>Tables Preexperiment2\WDaten Time</para>
        /// <para>To make this replacement, the partToReplace should be given by</para>
        /// <para>Tables Preexperiment1/</para>
        /// <para>and the newPart should be given by</para>
        /// <para>Tables Preexperiment2\</para>
        /// <para>Note that Preexperiment1\ and Preexperiment2\ are only partially defined items of the path.</para>
        /// </remarks>
        public bool ReplacePathParts(AbsoluteDocumentPath partToReplace, AbsoluteDocumentPath newPart, IDocumentLeafNode rootNode)
        {
            if (!(_docNodePath != null || IsDisposeInProgress))
            {
                throw new InvalidProgramException();
            }
            if (null == rootNode)
            {
                throw new ArgumentNullException(nameof(rootNode));
            }

            var success = _docNodePath.ReplacePathParts(partToReplace, newPart, out var newPath);

            if (success)
            {
                _docNodePath = newPath;
                ClearDocNode();
                ResolveDocumentObject(rootNode);
            }

            return(success);
        }
Beispiel #39
0
 public static string GetPathString(IDocumentLeafNode node, int maxDepth)
 {
     return(GetPath(node, maxDepth).ToString());
 }
Beispiel #40
0
		public static IDocumentLeafNode GetObject(RelativeDocumentPath path, IDocumentLeafNode startnode)
		{
			if (null == path)
				throw new ArgumentNullException(nameof(path));
			if (null == startnode)
				throw new ArgumentNullException(nameof(startnode));

			var node = startnode;

			for (int i = 0; i < path._numberOfLevelsDown && null != node; ++i)
			{
				node = node.ParentNode;
			}

			if (null == node)
				return null; // Path not resolveable

			for (int i = 0; i < path._pathParts.Length; i++)
			{
				if (node is Main.IDocumentNode)
					node = ((Main.IDocumentNode)node).GetChildObjectNamed(path._pathParts[i]);
				else
					return null;
			} // end for

			return node;
		}
Beispiel #41
0
 public DocumentNodeAndName(IDocumentLeafNode doc, Action setMemberToNullAction, string name)
 {
     _doc  = doc;
     _name = name;
     _setMemberToNullAction = setMemberToNullAction;
 }
Beispiel #42
0
		public DocumentNodeAndName(IDocumentLeafNode doc, Action setMemberToNullAction, string name)
		{
			_doc = doc;
			_name = name;
			_setMemberToNullAction = setMemberToNullAction;
		}
Beispiel #43
0
 /// <summary>
 /// Can be overriden by derived classes to ensure that the right type of document is stored in
 /// this proxy.
 /// </summary>
 /// <param name="obj">The object to test.</param>
 /// <returns>True if the <c>obj</c> has the right type to store in this proxy, false otherwise.</returns>
 protected virtual bool IsValidDocument(IDocumentLeafNode obj)
 {
     return(true);
 }
Beispiel #44
0
		/// <summary>
		/// Sets the document node that is held by this proxy.
		/// </summary>
		/// <param name="value">The document node. If <c>docNode</c> implements <see cref="Main.IDocumentLeafNode" />,
		/// the document path is stored for this object in addition to the object itself.</param>
		public void SetDocNode(IDocumentLeafNode value)
		{
			if (null == value)
				throw new ArgumentNullException(nameof(value));

			var oldValue = InternalDocumentNode;
			if (object.ReferenceEquals(oldValue, value))
				return;

			if (!IsValidDocument(value))
				throw new ArgumentException("This type of document is not allowed for the proxy of type " + this.GetType().ToString());

#if DOCNODEPROXY_CONCURRENTDEBUG
			_debug.Enqueue("START SetDocNode");
#endif

			if (null != _weakDocNodeChangedHandler)
			{
				_weakDocNodeChangedHandler.Remove();
				_weakDocNodeChangedHandler = null;
			}
			if (null != _weakDocNodeTunneledEventHandler)
			{
				_weakDocNodeTunneledEventHandler.Remove();
				_weakDocNodeTunneledEventHandler = null;
			}

#if DOCNODEPROXY_CONCURRENTDEBUG
			_debug.Enqueue("MIDDL SetDocNode EventHandlers removed");
#endif

			if (oldValue != null)
			{
				ClearDocNode();
			}

			InternalDocumentPath = Main.AbsoluteDocumentPath.GetAbsolutePath(value);
			_docNodeRef = new WeakReference(value);

#if DEBUG_DOCNODEPROXYLOGGING
			Current.Console.WriteLine("DocNodeProxy.SetDocNode, path is <<{0}>>", _docNodePath);
#endif

			InternalCheckAbsolutePath();

			value.TunneledEvent += (_weakDocNodeTunneledEventHandler = new WeakActionHandler<object, object, TunnelingEventArgs>(EhDocNode_TunneledEvent, handler => value.TunneledEvent -= handler));
			value.Changed += (_weakDocNodeChangedHandler = new WeakEventHandler(EhDocNode_Changed, handler => value.Changed -= handler));

			OnAfterSetDocNode();

			EhSelfChanged(new Main.InstanceChangedEventArgs(oldValue, value));

#if DOCNODEPROXY_CONCURRENTDEBUG
			_debug.Enqueue("STOP  SetDocNode");
#endif
		}
Beispiel #45
0
			public string GetNameOfChildObject(IDocumentLeafNode o)
			{
				throw new NotImplementedException();
			}
Beispiel #46
0
 protected ReadableColumnProxy(IDocumentLeafNode column)
     : base(column)
 {
 }