【问题标题】:WinForms: Changing ForeColor of Selected item in ListViewWinForms:更改 ListView 中所选项目的前景色
【发布时间】:2018-09-01 03:23:48
【问题描述】:

我将我的 ListView 中所有项目的 ForeColor 设置为不同的颜色,但是当项目被选中时,这个 get 会被覆盖(再次变为黑色;取消选择时变回自定义颜色)。

我希望我的商品保留我的自定义颜色,即使在选择时也是如此。

我基本上问的是 7 年前here 提出的相同问题,但似乎没有任何令人满意的答案。

我尝试在 SO 和其他地方搜索,但没有运气。到目前为止提供的唯一解决方案是绘制整个东西(DrawItem 方法),我尝试过,但对于这样一个小要求来说太复杂了......

这是唯一的方法吗?说不是这样。

【问题讨论】:

  • 由于您的要求 even in selection 您将需要执行自定义 DrawItem 方法。原因是在绘制突出显示的项目时覆盖 Highlight ForeColor 属性。抱歉,我知道没有办法解决
  • 其实没那么复杂。您可以使用默认的绘图程序。 LV 在什么视图模式下?另外:用户希望所有选择都以系统颜色突出显示。
  • Say it ain't so.原来如此。
  • using (SolidBrush br = new SolidBrush(e.Item.ForeColor)) if (e.Item.Selected) e.Graphics.DrawString(e.Item.Text, e.Item.Font, br, e.Bounds.X + 4, e.Bounds.Y); else e.DrawText(); - 要突出选择,您可以使用粗体字..
  • 两行代码。四、如果在Selected上更改ForeColor/BackColor。但是,为了适应我的ListView 中的所有项目都有不同的颜色 背后的逻辑,可能会有一些开销。但是,如果这个逻辑是预定义的,那么开销是非常低的。

标签: c# winforms listview


【解决方案1】:

启用您的 ListView OwnerDraw 模式,然后订阅其 DrawItemDrawColumnHeader 事件。
如果您的设计需要,也可以订阅DrawSubitem 活动。

此时,您可以在 ListView 的相关区域中绘制任何内容。

在示例中,我在页眉区域绘制了一个小符号。
标题文本也需要绘制。

如果背景颜色没有变化(和设计模式一样),你只需要使用DrawListViewItemEventArgs e参数函数e.DrawBackground();

如果不是,请使用e.Graphics.FillRectangle() 为由e.Bounds 定义的项目区域着色。

项目文本是使用e.Graphics.DrawString()绘制的。
项目文本为e.Item.Text文本区域再次由e.Bounds定义。
如果您不需要项目文本的任何特定细节/设置,您可以简单地使用 e.DrawText();,它使用 默认属性(在设计时定义) .

这里,项目颜色复杂的逻辑是在项目文本内部指定颜色。可以是别的什么。项目标签,它的索引位置,List<Parameters>,你可以命名它。

这可能是这样的:
(我添加了e.Graphics.TextRenderingHint = [] 来展示如何控制渲染文本的质量。e.Graphics.TextContrast 也可以用来增强对比度)。

注意:如果 ListView 具有 ImageList,则此代码示例仅绘制通用图像。您还应该验证是否定义了 SmallIcon/LargeIcon ImageLists,并以指定的大小绘制相关的 Image。不过,这是相同的程序。

protected void listView1_DrawItem(object sender, DrawListViewItemEventArgs e)
{
    e.Item.UseItemStyleForSubItems = true;
    int imageOffset = 0;
    Rectangle rect = e.Item.Bounds;
    bool drawImage = !(e.Item.ImageList is null);
    Color itemColor = Color.FromName(e.Item.Text.Substring(e.Item.Text.LastIndexOf(" ") + 1));
    using (var format = new StringFormat(StringFormatFlags.FitBlackBox)) {
        format.LineAlignment = StringAlignment.Center;

        if (drawImage) {
            imageOffset = e.Item.ImageList.ImageSize.Width + 1;
            rect.Location = new Point(e.Bounds.X + imageOffset, e.Item.Bounds.Y);
            rect.Size = new Size(e.Bounds.Width - imageOffset, e.Item.Bounds.Height);
            e.Graphics.DrawImage(e.Item.ImageList.Images[e.Item.ImageIndex], e.Bounds.Location);
        }

        if (e.Item.Selected) {
            using (var bkgrBrush = new SolidBrush(itemColor))
            using (var foreBrush = new SolidBrush(e.Item.BackColor)) {
                e.Graphics.FillRectangle(bkgrBrush, rect);
                e.Graphics.DrawString(e.Item.Text, e.Item.Font, foreBrush, rect, format);
            }
            e.DrawFocusRectangle();
        }
        else {
            //e.DrawDefault = true;
            using (var foreBrush = new SolidBrush(itemColor)) {
                e.Graphics.DrawString(e.Item.Text, e.Item.Font, foreBrush, rect, format);
            }
        }
    }
}

// Draws small symbol in the Header beside the normal Text
protected void listView1_DrawColumnHeader(object sender, DrawListViewColumnHeaderEventArgs e)
{
    e.DrawBackground();
    string extra = (e.ColumnIndex == 1) ? (char)32 + "\u2660" + (char)32 : (char)32 + "\u2663" + (char)32;
    using (var brush = new SolidBrush(e.ForeColor)) { 
        e.Graphics.DrawString(extra + e.Header.Text, e.Font, brush, e.Bounds, StringFormat.GenericTypographic);
    }
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-06-03
    • 2013-12-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-07-03
    相关资源
    最近更新 更多