简体   繁体   English

如何在计时器的刻度中更改标签的文本(GUI忙)

[英]How Change A Label's Text In A Timer's Tick (GUI Is Busy)

i have a strange situation. 我有一个奇怪的情况。
please see the backgroundWorker5_RunWorkerCompleted event: 请参阅backgroundWorker5_RunWorkerCompleted事件:

    private void backgroundWorker5_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {
        btnStartAdventures.Text = "Start Adventure";
        btnStartAdventures.Enabled = true;

        if (e.Error != null)
        {
            MessageBox.Show(e.Error.Message);
            return;
        }
        if (e.Cancelled)
        {
            lblStatusValueInAdventures.Text = "Cancelled...";
        }
        else
        {
            lblStatusValueInAdventures.Text = "Completed";
            timer1.Enabled = true;
            timer1.Start();
            // MessageBox.Show("start timer");
            Thread.Sleep((int.Parse(txtDelayInAdventures.Text)) * 60000);
            //MessageBox.Show("end timer");
            timer1.Enabled = false;
            timer1.Stop();
            lblTimer.Text = "0";
            btnStartAdventures.PerformClick();
        }
    }

and that Timer is : 那个计时器是:

private void timer1_Tick(object sender, EventArgs e)
{
    this.Invoke(new MethodInvoker(delegate { lblTimer.Text = (int.Parse(lblTimer.Text) + 1).ToString(); }));
}

but this timer can not change lblTimer's Text . 但是此计时器不能更改lblTimer's Text
how can i fix this problem? 我该如何解决这个问题?

EDIT: 编辑:
that Thread.Sleep is necessary and i can not remove it. 该Thread.Sleep是必要的,我无法将其删除。
i want a loop that never ends and those codes are for that. 我想要一个永无止境的循环,那些代码是为此而设计的。

thanks in advance 提前致谢

 Thread.Sleep 

There's your problem. 有你的问题。

Never call Thread.Sleep in a UI thread; 切勿在UI线程中调用Thread.Sleep it will freeze the UI. 它将冻结UI。

Get rid of that, and it will work fine. 摆脱它,它将正常工作。

You can put the rest of the work in the timer callback. 您可以将其余工作放在计时器回调中。

You can also use C# 5 async to make this much simpler. 您还可以使用C#5异步来简化此过程。

You have to refresh item. 您必须刷新项目。

lblTimer.Refresh()

and also you could refresh form 你也可以刷新表格

frmName.Refresh();

and make thread to sleep 0 milliseconds that gives space for other processes. 并使线程休眠0毫秒,以便为其他进程留出空间。

As requested; 按照要求;

What do you mean by "a loop that never ends"? “永无止境的循环”是什么意思? A Thread.Sleep on the UI thread (RunWorkerCompleted event executes on the UI thread) will effectively freeze the UI thread, which means that no interaction with the UI thread will be shown. UI线程上的Thread.Sleep (在UI线程上执行RunWorkerCompleted事件)将有效冻结UI线程,这意味着将不显示与UI线程的交互。

Comments: 评论:

What are you trying to achieve? 您想达到什么目的? As far as I can guess, you are doing some work in a background thread - backgroundWorker5 - (the UI thread is responsive). 据我所猜测,您正在后台线程(backgroundWorker5)(UI线程响应)中做一些工作。 When backgroundWorker5 is finished you want to start a timer and display a counter in a label while the UI is still responsive (for somebody to stop the timer maybe?). 当backgroundWorker5完成时,您想启动计时器并在UI仍响应时(在某人中停止计时器吗?)在标签中显示计数器。 Something like that? 这样的事吗? – Mario 3 mins ago edit –马里奥3分钟前编辑

yes you are right. 是的,你是对的。 i want a loop and it never stops until a user click cancel button. 我想要一个循环,直到用户单击“取消”按钮,它才会停止。 – MoonLight 1 min ago – MoonLight 1分钟前

So, try something like this: 因此,尝试这样的事情:

int time = 0;

private void backgroundWorker5_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
    btnStartAdventures.Text = "Start Adventure";
    btnStartAdventures.Enabled = true;

    if (e.Error != null)
    {
        MessageBox.Show(e.Error.Message);
        return;
    }
    if (e.Cancelled)
    {
        lblStatusValueInAdventures.Text = "Cancelled...";
    }
    else
    {
        lblStatusValueInAdventures.Text = "Completed";
        timer1.Interval = 1000; //<--- Tick each second, you can change this.
        timer1.Enabled = true;
        timer1.Start();
        // MessageBox.Show("start timer");
    }
}

private void timer1_Tick(object sender, EventArgs e)
{
    lblTimer.Text = (time + 1).ToString();
}

private void button_Cancel_Click(object sender, EventArgs e)
{
    //MessageBox.Show("end timer");
    timer1.Enabled = false;
    timer1.Stop();
    lblTimer.Text = "0";
    btnStartAdventures.PerformClick();
}

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

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