External/Aga.Controls/Tree/TreeModel.cs
author sl
Thu, 01 Jan 2015 23:35:49 +0100
changeset 405 5715aefd2bcc
permissions -rw-r--r--
SharpDisplay: Migrating to new robust client scheme.
     1 using System;
     2 using System.Collections.Generic;
     3 using System.Text;
     4 using System.Collections.ObjectModel;
     5 
     6 namespace Aga.Controls.Tree
     7 {
     8 	/// <summary>
     9 	/// Provides a simple ready to use implementation of <see cref="ITreeModel"/>. Warning: this class is not optimized 
    10 	/// to work with big amount of data. In this case create you own implementation of <c>ITreeModel</c>, and pay attention
    11 	/// on GetChildren and IsLeaf methods.
    12 	/// </summary>
    13 	public class TreeModel : ITreeModel
    14 	{
    15 		private Node _root;
    16 		public Node Root
    17 		{
    18 			get { return _root; }
    19 		}
    20 
    21 		public Collection<Node> Nodes
    22 		{
    23 			get { return _root.Nodes; }
    24 		}
    25 
    26 		public TreeModel()
    27 		{
    28 			_root = new Node();
    29 			_root.Model = this;
    30 		}
    31 
    32 		public TreePath GetPath(Node node)
    33 		{
    34 			if (node == _root)
    35 				return TreePath.Empty;
    36 			else
    37 			{
    38 				Stack<object> stack = new Stack<object>();
    39 				while (node != _root)
    40 				{
    41 					stack.Push(node);
    42 					node = node.Parent;
    43 				}
    44 				return new TreePath(stack.ToArray());
    45 			}
    46 		}
    47 
    48 		public Node FindNode(TreePath path)
    49 		{
    50 			if (path.IsEmpty())
    51 				return _root;
    52 			else
    53 				return FindNode(_root, path, 0);
    54 		}
    55 
    56 		private Node FindNode(Node root, TreePath path, int level)
    57 		{
    58 			foreach (Node node in root.Nodes)
    59 				if (node == path.FullPath[level])
    60 				{
    61 					if (level == path.FullPath.Length - 1)
    62 						return node;
    63 					else
    64 						return FindNode(node, path, level + 1);
    65 				}
    66 			return null;
    67 		}
    68 
    69 		#region ITreeModel Members
    70 
    71 		public System.Collections.IEnumerable GetChildren(TreePath treePath)
    72 		{
    73 			Node node = FindNode(treePath);
    74 			if (node != null)
    75 				foreach (Node n in node.Nodes)
    76 					yield return n;
    77 			else
    78 				yield break;
    79 		}
    80 
    81 		public bool IsLeaf(TreePath treePath)
    82 		{
    83 			Node node = FindNode(treePath);
    84 			if (node != null)
    85 				return node.IsLeaf;
    86 			else
    87 				throw new ArgumentException("treePath");
    88 		}
    89 
    90 		public event EventHandler<TreeModelEventArgs> NodesChanged;
    91 		internal void OnNodesChanged(TreeModelEventArgs args)
    92 		{
    93 			if (NodesChanged != null)
    94 				NodesChanged(this, args);
    95 		}
    96 
    97 		public event EventHandler<TreePathEventArgs> StructureChanged;
    98 		public void OnStructureChanged(TreePathEventArgs args)
    99 		{
   100 			if (StructureChanged != null)
   101 				StructureChanged(this, args);
   102 		}
   103 
   104 		public event EventHandler<TreeModelEventArgs> NodesInserted;
   105 		internal void OnNodeInserted(Node parent, int index, Node node)
   106 		{
   107 			if (NodesInserted != null)
   108 			{
   109 				TreeModelEventArgs args = new TreeModelEventArgs(GetPath(parent), new int[] { index }, new object[] { node });
   110 				NodesInserted(this, args);
   111 			}
   112 
   113 		}
   114 
   115 		public event EventHandler<TreeModelEventArgs> NodesRemoved;
   116 		internal void OnNodeRemoved(Node parent, int index, Node node)
   117 		{
   118 			if (NodesRemoved != null)
   119 			{
   120 				TreeModelEventArgs args = new TreeModelEventArgs(GetPath(parent), new int[] { index }, new object[] { node });
   121 				NodesRemoved(this, args);
   122 			}
   123 		}
   124 
   125 		#endregion
   126 	}
   127 }