InvokeRequired and ToolStripStatusLabel

9

在我的应用程序中,我有一个负责所有数据库操作的类。它被从主类调用,并使用委托在操作完成后调用方法。 由于它是异步的,所以我必须在我的 GUI 上使用 invoke 方法,因此我创建了一个简单的扩展方法:

 public static void InvokeIfRequired<T>(this T c, Action<T> action)
            where T: Control
        {
            if (c.InvokeRequired)
            {
                c.Invoke(new Action(() => action(c)));
            }
            else
            {
                action(c);
            }
        }

当我尝试在textBox上调用它时,这个功能可以很好地工作:

textBox1.InvokeIfRequired(c => { c.Text = "it works!"; });

但是当我尝试在ToolStripStatusLabel或ToolStripProgressBar上调用它时,会出现错误:
“类型'System.Windows.Forms.ToolStripStatusLabel'不能用作泛型类型或方法'SimpleApp.Helpers.InvokeIfRequired(T, System.Action)'中的类型参数'T'。从'System.Windows.Forms.ToolStripStatusLabel'到'System.Windows.Forms.Control'没有隐式引用转换。”
我知道这可能很简单,但我只是无法处理它 :/

也许这个相似的问题可以帮到您。https://dev59.com/wXNA5IYBdhLWcg3wAI3e - Rugbertl
3个回答

10
这是因为ToolStripItem(导致错误的两个基础)是一个Component而不是Control。尝试在拥有它们的工具栏上调用您的扩展方法并调整委托方法。

我刚才在谷歌上找到了相同的信息 :) 但是我该如何从statusStrip访问ToolStripStatusLabel?这样我就可以将statusStrip传递给我的方法了? - Misiu
2
MSDN是您的好朋友 :) 请访问http://msdn.microsoft.com/en-us/library/system.windows.forms.toolstrip.items.aspx。 - slawekwin
你很快 :) 但是如何访问Items?只能通过索引访问还是可以通过名称访问?例如,如果我将ToolStripStatusLabel命名为“status”,那么我如何在我的委托中访问它?只能像statusStrip1.Items[0]这样吗?我问这个问题是因为我将动态地向statusStrip添加控件,我可能会弄乱我的控件索引。 - Misiu
1
只需要2个点击...请阅读文档。http://msdn.microsoft.com/zh-cn/library/25b5ws77.aspx - slawekwin
你喜欢这个地方吗?:) - Alan

3
我想要补充一下已经接受的解决方案。您可以通过使用ToolStripStatusLabel的GetCurrentParent方法从组件中获取控件。
不要使用"toolStripStatusLabel1.InvokeIfRequired",而是使用"toolStripStatusLabel1.GetCurrentParent().InvokeIfRequired"。

1
谢谢你的回答。我一直在使用 Control,但是在得到你的答案后,我刚刚完成了我的工作。 - sebu

2

使用扩展方法 GetCurrentParent().InvokeRequired

public static void ToolStripStatusInvokeAction<TControlType>(this TControlType control, Action<TControlType> del)
    where TControlType : ToolStripStatusLabel
    {
        if (control.GetCurrentParent().InvokeRequired)
            control.GetCurrentParent().Invoke(new Action(() => del(control)));
        else
            del(control);
    }

调用ToolStripStatusInvokeAction扩展:

toolStripAppStatus.ToolStripStatusInvokeAction(t =>
{ 
    t.Text= "it works!";
    t.ForeColor = Color.Red;
});

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接