【发布时间】:2011-11-04 14:01:11
【问题描述】:
在我的 WinForms 应用程序中,我有一个每秒“滴答”一次的计时器。在这个计时器的刻度方法中,我做了很多事情,包括将项目添加到列表框(称为lbxLogText)。
我需要选择为某些项目的文本着色(颜色是在添加项目之前决定的)。因此,我将 DrawMode 属性设置为 OwnerDrawVariable,lbxLogText_DrawItem 方法如下所示:
private void lbxLogText_DrawItem(object sender, DrawItemEventArgs e)
{
e.DrawBackground();
e.DrawFocusRectangle();
e.Graphics.DrawString(logStringToAdd,
new Font(FontFamily.GenericSansSerif, 8),
new SolidBrush(logStringToAddColor), e.Bounds);
testCounter++;
label29.Text = testCounter.ToString();
}
logStringToAdd:一个全局的string。
logStringToAddColor:全局Color - 红色或黑色。
testCounter:一个全局的int,初始化为0。
我有一个名为Log() 的方法。这在上面提到的计时器的tick-method中被调用。
看起来是这样的:
private void Log(string status)
{
// |red, |black
if (status != null)
{
if (status.Contains("|red"))
{
status = status.Replace("|red", "");
logStringToAddColor = Color.Red;
}
else if (status.Contains("|black"))
{
status = status.Replace("|black", "");
logStringToAddColor = Color.Black;
}
logStringToAdd = status;
lbxLogText.Items.Add(new object());
}
// scroll to bottom
lbxLogText.SetSelected(lbxLogText.Items.Count - 1, true);
lbxLogText.SetSelected(lbxLogText.Items.Count - 1, false);
}
status: 可能是“系统工作正常。|黑色”,或“系统工作不正常。|红色”(例如)。此参数在 Log-call 之前更新(当然)。
在某种程度上,这段代码可以正常工作。我有以下问题:
运行程序时,我可以在
label29上看到testCounter变量不只是每秒递增,就像它从 1 开始,然后变成 3,然后是 6、10、15、21 , 28, 36(我想你现在已经掌握了模式)。这意味着 DrawItem 事件的调用次数更多,而不仅仅是每秒。假设
status从“asd123|black”变为“qwe456|red”。这意味着添加到列表框中的下一个项目应该是红色的。好吧,它确实变成了红色,但是列表框中的所有项变成了红色。并且所有项目的文本也都更改为最新的。在调试的时候,可以看到
SetSelected方法被调用的时候,直接下到了DrawItem事件方法。但我不知道如何避免这种情况,因为添加新项目时我需要列表框滚动到底部,所以最新的项目是可见的。
【问题讨论】: