如何在Winforms中具有ListBox的多色项目? [英] How to have a multi-coloured items of a ListBox in winforms?

查看:101
本文介绍了如何在Winforms中具有ListBox的多色项目?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在用Winforms开发软件,我陷入了自己的步骤

I am developing a software in winforms, I am stuck in a step where I have

 List<KeyValuePair<string, string>>. 

和一些示例数据:

List <KeyValuePair<"S", "1200">>
List <KeyValuePair<"S", "1300">>
List <KeyValuePair<"L", "1400">>

我想显示列表框内的键对值,其中基于该键对,列表框上的项具有不同的颜色,例如,如果键为S,则该项应为红色,如果键为L,则项目应为蓝色.

I want to diplay the value of the key pair inside a ListBox, where based in the key of the pair the Item on the ListBox has a diffrent colour, for example if the Key is S, then the Item should be red and if the Key is L the Item should be blue.

希望您能帮我这个忙.

Hope you could help me with this.

这是我执行的代码,但没有完成预期的操作:

this is the code I did but it doesn't do what is expected:

        e.DrawBackground();
        Graphics g = e.Graphics;
        Graphics x = e.Graphics;

        g.FillRectangle(new SolidBrush(Color.Olive), e.Bounds);
        x.FillRectangle(new SolidBrush(Color.Aquamarine), e.Bounds);

        foreach (var workOrders in GetItac.FilterWorkOrders())
        {
            if (workOrders.Key == "S")
            {
                g.DrawString(workOrders.Value, e.Font, new SolidBrush(e.ForeColor), new PointF(e.Bounds.X, e.Bounds.Y));

            }
            else
            {
                x.DrawString(workOrders.Value, e.Font, new SolidBrush(e.ForeColor), new PointF(e.Bounds.X, e.Bounds.Y));

            }

        }

推荐答案

当需要在ListBox控件中显示自定义结果时,需要启用列表中Items的自定义绘制,并设置ListBox

When you need to show customized results in a ListBox control, you need to enable the custom painting of the Items in the list, setting the ListBox DrawMode property to OwnerDrawVariable or OwnerDrawFixed (the latter will set all Items to the same height).
(Note → Here, I'm setting it to OwnerDrawVariable)

必须在 DrawItemEventArgs e.Graphics对象.这样可以正确刷新 ListBox/Form需要重新粉刷时.

The list Items painting has to be performed in the DrawItem event of the ListBox, using the DrawItemEventArgs e.Graphics object. This allow a correct refresh of the Items when the ListBox/Form need repainting.

1-您不必您的Graphics对象.
2-也不需要foreach循环,因为在创建/修改ListBox Items集合时每个项目都会被绘制.

1 - You don't have to multiply your Graphics object.
2 - The foreach loop is not needed either, because each Item will be painted when you create/modify the ListBox Items collection.

注意→我正在按照您在代码中显示的方式绘制Items背景,但是视觉效果可能有点怪异(这些颜色不能很好地融合在一起).

Note → I'm drawing the Items background the way you're showing in your code, but the visual result might be a bit weird (those colors don't blend well).

首先,模拟您的GetItac.FilterWorkOrders()方法的结果,该方法将返回List<KeyValuePair<string, string>>,并将那些Value项添加到列表中:

First, simulate the result of your GetItac.FilterWorkOrders() method, which will return a List<KeyValuePair<string, string>>, add those items Value to the list:

using System.Collections.Generic;

List<KeyValuePair<string, string>> workOrders;

workOrders = new List<KeyValuePair<string, string>>()
{
    new KeyValuePair<string, string>("S", "1200" ),
    new KeyValuePair<string, string>("S", "1300"),
    new KeyValuePair<string, string>("L", "1400")
};
//Select().ToList() extracts the Value string from the KeyValuePair elements
listBox1.DataSource = workOrders.Select(kv => kv.Value).ToList();

如果该方法实际上返回了List<KeyValuePair<string, string>>:

You can also code it this way, if that method actually returns a List<KeyValuePair<string, string>>:

workOrders = GetItac.FilterWorkOrders();
listBox1.DataSource = workOrders.Select(kv => kv.Value).ToList();
//Or
workOrders = GetItac.FilterWorkOrders();
listBox1.Items.AddRange(workOrders.Select(kv => kv.Value).ToArray());

填充ListBox Items集合后,将引发DrawItem事件,以允许绘画Items内容.
您可能需要添加

When the ListBox Items collection is filled, the DrawItem event will be raised, to allow the painting of the Items content.
You may need to add the MeasureItem event, to be sure to have a correct measure of each Item's height (mandatory, if you plan on modifying the ListBox Font.

对于绘制的每个项目,选择文本颜色以测试KeyValuePair<string, string>Key:如果其值为"S",则文本颜色设置为Color.Red,背景颜色设置为.否则将它们设置为Color.BlueColor.Aquamarine.

For each item that is drawn, the text color is chosen testing the Key of the KeyValuePair<string, string>: if its value is "S", the text color is set to Color.Red, the background color to Color.Olive. Otherwise they're set to Color.Blue and Color.Aquamarine.

private void listBox1_DrawItem(object sender, DrawItemEventArgs e)
{
    e.DrawBackground();
    Color textColor = (workOrders[e.Index].Key == "S") ? Color.Red : Color.Blue;
    Color backColor = (workOrders[e.Index].Key == "S") ? Color.Olive : Color.Aquamarine;
    using (SolidBrush backColorBrush = new SolidBrush(backColor))
    using (SolidBrush foreColorBrush = new SolidBrush(textColor))
    {
        e.Graphics.FillRectangle(backColorBrush, e.Bounds);
        e.Graphics.DrawString(workOrders[e.Index].Value, listBox1.Font, foreColorBrush, 
                              e.Bounds, StringFormat.GenericTypographic);
    }
}

private void listBox1_MeasureItem(object sender, MeasureItemEventArgs e)
{
    e.ItemHeight = listBox1.Font.Height;
}

这篇关于如何在Winforms中具有ListBox的多色项目?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆