Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/273.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 调用以更新UI控件_C#_Multithreading_Dispatcher - Fatal编程技术网

C# 调用以更新UI控件

C# 调用以更新UI控件,c#,multithreading,dispatcher,C#,Multithreading,Dispatcher,我有一个.Net 4.0类,它有一个自定义事件处理程序(StatusChanged)。我试图通过一个线程使用这个类。我没有使用BackgroundWorker的奢侈,因为我使用的库不支持多线程单元状态 StatusChanged委托中的一个参数是字符串 在UI中,单击按钮可初始化使用my类的线程 我正试图使其成为当触发StatusChanged事件时,UI控件(WPF)更新为StatusChanged字符串参数。我的理解是,Dispatcher.Invoke可以做到这一点,但我不知道如何从中提取

我有一个.Net 4.0类,它有一个自定义事件处理程序(
StatusChanged
)。我试图通过一个线程使用这个类。我没有使用BackgroundWorker的奢侈,因为我使用的库不支持多线程单元状态

StatusChanged
委托中的一个参数是字符串

在UI中,单击按钮可初始化使用my类的线程

我正试图使其成为当触发
StatusChanged
事件时,UI控件(WPF)更新为
StatusChanged
字符串参数。我的理解是,
Dispatcher.Invoke
可以做到这一点,但我不知道如何从中提取字符串

本质上,我试图获得与
BackgroundWorker.ProgressChanged
(使用
ProgressChangedEventArgument.UserState
)相当的值

下面是一些按比例缩小的代码,以演示我的想法:

使用事件处理程序初始化:

public class MyClass
{
    public event EventHandler StatusChanged;

    private void alertStatus(string message)
    {
        if(StatusChanged == null)
            return;
        this.StatusChanged(message, new EventArgs());
    }

    public void DoStuff()
    {
        ///Do Stuff 1
        alertStatus("Done with stuff #1");

        ///Do Stuff 2            
        alertStatus("Done with stuff #2");
    }
}
因此,按钮的.Click事件将执行以下操作:

private void buttonClicked(object sender, EventArgs e)
{
    Thread t = new Thread(doWork);
    t.Start();
}

private void doWork()
{
    MyClass class = new MyClass();
    class.StatusChanged += ...
    class.DoStuff();
    ///As StatusChanged fires within MyClass, a UI Textbox would get updated
}

使用lambda表达式最简单:

private void doWork()
{
    // Name changed to avoid it being a keyword
    MyClass clazz = new MyClass();
    clazz.StatusChanged += (sender, args) => {
        string message = (string) sender; // This is odd
        Action action = () => textBox.Text = message;
        Dispatcher.Invoke(action);
    };
    clazz.DoStuff();
}
但是,使用字符串作为事件的发送者是非常奇怪的-最好使用
EventArgs
的子类,并使其存储消息-然后让事件使用
EventHandler
而不仅仅是
EventHandler

上面的代码有点混乱,因为您使用一个委托订阅事件,然后将另一个委托传递给
Dispatcher.Invoke
——因此使用了两个lambda表达式(一个在另一个内部)。您可以始终使用方法组,至少对于外部方法组:

private void doWork()
{
    // Name changed to avoid it being a keyword
    MyClass clazz = new MyClass();
    clazz.StatusChanged += HandleStatusChange;
    clazz.DoStuff();
}

private void HandleStatusChange(object sender, EventArgs e)
{
    string message = (string) sender; // This is odd
    Action action = () => textBox.Text = message;
    Dispatcher.Invoke(action);
}

把绳子从什么地方拔出来?请展示您尝试过的内容-如果没有任何示例代码,很难理解这个问题。我添加了代码来演示我正在尝试做什么。但是您还没有展示您使用
Dispatcher尝试过的内容。调用
-这是我想看到的,所以我们可以帮你们解决这个问题。这是一个问题……我还并没有弄清楚如何使用Dispatcher.Invoke来完成这个任务。太棒了!这正是我需要的。非常感谢你。我同意使用字符串是很奇怪的。这是一项匆忙的工作,需要在本周进行测试,所以我不得不牺牲优雅。再次感谢。