using System; using System.Text; using System.Collections.Generic; namespace DevComponents.AdvTree { /// /// Represents the selected nodes collection. /// public class SelectedNodesCollection : NodeCollection { #region Internal Implementation internal AdvTree TreeSelectionControl = null; internal bool SuspendEvents = false; internal bool SuspendClearEvents = false; /// /// Initializes a new instance of the SelectedNodesCollection class. /// public SelectedNodesCollection() { PassiveCollection = true; } /// /// Adds new object to the collection and provides information about the source of the command /// /// Node to add /// Source action /// public override int Add(Node node, eTreeAction action) { if (this.List.Contains(node)) return -1; if (TreeSelectionControl.MultiSelect) { if (TreeSelectionControl.MultiSelectRule == eMultiSelectRule.SameParent && this.Count>0) { if (this[0].Parent != node.Parent) throw new InvalidOperationException("Node being added does not belong to the same parent as currently selected nodes. See AdvTree.MultiSelectRule property"); } if (!SuspendEvents) { AdvTreeNodeCancelEventArgs cancelArgs = new AdvTreeNodeCancelEventArgs(action, node); TreeSelectionControl.InvokeOnBeforeNodeSelect(cancelArgs); if (cancelArgs.Cancel) return -1; } } return base.Add(node, action); } /// /// Adds an array of objects to the collection. /// /// Array of Node objects. public override void AddRange(Node[] nodes) { this.MultiNodeOperation = true; base.AddRange(nodes); this.MultiNodeOperation = false; if (!SuspendEvents) TreeSelectionControl.InvokeSelectionChanged(EventArgs.Empty); } protected override void OnInsertComplete(int index, object value) { if (TreeSelectionControl.MultiSelect) { Node node = value as Node; node.IsSelected = true; TreeSelectionControl.InvalidateNode(node); if (node.SelectedCell == null) { node.SelectFirstCell(SourceAction); } AdvTreeNodeEventArgs args = new AdvTreeNodeEventArgs(SourceAction, node); TreeSelectionControl.InvokeOnAfterNodeSelect(args); node.InternalSelected(this.SourceAction); if(!_MultiNodeOperation) TreeSelectionControl.InvokeSelectionChanged(EventArgs.Empty); } base.OnInsertComplete(index, value); } protected override void OnRemoveComplete(int index, object value) { if (TreeSelectionControl.MultiSelect) { Node node = value as Node; node.IsSelected = false; TreeSelectionControl.InvalidateNode(node); if (node.SelectedCell != null) node.SelectedCell.SetSelected(false, SourceAction); TreeSelectionControl.InvokeOnAfterNodeDeselect(new AdvTreeNodeEventArgs(this.SourceAction, node)); node.InternalDeselected(this.SourceAction); if (!_MultiNodeOperation) TreeSelectionControl.InvokeSelectionChanged(EventArgs.Empty); } base.OnRemoveComplete(index, value); } private int _NumberOfClearedNodes = 0; protected override void OnClear() { if (TreeSelectionControl.MultiSelect) { _NumberOfClearedNodes = this.List.Count; Node[] list = new Node[_NumberOfClearedNodes]; this.List.CopyTo(list, 0); foreach (Node node in list) { node.IsSelected = false; TreeSelectionControl.InvalidateNode(node); if (node.SelectedCell == null) node.Cells[0].SetSelected(false, SourceAction); _ClearedEventArgsList.Add(new AdvTreeNodeEventArgs(this.SourceAction, node)); // Delay event notification to OnClearComplete so node is not in collection if collection is being tested //TreeSelectionControl.InvokeOnAfterNodeDeselect(new AdvTreeNodeEventArgs(this.SourceAction, node)); node.InternalDeselected(this.SourceAction); } } base.OnClear(); } private List _ClearedEventArgsList = new List(); protected override void OnClearComplete() { if (TreeSelectionControl.MultiSelect) { if (TreeSelectionControl != null && !SuspendClearEvents) { // Invoke nodes deselected foreach (AdvTreeNodeEventArgs advTreeNodeEventArgs in _ClearedEventArgsList) { TreeSelectionControl.InvokeOnAfterNodeDeselect(advTreeNodeEventArgs); } } _ClearedEventArgsList.Clear(); if (!SuspendClearEvents && _NumberOfClearedNodes > 0) TreeSelectionControl.InvokeSelectionChanged(EventArgs.Empty); } base.OnClearComplete(); } private bool _MultiNodeOperation; internal bool MultiNodeOperation { get { return _MultiNodeOperation; } set { _MultiNodeOperation = value; } } #endregion } }