1

单击按钮后,我需要不断更新我的文本框,但按钮应按原样执行其剩余任务。

很简单,当点击事件执行时,文本框不应该等待点击事件完成,而是开始不断更新其文本。

示例代码

using System.threading;

namespace name
{
    public class sA
    {
        public void th()
        {
           textbox.invoke(new MethodInvoke(()=> textbox.AppendText("hello\n")));
        }

        private void Button1Click(object sender, EventArgs e)
        {
           thread cThread=new thread(th);
           cThread.start();

           while(true)
           {
               // do any thing
           }
        }
    }
}

重要 :: 当它执行事件“Cthread.start();”时 文本框应立即开始更新文本,而单击事件的其余功能(如“while 循环”)应并行执行。

在此处输入图像描述

4

3 回答 3

4

如果这是在 Windows 窗体内.. 然后Application.DoEvents();在循环中的任何位置添加,例如

private void Button1Click(object sender, EventArgs e)
{
   thread cThread=new thread(th);
   cThread.start();
   while(true)
   {
     // do any thing   
     textbox.Invalidate();
     Application.DoEvents(); // Releases the current thread back to windows form
                          // NOTE Thread sleep different in Application.DoEvents();
                          //Application.DoEvents() is available only in System.Windows.Forms
   }
} 

希望这对你有所帮助,虽然迟到了.. :)

于 2012-09-21T01:57:01.673 回答
2

您的while(true)块也必须发生在另一个线程上。

现在它阻止 UI 线程执行任何更新。

方法 th() 在后台线程上运行,但在 UI 线程再次可用之前,对 Invoke 的调用无法运行。

于 2012-05-18T14:07:18.017 回答
1

如果我正确理解了您的问题,您需要在按钮单击过程在其“while”循环内运行时不断更新 TextBox 的文本。您并没有真正指定从哪里更新文本框,但我会假设它来自“while”循环中的代码。

正如“akatakritos”所说,您在按钮单击中的 while 循环是您的应用程序停止的原因。发生这种情况是因为 while 循环阻塞了用户界面 (UI) 线程。

您应该做的是移动“while”循环中的代码以在不同的线程中运行,并使用按钮单击启动这个新线程。

这是一种方法,也许不是最好的,但它会做你需要的:

创建一个新类:

public class ClassWithYourCode
{
    public TextBox TextBoxToUpdate { get; set; }
    Action<string> updateTextBoxDelegate;

    public ClassWithYourCode()
    { }

    public void methodToExecute()
    {
        bool IsDone = false;
        while (!IsDone)
        {
            // write your code here. When you need to update the 
            // textbox, call the function:
            // updateTextBox("message you want to send");
            // Below you can find some example code:

            for (int i = 0; i < 10; i++)
            {
                Thread.Sleep(1000);
                updateTextBox(string.Format("Iteration number: {0}", i));
            }

            // Don't forget to set "IsDone" to "true" so you can exit the while loop!
            IsDone = true;
        }

        updateTextBox("End of method execution!");
    }

    private void updateTextBox(string MessageToShow)
    {
        if (TextBoxToUpdate.InvokeRequired)
        {
            updateTextBoxDelegate = msgToShow => updateTextBox(msgToShow);
            TextBoxToUpdate.Invoke(updateTextBoxDelegate, MessageToShow);
        }
        else
        {
            TextBoxToUpdate.Text += string.Format("{0}{1}", MessageToShow, Environment.NewLine);
        }
    }

}

并且,在您的 button1_Click 方法中,您可以添加以下代码:

private void button1_Click(object sender, EventArgs e)
{
    ClassWithYourCode myCode = new ClassWithYourCode();
    myCode.TextBoxToUpdate = textBox1;

    Thread thread = new Thread(myCode.methodToExecute);
    thread.Start();
}

现在,您的“while”循环正在一个新线程中执行,并且每当您需要更新文本框时,您都可以从 UI 线程执行此操作,因为您无法从 UI 线程以外的线程更新 Windows 窗体控件。

于 2012-05-18T15:14:04.950 回答