У меня возникли проблемы со стандартным Windows Forms TreeView; в частности, с цветом, с которым элемент управления по умолчанию использовался для рендеринга выбранного узла, когда древовидный вид не имел фокуса. Это был светло-серый цвет, который на некоторых экранах был почти невидимым. Впоследствии я подклассифицировал TreeView и переопределил событие TreeView OnDrawNode
, чтобы покрасить мои узлы по своему желанию. Это работает хорошо, но теперь «HotTracking» (активное выделение, когда мышь находится над данным узлом дерева) перегружается моим пользовательским событием OnDrawNode
. Я не очень хорошо знаком с классами Graphics
и задался вопросом, как я могу изменить текущий подкласс, включив в него горячее отслеживание? Я знаю, что могу использовать e.Graphics.DrawLine(Pen pen, Point p1, Point p2);
, но это будет беспорядочно, есть ли более простой способ?Правильное отображение переопределенного TreeView
Вот существующий код:
class CustomTreeView : TreeView
{
public CustomTreeView()
{
this.DrawMode = TreeViewDrawMode.OwnerDrawText;
}
// Override the drawMode of TreeView.
protected override void OnDrawNode(DrawTreeNodeEventArgs e)
{
TreeNodeStates treeState = e.State;
Font treeFont = e.Node.NodeFont ?? e.Node.TreeView.Font;
// Colors.
Color foreColor = e.Node.ForeColor;
string strDeselectedColor = @"#6B6E77", strSelectedColor = @"#94C7FC"; //@"#1ABEE8"; //@"#2FC0EE"; //@"#3A8FEA";
Color selectedColor = System.Drawing.ColorTranslator.FromHtml(strSelectedColor);
Color deselectedColor = System.Drawing.ColorTranslator.FromHtml(strDeselectedColor);
// New brush.
SolidBrush selectedTreeBrush = new SolidBrush(selectedColor);
SolidBrush deselectedTreeBrush = new SolidBrush(deselectedColor);
// Set default font color.
if (foreColor == Color.Empty)
foreColor = e.Node.TreeView.ForeColor;
// Draw bounding box and fill.
if (e.Node == e.Node.TreeView.SelectedNode)
{
// Use appropriate brush depending on if the tree has focus.
if (this.Focused)
{
foreColor = SystemColors.HighlightText;
e.Graphics.FillRectangle(selectedTreeBrush /*SystemBrushes.Highlight*/, e.Bounds);
ControlPaint.DrawFocusRectangle(e.Graphics, e.Bounds, foreColor, SystemColors.Highlight);
TextRenderer.DrawText(e.Graphics, e.Node.Text, treeFont, e.Bounds, foreColor, TextFormatFlags.GlyphOverhangPadding);
}
else
{
foreColor = SystemColors.HighlightText;
e.Graphics.FillRectangle(deselectedTreeBrush /*SystemBrushes.Highlight*/, e.Bounds);
ControlPaint.DrawFocusRectangle(e.Graphics, e.Bounds, foreColor, SystemColors.Highlight);
TextRenderer.DrawText(e.Graphics, e.Node.Text, treeFont, e.Bounds, foreColor, TextFormatFlags.GlyphOverhangPadding);
}
}
else
{
// This is firing but is being over written, perhaps by the above?
if ((e.State & TreeNodeStates.Hot) == TreeNodeStates.Hot)
{
e.DrawDefault = true;
e.Graphics.FillRectangle(SystemBrushes.Window, e.Bounds);
TextRenderer.DrawText(e.Graphics, e.Node.Text, treeFont, e.Bounds, System.Drawing.Color.Blue, TextFormatFlags.GlyphOverhangPadding);
}
else
{
e.Graphics.FillRectangle(SystemBrushes.Window, e.Bounds);
TextRenderer.DrawText(e.Graphics, e.Node.Text, treeFont, e.Bounds, foreColor, TextFormatFlags.GlyphOverhangPadding);
}
}
}
Как всегда, ребята, большое спасибо за ваше время.
* «Это был светло-серый цвет, который на некоторых экранах был почти невидим». * Так что компьютер этого человека в основном непригодный для использования, не так ли? Поскольку Windows использует тот же самый неактивный цвет подсветки во всей системе и во всех других приложениях. Надеюсь, это киоск-машина, которая запускает * только * ваше приложение, иначе бесполезно его менять. И я не рекомендую менять его в любом случае, потому что, как вы заметили, рисунок владельца делает все намного сложнее. В этом случае вам нужно будет добавить код к методам обработчика событий мыши, чтобы самому выполнить горячее отслеживание. Это не будет автоматически. –
Почему это 'тщетно', чтобы изменить его? На белом фоне этот неактивный цвет подсветки очень слабый серый, и в некоторых случаях это не легко увидеть (например, проблема, которую я описываю для treeView выше). Обработчик событий мыши («MouseMove» или какое-то подобное событие), который имеет дело с «HotTracking», скорее всего, будет вызывать событие OnDrawNode для рендеринга узлов - вопрос все еще стоит. Как лучше всего реализовать функциональность «HotTracking». Спасибо за ваше время ... – MoonKnight