TreeView では、デフォルトのノードの代わりにカスタムノードを作成して表示することができます。カスタムプロパティを追加したり、さまざまなカスタマイズを表示することができます(画像の挿入/拡大縮小/配置、境界線の表示、フォントのスタイルと色のカスタマイズ、サイズの変更など)。TreeView でカスタムノードを設定するには、C1TreeColumn の CustomContentPresenter プロパティを設定します。
次の図に、TreeView のカスタムノードを示します。
TreeView でカスタムノードを作成するには、デフォルトノードをオーバーライドしてカスタムノードに適用されるプロパティとメソッドを定義したカスタムクラスを作成します。カスタムクラスを作成したら、そのインスタンスを初期化し、CustomContentPresenter プロパティを使用してカスタムノードを設定します。
次のコードスニペットは、カスタムクラスを作成し、カスタムノードの主な要素を定義する方法を示します。
Public Class CategoryCustomNode Inherits CustomContentPresenter ' レベル 0 Private _name As TextElement Private _description As TextElement Private _img As ImageElement Private _rw As RowPanel ' レベル 1 Private _product As TextElement Public Sub New() ' レベル 0 ' initテキスト要素 ' name _name = New TextElement() _name.Style = New Style() ' 説明 _description = New TextElement() _description.Style = New Style() _description.Width = 120 ' イメージ要素をを初期化します _img = New ImageElement() _img.Style = New Style() _img.Size = New Size(70, 50) ' テキスト要素のグリッドを初期化します Dim cp = New ColumnPanel() cp.Children.Add(_name) cp.Children.Add(_description) ' イメージのためにパネルを初期化します _rw = New RowPanel() _rw.Children.Add(cp) _rw.Children.Add(_img) _rw.Style = New Style() _rw.Style.VerticalAlignment = Alignment.Center ' レベル 1 _product = New TextElement() _product.Style = New Style() End Sub Public Overrides ReadOnly Property ToolTipText() As String Get Return _name.Text End Get End Property Public Overrides Sub SetStyle(styles As TreeNodeCellStyles) ' レベル 0 ' name _name.Style.Margins = New Thickness(1) _name.Style.Font = New Font("Calibri", 10, FontStyle.Bold) ' 説明 _description.Style.Margins = New Thickness(1) _description.Style.Font = New Font("Calibri", 9, FontStyle.Italic) _description.Style.WordWrap = True ' img _img.Style.ImageScaling = ImageScaling.Scale _img.Style.ImageAlignment = ImageAlignment.CenterCenter ' レベル 1 _product.Style.Font = New Font("Calibri", 10, FontStyle.Bold) _product.Style.Margins = New Thickness(2) _product.Style.HorizontalAlignment = Alignment.Center _product.Style.VerticalAlignment = Alignment.Center End Sub Public Overrides Sub SetValue(value As Object) If Node.level = 0 Then Dim row = DirectCast(Node.GetValue(), DataSet1.CategoriesRow) _name.Text = row.CategoryName _description.Text = row.Description Dim converter = New ImageConverter() If _img.Image IsNot Nothing Then _img.Image.Dispose() _img.Image = Nothing End If _img.Image = DirectCast(converter.ConvertFrom(row.Picture), Image) ' ルートパネルを設定します Child = _rw Else _product.Text = value.ToString() ' ルート要素を設定します Child = _product End If End Sub End Class Public Class ProductCustomNode Inherits CustomContentPresenter ' レベル 0 Private _count As TextElement ' レベル 1 Private _quantityPerUnit As TextElement Private _unitPrice As TextElement Private _unitInStock As TextElement Private _unitsOnOrder As TextElement Private _reorderLevel As TextElement Private _gp As GridPanel Private _eStyle As Style Public Sub New() ' レベル 0 ' カテゴリでのカウント _count = New TextElement() _count.Style = New Style() _count.Style.Margins = New Thickness(2) ' レベル 1 ' ラベルのスタイル Dim lStyle = New Style() lStyle.HorizontalAlignment = Alignment.Far lStyle.Margins = New Thickness(1) lStyle.Font = New Font("Calibri", 9, FontStyle.Regular) ' 要素スタイル _eStyle = New Style() _eStyle.Margins = New Thickness(1) _eStyle.Font = New Font("Calibri", 9, FontStyle.Regular) ' init要素 _quantityPerUnit = New TextElement(_eStyle.Clone()) _unitPrice = New TextElement(_eStyle.Clone()) _unitInStock = New TextElement(_eStyle.Clone()) _unitsOnOrder = New TextElement(_eStyle.Clone()) _reorderLevel = New TextElement(_eStyle.Clone()) ' テキスト要素のグリッドを初期化します _gp = New GridPanel() _gp.Columns.Add() ' ラベル _gp.Columns(0).Width = 100 _gp.Columns.Add() ' テキスト _gp.Columns(1).Width = 120 _gp.Rows.Add() ' ReorderLevel _gp(0, 0).Element = New TextElement(lStyle, "Reorder level:") _gp(0, 1).Element = _reorderLevel _gp.Rows.Add() ' UnitPrice _gp(1, 0).Element = New TextElement(lStyle, "Unit price:") _gp(1, 1).Element = _unitPrice _gp.Rows.Add() ' QuantityPerUnit _gp(2, 0).Element = New TextElement(lStyle, "Quantity per unit:") _gp(2, 1).Element = _quantityPerUnit _gp.Columns.Add() ' ラベル _gp.Columns(2).Width = 100 _gp.Columns.Add() ' テキスト ' UnitsInStock _gp(0, 2).Element = New TextElement(lStyle, "Units in stock:") _gp(0, 3).Element = _unitInStock ' UnitsOnOrder _gp(1, 2).Element = New TextElement(lStyle, "Units on order:") _gp(1, 3).Element = _unitsOnOrder End Sub Public Overrides ReadOnly Property ToolTipText() As String Get Return String.Empty End Get End Property Public Overrides Sub SetStyle(styles As TreeNodeCellStyles) ' レベル 0 _count.Style.HorizontalAlignment = Alignment.Center _count.Style.VerticalAlignment = Alignment.Center _count.Style.Font = New Font("Calibri", 11, FontStyle.Bold) ' レベル 1 _unitPrice.Style.Font = New Font(_eStyle.Font, FontStyle.Bold) If _unitInStock.Text = "0" Then _unitInStock.Style.ForeColor = Color.Red _unitInStock.Style.Font = New Font(_eStyle.Font, FontStyle.Bold) End If If _unitsOnOrder.Text = "0" Then _unitsOnOrder.Style.ForeColor = Color.Red _unitsOnOrder.Style.Font = New Font(_eStyle.Font, FontStyle.Bold) End If End Sub Public Overrides Sub SetValue(value As Object) If Node.level = 0 Then Dim count = If(Node.HasChildren, Node.Nodes.Count, 0) _count.Text = count.ToString() Child = _count Else Dim row = DirectCast(Node.GetValue(), DataSet1.ProductsRow) _quantityPerUnit.Text = row.QuantityPerUnit _unitPrice.Text = row.UnitPrice.ToString("C") _unitInStock.Text = row.UnitsInStock.ToString() _unitsOnOrder.Text = row.UnitsOnOrder.ToString() _reorderLevel.Text = row.ReorderLevel.ToString() Child = _gp End If End Sub End Class
public class CategoryCustomNode : CustomContentPresenter { // レベル 0 private TextElement _name; private TextElement _description; private ImageElement _img; private RowPanel _rw; // レベル 1 private TextElement _product; public CategoryCustomNode() { // レベル 0 // initテキスト要素 // name _name = new TextElement(); _name.Style = new Style(); // 説明 _description = new TextElement(); _description.Style = new Style(); _description.Width = 120; // イメージ要素をを初期化します。 _img = new ImageElement(); _img.Style = new Style(); _img.Size = new Size(70, 50); // テキスト要素のグリッドを初期化します。 var cp = new ColumnPanel(); cp.Children.Add(_name); cp.Children.Add(_description); // イメージのためにパネルを初期化します。 _rw = new RowPanel(); _rw.Children.Add(cp); _rw.Children.Add(_img); _rw.Style = new Style(); _rw.Style.VerticalAlignment = Alignment.Center; // レベル 1 _product = new TextElement(); _product.Style = new Style(); } public override string ToolTipText { get { return _name.Text; } } public override void SetStyle(TreeNodeCellStyles styles) { // レベル 0 // name _name.Style.Margins = new Thickness(1); _name.Style.Font = new Font("Calibri", 10, FontStyle.Bold); // 説明 _description.Style.Margins = new Thickness(1); _description.Style.Font = new Font("Calibri", 9, FontStyle.Italic); _description.Style.WordWrap = true; // img _img.Style.ImageScaling = ImageScaling.Scale; _img.Style.ImageAlignment = ImageAlignment.CenterCenter; // レベル 1 _product.Style.Font = new Font("Calibri", 10, FontStyle.Bold); _product.Style.Margins = new Thickness(2); _product.Style.HorizontalAlignment = Alignment.Center; _product.Style.VerticalAlignment = Alignment.Center; } public override void SetValue(object value) { if (Node.Level == 0) { var row = (DataSet1.CategoriesRow)Node.GetValue(); _name.Text = row.CategoryName; _description.Text = row.Description; var converter = new ImageConverter(); if (_img.Image != null) { _img.Image.Dispose(); _img.Image = null; } _img.Image = (Image)converter.ConvertFrom(row.Picture); // ルートパネルを設定します。 Child = _rw; } else { _product.Text = value.ToString(); // ルート要素を設定します。 Child = _product; } } } public class ProductCustomNode : CustomContentPresenter { // レベル 0 private TextElement _count; // レベル 1 private TextElement _quantityPerUnit; private TextElement _unitPrice; private TextElement _unitInStock; private TextElement _unitsOnOrder; private TextElement _reorderLevel; private GridPanel _gp; private Style _eStyle; public ProductCustomNode() { // レベル0 // カテゴリでのカウント _count = new TextElement(); _count.Style = new Style(); _count.Style.Margins = new Thickness(2); // レベル01 // ラベルのスタイル var lStyle = new Style(); lStyle.HorizontalAlignment = Alignment.Far; lStyle.Margins = new Thickness(1); lStyle.Font = new Font("Calibri", 9, FontStyle.Regular); // 要素スタイル _eStyle = new Style(); _eStyle.Margins = new Thickness(1); _eStyle.Font = new Font("Calibri", 9, FontStyle.Regular); // init要素 _quantityPerUnit = new TextElement(_eStyle.Clone()); _unitPrice = new TextElement(_eStyle.Clone()); _unitInStock = new TextElement(_eStyle.Clone()); _unitsOnOrder = new TextElement(_eStyle.Clone()); _reorderLevel = new TextElement(_eStyle.Clone()); // テキスト要素のグリッドを初期化します。 _gp = new GridPanel(); _gp.Columns.Add(); // ラベル _gp.Columns[0].Width = 100; _gp.Columns.Add(); // テキスト _gp.Columns[1].Width = 120; _gp.Rows.Add(); // ReorderLevel _gp[0, 0].Element = new TextElement(lStyle, "Reorder level:"); _gp[0, 1].Element = _reorderLevel; _gp.Rows.Add(); // UnitPrice _gp[1, 0].Element = new TextElement(lStyle, "Unit price:"); _gp[1, 1].Element = _unitPrice; _gp.Rows.Add(); // QuantityPerUnit _gp[2, 0].Element = new TextElement(lStyle, "Quantity per unit:"); _gp[2, 1].Element = _quantityPerUnit; _gp.Columns.Add(); // ラベル _gp.Columns[2].Width = 100; _gp.Columns.Add(); // テキスト // UnitsInStock _gp[0, 2].Element = new TextElement(lStyle, "Units in stock:"); _gp[0, 3].Element = _unitInStock; // UnitsOnOrder _gp[1, 2].Element = new TextElement(lStyle, "Units on order:"); _gp[1, 3].Element = _unitsOnOrder; } public override string ToolTipText { get { return string.Empty; ; } } public override void SetStyle(TreeNodeCellStyles styles) { // レベル 0 _count.Style.HorizontalAlignment = Alignment.Center; _count.Style.VerticalAlignment = Alignment.Center; _count.Style.Font = new Font("Calibri", 11, FontStyle.Bold); // レベル 1 _unitPrice.Style.Font = new Font(_eStyle.Font, FontStyle.Bold); if (_unitInStock.Text == "0") { _unitInStock.Style.ForeColor = Color.Red; _unitInStock.Style.Font = new Font(_eStyle.Font, FontStyle.Bold); } if (_unitsOnOrder.Text == "0") { _unitsOnOrder.Style.ForeColor = Color.Red; _unitsOnOrder.Style.Font = new Font(_eStyle.Font, FontStyle.Bold); } } public override void SetValue(object value) { if (Node.Level == 0) { var count = Node.HasChildren ? Node.Nodes.Count : 0; _count.Text = count.ToString(); Child = _count; } else { var row = (DataSet1.ProductsRow)Node.GetValue(); _quantityPerUnit.Text = row.QuantityPerUnit; _unitPrice.Text = row.UnitPrice.ToString("C"); _unitInStock.Text = row.UnitsInStock.ToString(); _unitsOnOrder.Text = row.UnitsOnOrder.ToString(); _reorderLevel.Text = row.ReorderLevel.ToString(); Child = _gp; } } }
次のコードスニペットは、CustomContentPresenter プロパティを使用してカスタムノードを設定する方法を示します。
' カスタムノードを設定します C1TreeView1.Columns(0).CustomContentPresenter = New CategoryCustomNode() C1TreeView1.Columns(1).CustomContentPresenter = New ProductCustomNode()
// カスタムノードを設定します。 c1TreeView1.Columns[0].CustomContentPresenter = new CategoryCustomNode(); c1TreeView1.Columns[1].CustomContentPresenter = new ProductCustomNode();