c# - 在不阻塞当前线程的情况下显示表单(对话框)(进度条示例)

标签 c# .net multithreading devexpress

我正在尝试创建一个使用 BackgroundWorker 的 ProgressBar 表单在显示进度条的同时在不同线程上执行操作。

目前我的 ProgressBar 类包含一个 ProgressBarControl,代码如下所示:

public partial class QTProgressBar : DevExpress.XtraEditors.XtraForm
{
    private BackgroundWorker m_backgroundWorker;
    private AutoResetEvent m_resetEvent;

    public QTProgressBar()
    {
        InitializeComponent();

        InitializeProgressBar();

        m_backgroundWorker = new BackgroundWorker();
        m_backgroundWorker.WorkerReportsProgress = true;
        m_backgroundWorker.WorkerSupportsCancellation = true;
        m_backgroundWorker.DoWork += new DoWorkEventHandler(m_backgroundWorker_DoWork);
        m_backgroundWorker.ProgressChanged += new ProgressChangedEventHandler(m_backgroundWorker_ProgressChanged);
        m_backgroundWorker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(m_backgroundWorker_RunWorkerCompleted);
        m_resetEvent = new AutoResetEvent(false);
    }

    void m_backgroundWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {
        m_resetEvent.Reset();

        CloseProgressBar();
    }

    void CloseProgressBar()
    {
        if (InvokeRequired)
        {
            Invoke( new MethodInvoker(CloseProgressBar));
            return;
        }
        this.Close();
    }

    void m_backgroundWorker_DoWork(object sender, DoWorkEventArgs e)
    {
        Action operation = e.Argument as Action;
        operation();
    }

    public void StartAsyncTask(Action operation)
    {
        m_resetEvent.Set();
        m_backgroundWorker.RunWorkerAsync(operation);
    }
}

现在,当我想显示一个弹出窗口时,我会这样做:

QTProgressBar op = new QTProgressBar();
op.StartAsyncTask(() => LongDurationOperation(5, 5));
op.ShowDialog(); // i would like to move this inside the ProgressBar class.
//Thread gets blocked here until operation finishes. 

LongDurationOperation 在哪里:

public void LongDurationOperation(int n, int m)
{
    for (int i = 0; i < n; i++)
    {
        for (int j = 0; j < n; j++)
        {
            Thread.Sleep(100);
        }
    }
}

我想避免阻塞任何调用

的线程
ShowDialog() 

progressBar 类的方法。 如果我将其移动到 ProgressBar 类线程内的任何位置,线程将被阻塞并且操作不会执行。

是否可以避免阻塞调用 Showdialog() 方法的线程?

另外,你能给我一些关于如何改进这个类(class)的提示吗?

非常感谢。

最佳答案

表单中存在两种不同的调用:

myForm.ShowDialog();

是阻塞调用它的线程的模态版本。它用于必须阻止其他操作发生的弹出窗口(如保存对话框)。

myForm.Show(IWin32Window owner);

是非模态版本。它不会阻塞当前线程,但不会返回任何结果。但是,您必须将它传递给所有者,通常是这样的:

myForm.Show(this);

关于c# - 在不阻塞当前线程的情况下显示表单(对话框)(进度条示例),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13341241/

相关文章:

javascript - 如何根据单元格值修改或类似于 @model.count 的计数行

c# - 为什么这个属性会导致 StackOverFlow 异常?

c# - 模型绑定(bind)绑定(bind)我的 json 数组,但不绑定(bind)值

.net - 如何在 TreeView 中选择下一个/上一个 TreeViewItem?

java - 如何生成多个圆形并使这些形状沿着框架向下移动

java - 无法在未调用 Looper.prepare() 的线程内创建处理程序

c# - .NET app.config 文件——这是否需要与我的应用程序一起分发?

c# - 泛型实现中的值和引用类型

.net - SmtpAppender log4net 使用 gmail smtp

multithreading - Spark 如何在多核或超线程机器上实现一项任务内的并行性