简体   繁体   English

是否有任何命令立即更新UI?

[英]Is there any command to update UI immediately?

I want to update a progress bar from running 1 to 100 with this code. 我想使用此代码更新从1到100的进度条。

for (int i = 0; i <= 100; i++) {
    System.Threading.Thread.Sleep(100);
    progressBar1.Value = i;
}

But the result is, the UI freeze until looping finish. 但结果是,UI冻结直到循环完成。

I know Dispatcher can help, but I don't want to split function. 我知道Dispatcher可以提供帮助,但我不想拆分功能。

Is there any command to update UI immediately like.. 是否有任何命令立即更新UI像..

for (int i = 0; i <= 100; i++) {
    System.Threading.Thread.Sleep(100);
    progressBar1.Value = i;
    UpdateUINow();
}

Edit: I'm using WPF, and I use Thread.Sleep to simulate long running process. 编辑:我正在使用WPF,我使用Thread.Sleep来模拟长时间运行的进程。

In fact, I want any command liked Application.DoEvents . 实际上,我想要任何喜欢Application.DoEvents命令。 But I cannot find this command in WPF. 但是我在WPF中找不到这个命令。

Please don't sleep in the UI thread. 不要在UI线程中睡觉。 It will freeze your UI - it's a bad thing to do. 它会冻结你的UI - 这是一件坏事。

Either have a timer of some kind (use the right kind of timer and you should be able to get it to fire in your UI thread) or use a separate thread (either via BackgroundWorker , a new separate thread, or the ThreadPool ) and make it call back to the UI thread to update it. 要么有一个类型的计时器(使用正确的计时器,你应该能够在你的UI线程中启动它)或使用一个单独的线程(通过BackgroundWorker ,一个新的单独的线程,或ThreadPool )和make它回调UI线程来更新它。

Application.DoEvents is a hacky workaround in WinForms, but the fact that you've mentioned a Dispatcher suggests you're using WPF - is that the case? Application.DoEvents是WinForms中的一个hacky变种方法,但你提到Dispatcher建议你使用WPF的事实是这样的吗? The kind of timer you should use (if you want to use that solution) will depend on the UI framework you're using. 您应该使用的计时器类型(如果您要使用该解决方案)将取决于您正在使用的UI框架。

另一种方法是使用BackgroundWorker(ThreadPool在这里有点过分但技术上可以使用)并让它报告进度。

I would use a C# BackgroundWorker to update your UI. 我会使用C# BackgroundWorker来更新您的UI。 This isn't working like you'd expect it to because the Thread.Sleep() is freezing your UI thread. 这不像你期望的那样工作,因为Thread.Sleep()冻结你的UI线程。

EDIT: Tutorial that does a bit more what you want here 编辑:教程, 在这里做更多你想要的

Ditto on sleeping in the main (GUI) thread -- avoid it at all costs. 在主(GUI)线程中睡觉同样 - 不惜一切代价避免它。 Although you don't want to Dispatcher, I'd still recommend trying (something like) this: 虽然您不想使用Dispatcher,但我仍然建议尝试(类似)这样:

public partial class Window1 : Window
{
    DispatcherTimer _timer = new DispatcherTimer();

    public Window1()
    {
        InitializeComponent();
    }

    private void Window_Loaded(object sender, RoutedEventArgs e)
    {
        progressBar1.Value = 0;
        progressBar1.Maximum = 100;
        _timer.Interval = TimeSpan.FromMilliseconds( 100);
        _timer.Tick += ProgressUpdateThread;
        _timer.Start();
    }

    private void ProgressUpdateThread( object sender, EventArgs e)
    {
        progressBar1.Value++;
    }
}

看看DoEvents是否可以帮助您。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM