Free cookie consent management tool by TermsFeed Policy Generator

source: trunk/sources/HeuristicLab.Core.Views/3.3/ScopeView.cs @ 3557

Last change on this file since 3557 was 3528, checked in by swagner, 14 years ago

Implemented reviewers' comments (#893)

File size: 11.9 KB
Line 
1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2010 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
4 *
5 * This file is part of HeuristicLab.
6 *
7 * HeuristicLab is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * HeuristicLab is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
19 */
20#endregion
21
22using System;
23using System.Collections.Generic;
24using System.Windows.Forms;
25using HeuristicLab.Collections;
26using HeuristicLab.MainForm;
27
28namespace HeuristicLab.Core.Views {
29  /// <summary>
30  /// The visual represenation of <see cref="Scope"/>.
31  /// </summary>
32  [View("Scope View")]
33  [Content(typeof(Scope), true)]
34  [Content(typeof(IScope), false)]
35  public sealed partial class ScopeView : ItemView {
36    private Dictionary<IScope, TreeNode> scopeNodeTable;
37    private Dictionary<ScopeList, IScope> subScopesScopeTable;
38
39    /// <summary>
40    /// Gets or sets the scope to represent visually.
41    /// </summary>
42    /// <remarks>Uses property <see cref="ViewBase.Item"/> of base class <see cref="ViewBase"/>.
43    /// No own data storage present.</remarks>
44    public new IScope Content {
45      get { return (IScope)base.Content; }
46      set { base.Content = value; }
47    }
48
49    /// <summary>
50    /// Initializes a new instance of <see cref="ScopeView"/> with caption "Scope" and
51    /// property <see cref="AutomaticUpdating"/> set to <c>false</c>.
52    /// </summary>
53    public ScopeView() {
54      InitializeComponent();
55      Caption = "Scope";
56      scopeNodeTable = new Dictionary<IScope, TreeNode>();
57      subScopesScopeTable = new Dictionary<ScopeList, IScope>();
58
59    }
60    /// <summary>
61    /// Initializes a new instance of <see cref="ScopeView"/> with the given <paramref name="scope"/>.
62    /// </summary>
63    /// <remarks>Calls <see cref="ScopeView()"/>.</remarks>
64    /// <param name="scope">The scope to represent visually.</param>
65    public ScopeView(IScope content)
66      : this() {
67      Content = content;
68    }
69
70    /// <summary>
71    /// Updates all controls with the latest data of the model.
72    /// </summary>
73    /// <remarks>Calls <see cref="ViewBase.UpdateControls"/> of base class <see cref="ViewBase"/>.</remarks>
74    protected override void OnContentChanged() {
75      base.OnContentChanged();
76      if (scopesTreeView.Nodes.Count > 0)
77        ClearTreeNode(scopesTreeView.Nodes[0]);
78      scopesTreeView.Nodes.Clear();
79      variableCollectionView.Content = null;
80      Caption = "Scope";
81      if (Content != null) {
82        Caption = Content.Name + " (" + Content.ItemName + ")";
83        scopesTreeView.Nodes.Add(CreateTreeNode(Content));
84      }
85      SetEnabledStateOfControls();
86    }
87
88    protected override void OnReadOnlyChanged() {
89      base.OnReadOnlyChanged();
90      SetEnabledStateOfControls();
91    }
92
93    private void SetEnabledStateOfControls() {
94      scopesTreeView.Enabled = Content != null;
95      variableCollectionView.Enabled = Content != null;
96    }
97
98    #region TreeNode Management
99    private TreeNode CreateTreeNode(IScope scope) {
100      TreeNode node = new TreeNode();
101      node.Text = scope.Name;
102      node.Tag = scope;
103
104      scopeNodeTable.Add(scope, node);
105      scope.NameChanged += new EventHandler(Scope_NameChanged);
106      subScopesScopeTable.Add(scope.SubScopes, scope);
107      scope.SubScopes.ItemsAdded += new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsAdded);
108      scope.SubScopes.ItemsRemoved += new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsRemoved);
109      scope.SubScopes.ItemsReplaced += new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsReplaced);
110      scope.SubScopes.ItemsMoved += new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsMoved);
111      scope.SubScopes.CollectionReset += new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_CollectionReset);
112      if (scope.SubScopes.Count > 0)
113        node.Nodes.Add(new TreeNode());
114      return node;
115    }
116
117    private void ClearTreeNode(TreeNode node) {
118      if (scopesTreeView.SelectedNode == node) {
119        scopesTreeView.SelectedNode = null;
120        UpdateVariables();
121      }
122
123      foreach (TreeNode child in node.Nodes)
124        ClearTreeNode(child);
125
126      IScope scope = node.Tag as IScope;
127      if (scope != null) {
128        scope.NameChanged -= new EventHandler(Scope_NameChanged);
129        scopeNodeTable.Remove(scope);
130        scope.SubScopes.ItemsAdded -= new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsAdded);
131        scope.SubScopes.ItemsRemoved -= new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsRemoved);
132        scope.SubScopes.ItemsReplaced -= new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsReplaced);
133        scope.SubScopes.ItemsMoved -= new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsMoved);
134        scope.SubScopes.CollectionReset -= new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_CollectionReset);
135        subScopesScopeTable.Remove(scope.SubScopes);
136      }
137    }
138    #endregion
139
140    #region TreeView Events
141    private void scopesTreeView_AfterSelect(object sender, TreeViewEventArgs e) {
142      UpdateVariables();
143    }
144    private void scopesTreeView_MouseDown(object sender, MouseEventArgs e) {
145      TreeNode node = scopesTreeView.GetNodeAt(e.X, e.Y);
146      scopesTreeView.SelectedNode = node;
147      UpdateVariables();
148    }
149    private void scopesTreeView_BeforeExpand(object sender, TreeViewCancelEventArgs e) {
150      TreeNode node = e.Node;
151      IScope scope = (IScope)node.Tag;
152
153      node.Nodes.Clear();
154      for (int i = 0; i < scope.SubScopes.Count; i++)
155        node.Nodes.Add(CreateTreeNode(scope.SubScopes[i]));
156    }
157    private void scopesTreeView_AfterCollapse(object sender, System.Windows.Forms.TreeViewEventArgs e) {
158      TreeNode node = e.Node;
159      IScope scope = (IScope)node.Tag;
160
161      if (node.Nodes.Count > 0) {
162        for (int i = 0; i < node.Nodes.Count; i++)
163          ClearTreeNode(node.Nodes[i]);
164        node.Nodes.Clear();
165        node.Nodes.Add(new TreeNode());
166      }
167    }
168    private void scopesTreeView_ItemDrag(object sender, ItemDragEventArgs e) {
169      if (!Locked) {
170        TreeNode node = (TreeNode)e.Item;
171        IScope scope = node.Tag as IScope;
172        if (scope != null) {
173          DataObject data = new DataObject();
174          data.SetData("Type", scope.GetType());
175          data.SetData("Value", scope);
176          DoDragDrop(data, DragDropEffects.Copy | DragDropEffects.Link);
177        }
178      }
179    }
180    #endregion
181
182    #region Content Events
183    private void Scope_NameChanged(object sender, EventArgs e) {
184      if (InvokeRequired)
185        Invoke(new EventHandler(Scope_NameChanged), sender, e);
186      else {
187        IScope scope = (IScope)sender;
188        scopeNodeTable[scope].Text = scope.Name;
189      }
190    }
191    private void SubScopes_ItemsAdded(object sender, CollectionItemsChangedEventArgs<IndexedItem<IScope>> e) {
192      if (InvokeRequired)
193        Invoke(new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsAdded), sender, e);
194      else {
195        IScope parentScope = subScopesScopeTable[(ScopeList)sender];
196        TreeNode parentNode = scopeNodeTable[parentScope];
197        scopesTreeView.BeginUpdate();
198        if (parentNode.IsExpanded) {
199          foreach (IndexedItem<IScope> item in e.Items) {
200            TreeNode node = CreateTreeNode(item.Value);
201            parentNode.Nodes.Insert(item.Index, node);
202          }
203        } else if (parentNode.Nodes.Count == 0) {
204          parentNode.Nodes.Add(new TreeNode());
205        }
206        scopesTreeView.EndUpdate();
207      }
208    }
209    private void SubScopes_ItemsRemoved(object sender, CollectionItemsChangedEventArgs<IndexedItem<IScope>> e) {
210      if (InvokeRequired)
211        Invoke(new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsRemoved), sender, e);
212      else {
213        IScope parentScope = subScopesScopeTable[(ScopeList)sender];
214        TreeNode parentNode = scopeNodeTable[parentScope];
215        scopesTreeView.BeginUpdate();
216        if (parentNode.IsExpanded) {
217          foreach (IndexedItem<IScope> item in e.Items) {
218            TreeNode node = scopeNodeTable[item.Value];
219            ClearTreeNode(node);
220            node.Remove();
221          }
222        } else if (parentScope.SubScopes.Count == 0) {
223          parentNode.Nodes.Clear();
224        }
225        scopesTreeView.EndUpdate();
226      }
227    }
228    private void SubScopes_ItemsReplaced(object sender, CollectionItemsChangedEventArgs<IndexedItem<IScope>> e) {
229      if (InvokeRequired)
230        Invoke(new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsReplaced), sender, e);
231      else {
232        IScope parentScope = subScopesScopeTable[(ScopeList)sender];
233        TreeNode parentNode = scopeNodeTable[parentScope];
234        scopesTreeView.BeginUpdate();
235        if (parentNode.IsExpanded) {
236          foreach (IndexedItem<IScope> item in e.Items) {
237            TreeNode node = parentNode.Nodes[item.Index];
238            ClearTreeNode(node);
239            node.Remove();
240            node = CreateTreeNode(item.Value);
241            parentNode.Nodes.Insert(item.Index, node);
242          }
243          scopesTreeView.EndUpdate();
244        }
245      }
246    }
247    private void SubScopes_ItemsMoved(object sender, CollectionItemsChangedEventArgs<IndexedItem<IScope>> e) {
248      if (InvokeRequired)
249        Invoke(new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_ItemsMoved), sender, e);
250      else {
251        IScope parentScope = subScopesScopeTable[(ScopeList)sender];
252        TreeNode parentNode = scopeNodeTable[parentScope];
253        scopesTreeView.BeginUpdate();
254        if (parentNode.IsExpanded) {
255          parentNode.Nodes.Clear();
256          foreach (IndexedItem<IScope> item in e.Items)
257            parentNode.Nodes.Insert(item.Index, scopeNodeTable[item.Value]);
258        }
259        scopesTreeView.EndUpdate();
260      }
261    }
262    private void SubScopes_CollectionReset(object sender, CollectionItemsChangedEventArgs<IndexedItem<IScope>> e) {
263      if (InvokeRequired)
264        Invoke(new CollectionItemsChangedEventHandler<IndexedItem<IScope>>(SubScopes_CollectionReset), sender, e);
265      else {
266        IScope parentScope = subScopesScopeTable[(ScopeList)sender];
267        TreeNode parentNode = scopeNodeTable[parentScope];
268        scopesTreeView.BeginUpdate();
269        if (parentNode.IsExpanded) {
270          foreach (TreeNode node in parentNode.Nodes)
271            ClearTreeNode(node);
272          parentNode.Nodes.Clear();
273          foreach (IndexedItem<IScope> item in e.Items) {
274            TreeNode node = CreateTreeNode(item.Value);
275            parentNode.Nodes.Insert(item.Index, node);
276          }
277        } else {
278          parentNode.Nodes.Clear();
279          if (parentScope.SubScopes.Count > 0)
280            parentNode.Nodes.Add(new TreeNode());
281        }
282        scopesTreeView.EndUpdate();
283      }
284    }
285    #endregion
286
287    #region Helpers
288    private void UpdateVariables() {
289      if (scopesTreeView.SelectedNode == null) {
290        variableCollectionView.Content = null;
291        variableCollectionView.Enabled = false;
292      } else {
293        variableCollectionView.Enabled = true;
294        variableCollectionView.Content = ((IScope)scopesTreeView.SelectedNode.Tag).Variables;
295      }
296    }
297    #endregion
298  }
299}
Note: See TracBrowser for help on using the repository browser.