【问题标题】:How to run a ProgressBar within a method with other methods如何使用其他方法在方法中运行 ProgressBar
【发布时间】:2020-10-01 09:00:02
【问题描述】:

我遇到了在单独的 UI 线程中实现 ProgressBar 的问题...

我的程序中有很多方法,我想在其中启动和停止进度条。

因此,我在我的 UI 中放置了一个 UI 组件 ProgressBar 并为它制作了一个模型,当在我的模型类中单独调用/使用时(我没有在后面的代码中工作),它(绑定后)可以正常工作。 当我将我的 Progress 模型属性设置为不确定然后调用其他一些方法时,就会出现问题:整个过程同步工作,并且进度条仅在退出主方法时才移动。

这是我想要实现的示例:

public void MyMethod1()
{
    StartProgress();

    NormalSubMethod1();
    NormalSubMethod2();
    (...)

    EndProgress();
}

public void MyMethod2()
{
    StartProgress();

    NormalSubMethod5();
    (...)

    EndProgress();
}

这是我的StartProgress() 的样子,我尝试过但没有成功:

public async void StartProgress()
{
    //Task.Run(() => { Progress.IsIndeterminate = true; });

    //await Task.Run(() => Progress.IsIndeterminate = true); // starts moving
}

public async void StopProgress()
{
    Progress.IsIndeterminate = false; // stops moving
}

我知道这一定是没有正确使用asyncawaitTask 的问题,但我还不能让它工作。任何人都可以帮助我提供有关如何完成此操作的提示吗?

【问题讨论】:

  • @dymanoid 在我看来不是...看来我只能在后面的代码中使用 Dispatcher,而且我明确没有在那里工作,但在模型中...我可能需要使用 @ 987654330@、awaitasync
  • Avoid async void。它仅适用于异步事件处理程序,您的方法 StartProgressStopProgress 不是事件处理程序。

标签: c# wpf asynchronous task progress-bar


【解决方案1】:

您的NormalSubMethod-s 本身应该是异步的。下面是一个如何工作的例子。请看看这里是如何使用 async/await 的。

XAML

<StackPanel>
    <ProgressBar
        x:Name="progress"
        Width="100"
        Height="30"/>
    <Button Content="Button"
            Width="60"
            Height="30" Click="Button_Click"
            />
    <TextBlock 
        TextWrapping="Wrap" 
        x:Name="textBlock" />
</StackPanel>

代码

    private async void Button_Click(object sender, RoutedEventArgs e)
    {
        StartProgress();
        await MyMethod();
        StopProgress();
    }

    private async Task MyMethod()
    {
        textBlock.Text += "MyMethod start" + Environment.NewLine;
  
        await Task.Delay(3000); // here we are imitating the real work
  
        textBlock.Text += "MyMethod end" + Environment.NewLine;
    }

    public void StartProgress()
    {
        progress.IsIndeterminate = true;
        textBlock.Text += "StartProgress" + Environment.NewLine;
    }

    public void StopProgress()
    {
        progress.IsIndeterminate = false;
        textBlock.Text += "StopProgress" + Environment.NewLine;
    }

编辑

您还可以使用Task.Run 包装现有的同步方法以异步运行它。

    private async Task MyMethod()
    {
        textBlock.Text += "MyMethod start" + Environment.NewLine;
        await Task.Run(() => NormalSubMethod1());
        textBlock.Text += "MyMethod end" + Environment.NewLine;
    }

    private void NormalSubMethod1()
    {
        long n = 0;
        for (var i = 0; i < 1e9; i++)
        {
            n++;
        }
    }

【讨论】:

  • 感谢这个工作示例;但是,在第一次尝试时,我还不能让它在我的环境中工作,我可能会更深入地研究它。无论如何,如果没有await Task.Delay(3000) 行会怎样?编译器抱怨缺少await...
猜你喜欢
  • 1970-01-01
  • 2012-12-02
  • 2013-03-17
  • 1970-01-01
  • 2021-03-01
  • 1970-01-01
  • 1970-01-01
  • 2018-08-26
  • 2019-06-18
相关资源
最近更新 更多