private void TreeControl_NodeExpandedChanged(object sender, TreeControl.NodeEventArgs e) { var treeView = TreeView.As <FilteredTreeView>(); // early exit if (m_updating || !m_searching || e.Node.Tag == null || treeView == null) { return; } if (m_toExpand != null) { var node = m_toExpand; m_toExpand = null; try { m_updating = true; TreeControlAdapter.Expand(node.Tag); treeView.RestoreExpansion(e.Node, TreeControlAdapter); } finally { m_updating = false; } } else if (e.Node.Expanded && RestoreSubExpansion) { treeView.RestoreExpansion(e.Node, TreeControlAdapter); } }
/// <summary> /// Draws the category expander icon for the Microsoft Office-like categorized palette</summary> /// <param name="node">The node to draw a category expander icon for</param> /// <param name="g">The current GDI+ graphics object</param> /// <param name="r">The bounds of the category expander icon</param> public virtual void DrawCategory(TreeControl.Node node, Graphics g, Rectangle r) { var color1 = (CategoryStartColor.A == 0) ? ColorUtil.GetShade(Owner.BackColor, 0.97f) : CategoryStartColor; var color2 = (CategoryEndColor.A == 0) ? ColorUtil.GetShade(CategoryStartColor, 0.9f) : CategoryEndColor; using (LinearGradientBrush brush = new LinearGradientBrush(r, color1, color2, LinearGradientMode.Vertical)) { g.FillRectangle(brush, r); } Padding margin = Owner.Margin; int xPadding = margin.Left; int yPadding = margin.Top; GdiUtil.DrawOfficeExpander( r.Width - ExpanderSize.Width - xPadding, r.Y + yPadding, ExpanderPen, !node.Expanded, g); }
/// <summary> /// Measures the dimensions of the label in pixels. Must be in sync with DrawLabel.</summary> /// <param name="node">The tree node whose label is to be measured</param> /// <param name="g">The current GDI+ Graphics object</param> /// <returns>The width and height of a tight rectangle around the label in pixels. The /// TreeControl provides the padding in between items. Technically, the units of measure /// are specified by Graphics.PageUnit.</returns> public override Size MeasureLabel(TreeControl.Node node, Graphics g) { Size result = base.MeasureLabel(node, g); result.Width += node.Label.Length; //throw in an extra pixel per char return(result); }
internal void AddOpaqueNode(TreeControl.Node node) { if (m_opaqueNodes.Contains(node.Tag)) { m_currentOpaqueNodes.Add(node.Tag); } }
/// <summary> /// Draws the check box at the given location and of the size specified by CheckBoxSize</summary> /// <param name="node">The node that the check box is to be drawn for. The HasCheck property /// is assumed to be true.</param> /// <param name="g">The current GDI+ graphics object</param> /// <param name="x">The x-coordinate of the upper-left corner of the check box</param> /// <param name="y">The y-coordinate of the upper-left corner of the check box</param> public virtual void DrawCheckBox(TreeControl.Node node, Graphics g, int x, int y) { Rectangle bounds = new Rectangle(x, y, CheckBoxSize.Width, CheckBoxSize.Height); if (node.CheckState == CheckState.Indeterminate) { // draw indeterminate state. Brush fillBrush = SystemBrushes.Window; Brush fillBrush2 = node.CheckBoxEnabled ? SystemBrushes.ControlText : SystemBrushes.GrayText; Pen borderPen = node.CheckBoxEnabled ? SystemPens.ControlDark : SystemPens.InactiveBorder; var rect = Rectangle.Inflate(bounds, -1, -1); g.FillRectangle(fillBrush, rect); var rect2 = Rectangle.Inflate(bounds, -4, -4); g.FillRectangle(fillBrush2, rect2); g.DrawRectangle(borderPen, rect.X, rect.Y, rect.Width - 1, rect.Height - 1); } else { var buttonState = ButtonState.Flat; if (node.CheckState == CheckState.Checked) { buttonState |= ButtonState.Checked; } if (!node.CheckBoxEnabled) { buttonState |= ButtonState.Inactive; } ControlPaint.DrawCheckBox(g, bounds, buttonState); } }
void NotesPanel_DocumentChanged(object sender, DocumentChangedEventArgs args) { INotableDocument doc = args.New as INotableDocument; if (doc != null) { treeList.Root.Clear(); ICollection <string> notes = doc.Notes; if (notes == null) { return; } foreach (string n in notes) { TreeControl.Node node = treeList.Root.Add(n); if (n.Length > 0) { node.Label = n; } else { node.Label = "<empty note>".Localize(); } node.AllowLabelEdit = true; } } else { treeList.Root.Clear(); } }
internal void RemoveOpaqueNode(TreeControl.Node node) { if (m_opaqueNodes.Contains(node.Tag)) { m_currentOpaqueNodes.Remove(node.Tag); } }
private void selection_Changed(object sender, EventArgs e) { if (!m_synchronizingSelection) { try { m_synchronizingSelection = true; m_treeControl.ClearSelection(); TreeControl.Node lastSelected = null; foreach (Path <object> path in m_selectionContext.GetSelection <Path <object> >()) { // Set the node as selected if the whole path can be found. // Expand as much of 'path' as possible, if m_autoExpand is true. TreeControl.Node node = ExpandPath(path, !m_autoExpand); if (node != null) { lastSelected = node; node.Selected = true; } } if (lastSelected != null) { m_treeControl.EnsureVisible(lastSelected); } } finally { m_synchronizingSelection = false; } } }
void UpdateNode(TreeControl.Node node) { Translators.HierarchyTranslator trans = Translators.HierarchyTranslator.GetTranslator(node.Tag.GetType()); if (trans != null) { node.Clear(); FontStyle fs = node.FontStyle; node.Label = trans.GetLabel(node.Tag, out fs); node.FontStyle = fs; node.ImageIndex = trans.GetImage(node.Tag); object statusTag = trans.GetStatusTag(node.Tag); node.Expanded = expansionStatus.ContainsKey(statusTag) && expansionStatus[statusTag]; List <object> children = trans.GetChildren(node.Tag); if (children != null && children.Count > 0) { node.IsLeaf = false; foreach (object o in children) { Fill(node, o); } } else { node.IsLeaf = true; } } }
private void SetChildren(TreeControl.Node parentNode) { if (m_treeView == null) { return; } if (parentNode.Expanded) { object obj = parentNode.Tag; if (obj != null) { TreeControl.Node node = null; foreach (object child in m_treeView.GetChildren(obj)) { node = parentNode.Add(child); m_itemToNodeMap.Add(child, node); UpdateNode(node); } if (node == null) // no children? { parentNode.IsLeaf = true; } } } else { foreach (TreeControl.Node child in parentNode.Children) { Unbind(child); } parentNode.Clear(); } }
// return true when not all of its children are visble internal bool IsNodeOpaque(TreeControl.Node node) { if (node.Tag == null) { return(false); } return(m_opaqueNodes.Contains(node.Tag)); }
// return true when not all of its children are visble internal bool IsNodeMatched(TreeControl.Node node) { if (node.Tag == null) { return(false); } return(m_visibleNodes.Contains(node.Tag)); }
// return false if the node itself, or any of its children label matches the searching pattern private bool NeedGrayBackground(TreeControl.Node node) { if (string.IsNullOrEmpty(FilteringPattern)) { return(false); } return(FilteringStatus == null || (FilteringStatus(node) & NodeFilteringStatus.Visible) == 0); }
/// <summary> /// Draws the node background at the given location</summary> /// <param name="node">The node to be drawn</param> /// <param name="g">The current GDI+ graphics object</param> /// <param name="x">The x-coordinate of the upper-left corner of the node</param> /// <param name="y">The y-coordinate of the upper-left corner of the node</param> public virtual void DrawBackground(TreeControl.Node node, Graphics g, int x, int y) { if (NeedGrayBackground(node)) { Rectangle bgRect = new Rectangle(Owner.Margin.Left, Owner.Margin.Top + y, Owner.Width - Owner.Margin.Left - Owner.Margin.Right, node.LabelHeight + Owner.Margin.Top + Owner.Margin.Bottom); bgRect.Y -= 3; g.FillRectangle(m_brushNonMatchedBg, bgRect); } }
/// <summary> /// Restores subtree's node expansion states, if remembered</summary> /// <param name="treeControlAdapter">TreeControlAdapter that performs node expansion</param> /// <param name="parent">Node whose subtree's expansion state was remembered</param> public void RestoreExpansion(TreeControlAdapter treeControlAdapter, TreeControl.Node parent) { if (parent.Tag != null && m_expandedItems.ContainsKey(parent.Tag)) { foreach (object item in m_expandedItems[parent.Tag]) { treeControlAdapter.Expand(item); } } }
/// <summary> /// Gets the item under the given point</summary> /// <param name="clientPoint">Point, in client coordinates</param> /// <returns>Item under point, or null if none</returns> public object GetItemAt(Point clientPoint) { TreeControl.Node node = m_treeControl.GetNodeAt(clientPoint); if (node != null) { return(node.Tag); } return(null); }
private IEnumerable <TreeControl.Node> GetSubtree(TreeControl.Node parent) { yield return(parent); foreach (TreeControl.Node child in parent.Children) { foreach (TreeControl.Node decendent in GetSubtree(child)) { yield return(decendent); } } }
private Path <object> MakePath(TreeControl.Node node) { List <object> tags = new List <object>(); for (; node != null; node = node.Parent) { tags.Add(node.Tag); } tags.Reverse(); return(new AdaptablePath <object>(tags)); }
private void Unbind(TreeControl.Node node) { if (node.Tag != null) { m_itemToNodeMap.Remove(node.Tag, node); } foreach (TreeControl.Node child in node.Children) { Unbind(child); } }
/// <summary> /// Draws the text of a tree node's label at the specified location and the same size /// that MeasureLabel() would calculate for this node</summary> /// <param name="node">The tree control's node whose label is to be drawn</param> /// <param name="g">The current GDI+ graphics object</param> /// <param name="x">The x-coordinate of the upper-left corner of the drawn text</param> /// <param name="y">The y-coordinate of the upper-left corner of the drawn text</param> public virtual void DrawLabel(TreeControl.Node node, Graphics g, int x, int y) { Rectangle textRect = new Rectangle(x, y, node.LabelWidth, node.LabelHeight); Brush textBrush = m_textBrush; Font font = GetDefaultFont(node, g); if (!string.IsNullOrEmpty(FilteringPattern)) { // bool matched = false; int regularStart = 0; int matchStart; PointF textLoc = new PointF(textRect.X, textRect.Y); do { // highlight the backdground of matched text matchStart = node.Label.IndexOf(FilteringPattern, regularStart, StringComparison.CurrentCultureIgnoreCase); if (matchStart >= 0) { // matched = true; // non-matched substring string regularString = node.Label.Substring(regularStart, matchStart - regularStart); SizeF regularSize = MeasureDisplayStringWidth(g, regularString, font); textLoc.X += regularSize.Width; regularStart = matchStart + FilteringPattern.Length; // advance string offset // matched substring string matchedString = node.Label.Substring(matchStart, FilteringPattern.Length); SizeF matchedSize = MeasureDisplayStringWidth(g, matchedString, font); RectangleF matchedRect = new RectangleF(textLoc, matchedSize); // offset a couple of pixels to avoid obvious overlap with preceding char matchedRect.X += 2; matchedRect.Width -= 2; g.FillRectangle(m_brushMatchedHighLight, matchedRect); textLoc.X += matchedSize.Width; } } while (matchStart >= 0); } if (node.Selected) { Brush highlightBrush = Owner.ContainsFocus ? HighlightBrush : DeactiveHighlightBrush; Brush highlightTextBrush = Owner.ContainsFocus ? HighlightTextBrush : DeactiveHighlightTextBrush; g.FillRectangle(highlightBrush, textRect); textBrush = highlightTextBrush; } g.DrawString(node.Label, font, textBrush, textRect); }
private void TreeControl_NodeExpandedChanging(object sender, TreeControl.CancelNodeEventArgs e) { var treeView = TreeView.As <FilteredTreeView>(); // early exit if (m_updating || !m_searching || e.Node.Tag == null || treeView == null) { return; } // is the node or any of its decendants passed filter if (treeView.IsMatched(e.Node.Tag)) { if (e.Node.Expanded) { if (!treeView.IsFullyExpaned(e.Node.Tag)) { // add all the children that did not pass // the filtering to the exempted set. treeView.AddToExemptSet(e.Node.Tag); // save e.Node and expand it in NodeExpandedChanged event handler. m_toExpand = e.Node; } if (RestoreSubExpansion) { treeView.SaveExpansion(e.Node); } } // end of if (e.Node.Expanded ) else { // e.Node about to expand. Remove all its children from exempted set. // so normal filtering will be applied. treeView.RemoveFromExemptSet(e.Node.Tag); } }// end of if(treeView.IsMatched(e.Node.Tag)) else { if (e.Node.Expanded) { if (RestoreSubExpansion) { treeView.SaveExpansion(e.Node); } } else { treeView.AddToExemptSet(e.Node.Tag); } } }
/// <summary> /// Makes sure the tree nodes corresponding to the path are visible</summary> /// <param name="path">Path identifying tree nodes</param> /// <param name="select">Whether node should be selected</param> /// <returns>The node specified by the path, or null if it could not be found</returns> public TreeControl.Node Show(Path <object> path, bool select) { TreeControl.Node node = ExpandPath(path, false); if (node != null) { if (select) { node.Selected = true; } m_treeControl.EnsureVisible(node); } return(node); }
/// <summary> /// Draws the node background at the given location</summary> /// <param name="node">The node to be drawn</param> /// <param name="g">The current GDI+ graphics object</param> /// <param name="x">The x-coordinate of the upper-left corner of the node</param> /// <param name="y">The y-coordinate of the upper-left corner of the node</param> public virtual void DrawBackground(TreeControl.Node node, Graphics g, int x, int y) { if (FilteringStatus != null && FilteringPattern != null && FilteringPattern.Count > 0) { if ((FilteringStatus(node) & NodeFilteringStatus.Visible) == 0) { Rectangle bgRect = new Rectangle(Owner.Margin.Left, Owner.Margin.Top + y, Owner.Width - Owner.Margin.Left - Owner.Margin.Right, node.LabelHeight + Owner.Margin.Top + Owner.Margin.Bottom); bgRect.Y -= 3; g.FillRectangle(NoMatchHighlightBrush, bgRect); } } }
internal void RestoreExpansion(TreeControl.Node parent, TreeControlAdapter treeAdapter) { if (parent.Tag == null) { return; } List <object> expandedItems; if (m_expandedNodeMap.TryGetValue(parent.Tag, out expandedItems)) { m_expandedNodeMap.Remove(parent.Tag); expandedItems.ForEach(item => treeAdapter.Expand(item)); } }
/// <summary> /// Draws the text of a tree node's label at the specified location and the same size /// that MeasureLabel() would calculate for this node</summary> /// <param name="node">The tree control's node whose label is to be drawn</param> /// <param name="g">The current GDI+ graphics object</param> /// <param name="x">The x-coordinate of the upper-left corner of the drawn text</param> /// <param name="y">The y-coordinate of the upper-left corner of the drawn text</param> public virtual void DrawLabel(TreeControl.Node node, Graphics g, int x, int y) { Rectangle textRect = new Rectangle(x, y, node.LabelWidth, node.LabelHeight); Brush textBrush = m_textBrush; Font font = GetDefaultFont(node, g); if (FilteringPattern != null && FilteringPattern.Count > 0 && node.Label != null) { int regularStart = 0; int matchStart; PointF textLoc = new PointF(textRect.X, textRect.Y); do { // highlight the background of matched text int patternLength = 0; matchStart = FilteringPattern.IndexOfTag(node.Label, regularStart, out patternLength); if (matchStart >= 0) { // non-matched substring string regularString = node.Label.Substring(regularStart, matchStart - regularStart); SizeF regularSize = MeasureDisplayStringWidth(g, regularString, font); textLoc.X += regularSize.Width; regularStart = matchStart + patternLength; // advance string offset // matched substring string matchedString = node.Label.Substring(matchStart, patternLength); SizeF matchedSize = MeasureDisplayStringWidth(g, matchedString, font); RectangleF matchedRect = new RectangleF(textLoc, matchedSize); // offset a couple of pixels to avoid obvious overlap with preceding char matchedRect.X += 2; matchedRect.Width -= 2; g.FillRectangle(MatchedHighlightBrush, matchedRect); textLoc.X += matchedSize.Width; } } while (matchStart >= 0); } if (node.Selected) { Brush highlightBrush = Owner.ContainsFocus ? HighlightBrush : DeactiveHighlightBrush; Brush highlightTextBrush = Owner.ContainsFocus ? HighlightTextBrush : DeactiveHighlightTextBrush; g.FillRectangle(highlightBrush, textRect); textBrush = highlightTextBrush; } g.DrawString(node.Label, font, textBrush, textRect); }
/// <summary> /// Constructor</summary> /// <param name="settingsService">Settings service</param> /// <param name="dialogOwner">Dialog owner window HWND</param> /// <param name="pathName">Path of settings to display initially, or null</param> public SettingsDialog(SettingsService settingsService, IWin32Window dialogOwner, string pathName) { // // Required for Windows Form Designer support // InitializeComponent(); SplitterRatio = 0.33f; m_settingsService = settingsService; m_dialogOwner = dialogOwner; m_originalState = m_settingsService.UserState; // for cancel m_treeControl = new TreeControl(TreeControl.Style.SimpleTree); m_treeControl.Dock = DockStyle.Fill; m_treeControl.SelectionMode = SelectionMode.One; m_treeControl.ShowRoot = false; m_treeControl.ImageList = ResourceUtil.GetImageList16(); m_treeControl.ExpandAll(); m_treeControl.NodeSelectedChanged += treeControl_NodeSelectedChanged; m_treeControlAdapter = new TreeControlAdapter(m_treeControl); m_treeControlAdapter.TreeView = settingsService.UserSettings; treePanel.Controls.Add(m_treeControl); m_propertyGrid = new Sce.Atf.Controls.PropertyEditing.PropertyGrid(); m_propertyGrid.Dock = DockStyle.Fill; propertiesPanel.Controls.Add(m_propertyGrid); // select an initial node so something is displayed in the PropertyGrid TreeControl.Node firstNode = null; if (pathName != null) { firstNode = m_treeControlAdapter.ExpandPath(m_settingsService.GetSettingsPath(pathName)); } if (firstNode == null) // in case pathName is not null, but ExpandPath returns null { firstNode = m_treeControl.ExpandToFirstLeaf(); } firstNode.Selected = true; ShowProperties(m_settingsService.GetProperties((Tree <object>)firstNode.Tag)); //does auto-setting of column widths defaultsButton.Click += DefaultsButton_Click; }
/// <summary> /// Draws the text of a tree node's label at the specified location and the same size /// that MeasureLabel() would calculate for this node</summary> /// <param name="node">The tree control's node whose label is to be drawn</param> /// <param name="g">The current GDI+ graphics object</param> /// <param name="x">The x-coordinate of the upper-left corner of the drawn text</param> /// <param name="y">The y-coordinate of the upper-left corner of the drawn text</param> public override void DrawLabel(TreeControl.Node node, Graphics g, int x, int y) { RectangleF textRect = new RectangleF(x, y, node.LabelWidth, node.LabelHeight); Brush textBrush; Font font = GetDefaultFont(node, g); if (node.Selected) { Brush highlightBrush = SystemBrushes.Highlight; if (!Owner.ContainsFocus) { highlightBrush = SystemBrushes.ButtonHighlight; } g.FillRectangle(highlightBrush, textRect); } // Compute the rectangles around each character of the label. CharacterRange[] ranges = new CharacterRange[node.Label.Length]; for (int i = 0; i < node.Label.Length; i++) { ranges[i] = new CharacterRange(i, 1); } StringFormat format = new StringFormat(); format.Trimming = StringTrimming.None; format.FormatFlags |= StringFormatFlags.NoClip; format.SetMeasurableCharacterRanges(ranges); Region[] regions = g.MeasureCharacterRanges(node.Label, font, textRect, format); // Draw each character, cycling through the colored pens. int currColorIndex = 0; for (int i = 0; i < node.Label.Length; i++) { RectangleF oneCharRect = regions[i].GetBounds(g); oneCharRect.Width += 1; oneCharRect.X += i; //throw in an extra pixel per char to prevent overlap string oneLetter = new string(node.Label[i], 1); textBrush = s_coloredBrushes[currColorIndex++]; if (currColorIndex == s_coloredBrushes.Length) { currColorIndex = 0; } g.DrawString(oneLetter, font, textBrush, oneCharRect, format); } }
/// <summary> /// Saves subtree's node expansion states and attaches it to the parent node</summary> /// <param name="parent">Node whose expansion state is remembered</param> public void RememberExpansion(TreeControl.Node parent) { if (parent.Tag != null) { var expandedItems = new List <object>(); foreach (TreeControl.Node node in GetSubtree(parent)) { if (node.Expanded) { expandedItems.Add(node.Tag); } } m_expandedItems[parent.Tag] = expandedItems; } }
private void AddPaths(TreeControl.Node node, List <object> path, HashSet <Path <object> > paths) { if (node.Expanded) { path.Add(node.Tag); paths.Add(new AdaptablePath <object>(path)); foreach (TreeControl.Node child in node.Children) { AddPaths(child, path, paths); } path.RemoveAt(path.Count - 1); } }
void Fill(string path, TreeControl.Node current) { try { foreach (string dir in System.IO.Directory.EnumerateDirectories(path)) { TreeControl.Node newNode = current.Add(dir); newNode.Label = System.IO.Path.GetFileName(dir); newNode.IsLeaf = System.IO.Directory.EnumerateDirectories(dir).Count() == 0; newNode.ImageIndex = 0; } } catch (Exception) { } }