winforms Windows窗体控件,显示MessageBox时是否阻止Invoke(Action)?

xqkwcwgp  于 2023-05-29  发布在  Windows
关注(0)|答案(1)|浏览(151)

我得调试以前同事写的代码。应用程序是机器控制的一部分。这台机器已经交付给我们的客户,这限制了我的调试能力。
情况如下:显示Windows窗体MessageBox:

if (MessageBox.Show(toask, "Überprüfung", MessageBoxButtons.OKCancel, MessageBoxIcon.Question, 
                    MessageBoxDefaultButton.Button1, MessageBoxOptions.DefaultDesktopOnly)
                    != DialogResult.OK)
{
    // Do something here
    return;
}

用户至少在半分钟内不会单击框,因为当框显示时,他必须做一些事情。同时,我需要执行System.Timers.Timer(500ms,AutoReset == false)事件的回调方法:

private void timerLoop_Elapsed(object sender, ElapsedEventArgs e)
{
    Action updateUI = () =>
    {
        // Do some extensive work, accessing Windows Forms controls.
        // I'm expecting a bool variable to be set here.
    }
    if (this.InvokeRequired)
        this.Invoke(updateUI);
    else
        updateUI();

    timerLoop.Start();
}

代码块中提到的bool变量没有设置,尽管它应该设置。由于回调方法总是在UI线程以外的线程中执行,因此调用了this.Invoke(updateUI)(可能会删除if(this.InvokeRequired))。
我的问题是:当显示MessageBox时,被调用的updateUI是否被阻止执行?这可以解释应用程序的行为。如果是这样,我可以做什么来强制回调的执行,而MessageBox显示?BeginInvoke()有帮助吗?

**附录1:**计时器以前是Windows.Forms.Timer,而不是Systems.Timers.Timer。我改变了它,试图解决另一个问题。在此之前,应用程序在上述情况下工作(除了其他问题)。

看起来,这些信息与问题相关?但是,我不明白为什么在MessageBox中处理了Forms.Timer的回调,而在Timers.Timers回调中却没有处理Control.Invoke?

k0pti3hp

k0pti3hp1#

我想用一个小测试程序来验证我的理论:

namespace Timers_Test
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();

            timersTimer.Elapsed += OnElapsed;

            winFormsTimer.Start();
            timersTimer.Start();
        }

        private System.Timers.Timer timersTimer = new System.Timers.Timer(500);

        private void winFormsTimer_Tick(object sender, EventArgs e)
        {
            tBFormsTimer.Text = DateTime.Now.ToString("hh:mm:ss");
        }

        private void OnElapsed(object sender, ElapsedEventArgs e)
        {
            tBTimersTimer.Invoke((Action)(() => tBTimersTimer.Text = DateTime.Now.ToString("hh:mm:ss")));
        }

        private void btnMessageBox_Click(object sender, EventArgs e)
        {
            MessageBox.Show("Which Callbacks does this MessageBox block?", "Test", MessageBoxButtons.OK, MessageBoxIcon.Question);
        }
    }
}

Screenshot of the running application.
这回答了问题:我的观察是,Control.Invoke(Action)中的操作直到单击MessageBox之后才被阻止,至少不是绝对的。

相关问题