2 using System
.Collections
;
4 using System
.Windows
.Forms
;
9 public class MultiselectTreeview
: TreeView
11 protected ArrayList m_coll
;
12 protected TreeNode m_firstNode
;
14 public ArrayList SelectedNodes
22 removePaintFromNodes();
29 protected override void OnAfterSelect(TreeViewEventArgs e
)
31 // e.Node is the current node exposed by the base TreeView control
33 base.OnAfterSelect(e
);
34 removePaintFromNodes();
36 bool bControl
= (ModifierKeys
== Keys
.Control
);
37 bool bShift
= (ModifierKeys
== Keys
.Shift
);
41 if (!m_coll
.Contains(e
.Node
)) // new node ?
45 else // not new, remove it from the collection
47 m_coll
.Remove(e
.Node
);
54 Queue myQueue = new Queue();
56 TreeNode uppernode = m_firstNode;
57 TreeNode bottomnode = e.Node;
59 // case 1 : begin and end nodes are parent
60 bool bParent = isParent(m_firstNode, e.Node);
63 bParent = isParent(bottomnode, uppernode);
64 if (bParent) // swap nodes
66 TreeNode t = uppernode;
67 uppernode = bottomnode;
73 TreeNode n = bottomnode;
74 while (n != uppernode.Parent)
76 if (!m_coll.Contains(n)) // new node ?
82 // case 2 : nor the begin nor the
83 // end node are descendant one another
86 // are they siblings ?
88 if ((uppernode.Parent == null && bottomnode.Parent == null)
89 || (uppernode.Parent != null &&
90 uppernode.Parent.Nodes.Contains(bottomnode)))
92 int nIndexUpper = uppernode.Index;
93 int nIndexBottom = bottomnode.Index;
94 if (nIndexBottom < nIndexUpper) // reversed?
96 TreeNode t = uppernode;
97 uppernode = bottomnode;
99 nIndexUpper = uppernode.Index;
100 nIndexBottom = bottomnode.Index;
103 TreeNode n = uppernode;
104 while (nIndexUpper <= nIndexBottom)
106 if (!m_coll.Contains(n)) // new node ?
117 if (!m_coll.Contains(uppernode))
118 myQueue.Enqueue(uppernode);
119 if (!m_coll.Contains(bottomnode))
120 myQueue.Enqueue(bottomnode);
125 m_coll.AddRange(myQueue);
127 paintSelectedNodes();
128 // let us chain several SHIFTs if we like it
129 m_firstNode = e.Node;
134 // in the case of a simple click, just add this item
135 if (m_coll
!= null && m_coll
.Count
> 0)
142 removePaintFromNodes();
145 protected bool isParent(TreeNode parentNode
, TreeNode childNode
)
147 if (parentNode
== childNode
)
150 TreeNode n
= childNode
;
152 while (!bFound
&& n
!= null)
155 bFound
= (n
== parentNode
);
161 protected void paintSelectedNodes()
163 foreach (TreeNode n
in m_coll
)
165 n
.BackColor
= SystemColors
.Highlight
;
166 n
.ForeColor
= SystemColors
.HighlightText
;
170 protected void removePaintFromNodes()
172 if (m_coll
.Count
== 0) return;
174 TreeNode n0
= (TreeNode
)m_coll
[0];
175 Color back
= n0
.TreeView
.BackColor
;
176 Color fore
= n0
.TreeView
.ForeColor
;
178 foreach (TreeNode n
in m_coll
)