2014-09-22 50 views
0

我正在做一些應用程序,生成一些文本,但當我點擊我的按鈕它需要大約1或2秒後,將顯示一些消息框,但我想增加它到5或6秒。這是我的代碼,當你點擊按鈕:延遲做一些代碼,然後再開始在C#

private void button1_Click(object sender, EventArgs e) 
{ 
    progressBar1.MarqueeAnimationSpeed = 50; 
    //my code 
    // delay here for 5 or 6 sec 
    MessageBox.Show(id); 
    pictureBox1.Visible = true; 
} 

那麼我該怎麼做呢?

回答

8

使用async/await功能等待asyncronously所以當你在等待你的UI線程將響應:

private async void button1_Click(object sender, EventArgs e) 
{ 
    progressBar1.MarqueeAnimationSpeed = 50; 
    await Task.Delay(5000); 
    MessageBox.Show(id); 
    pictureBox1.Visible = true; 
} 
+0

正在尋找這個人,但不記得如何做到這一點。好的解決方案 – DatRid 2014-09-22 10:30:21

+0

夥計,這工作正常! TNX – 2014-09-22 10:52:37

0
Thread.Sleep(5000); 

Thread.Sleep()將暫停您的代碼。 時間以毫秒或時間跨度指定。

但請注意,代碼將完全停在那裏,並等待指定時間結束。

+0

這將防止更新UI。 – 2014-09-22 10:28:04

+1

我不知道這是否會殺死進度條的動畫... – Rawling 2014-09-22 10:28:07

0
Thread.Sleep(5000) 

將暫停你的代碼5秒...... 睡眠方法的參數以毫秒爲單位。 但是,爲什麼要讓Messagebox等到它出現? Thread.Sleep被認爲是大多數時間的代碼味道...

編輯:這將阻止UI線程。如果UI必須保持響應,請使用Selman22的解決方案

+0

Tnx但我輸入了這段代碼它說:**錯誤1名稱'線程'在當前上下文中不存在** – 2014-09-22 10:31:14

+2

@ale_x您需要什麼要做的是學習如何閱讀MSDN上的文檔。在MSDN上搜索Thread類,並閱讀它的文檔。這將告訴你要引用哪個程序集,以及需要使用哪個命名空間。 – 2014-09-22 10:32:26

+0

或者只需在我的答案中單擊MSDN-Link。但我建議你使用Patrick Hofman/Selman22的解決方案! – DatRid 2014-09-22 10:33:29

1

一個簡單的解決方案是創建一個具有所需間隔的單次計時器。當計時器啓動時,顯示您的消息框。

你不想做的是從你的GUI線程中調用Sleep,因爲那會阻塞GUI。

+0

好吧,指定它:他從來沒有說過阻止GUI並不是一個機會,因爲他的代碼如何被寫入,它看起來像所有的代碼(以及進度-bar-stuff)在他想要延遲代碼之前完成。 – DatRid 2014-09-22 10:36:40

+0

@DatRid從GUI線程休眠線程阻塞UI。應用程序需要及時地爲其消息隊列提供服務。 – 2014-09-22 10:38:03

+0

當然,我完全和你在一起。只是說他從來沒有說過會不會沒事。一般來說這是一個壞主意?當然。 – DatRid 2014-09-22 10:42:38

1

只是Thread.Sleep不幫你,因爲它會阻止用戶界面和進度條不得到更新。使用Task.Run

progressBar1.MarqueeAnimationSpeed = 50; 

Task.Run(() => 
    { 
     // your long running code 
    }) 
.ContinueWith(() => 
    { 
     this.Invoke((Action)delegate() 
     { 
      MessageBox.Show(id); 
      pictureBox1.Visible = true; 
     }); 
    }); 
0

Selman22的解決方案是好的,另一種方式來使用建議Thread.Sleep();,不會凍結您的GUI是使用一個後臺工作及其進展情況改變的事件。 你可以做一些循環迭代100次,每次迭代你做一個小的Thread.Sleep();,每次迭代後你發送一個改變的進度並更新你的進度條。

後臺工作應該是這樣的:

private void BackgroundWorkerStartEvent(object sender, EventArgs e) 
    { 
     if (!backgroundWorker1.IsBusy) 
     { 
      backgroundWorker1.RunWorkerAsync(); 
     } 
    } 

    private void BackgroundWorkerCancelBeforeWorkIsDoneEvent(object sender, EventArgs e) 
    { 
     if (backgroundWorker1.WorkerSupportsCancellation) 
     { 
      backgroundWorker1.CancelAsync(); 
     } 
    } 

    private void DoWorkEvent(object sender, DoWorkEventArgs e) 
    { 
     BackgroundWorker worker = sender as BackgroundWorker; 
     const int loopnumber = 100; 

     for (int i = 1; i <= loopnumber; i++) 
     { 
      if (worker != null && worker.CancellationPending) 
      { 
       e.Cancel = true; 
       break; 
      } 
      System.Threading.Thread.Sleep(100); 
      if (worker != null) worker.ReportProgress(i * 100/loopnumber); 
     } 
    } 

    private void ProgressChangedEvent(object sender, ProgressChangedEventArgs e) 
    { 
     //...update your progress bar or something. 
    } 

    private void RunWorkerCompletedEvent(object sender, RunWorkerCompletedEventArgs e) 
    { 
     if (e.Cancelled) 
     { 
      //...Do what you do if the backgroundworker go cancelled... 
     } 
     else if (e.Error != null) 
     { 
      //...Error displaying... 
     } 
     else 
     { 
      //...Do what you do if it worked fine... 
     } 
    }