2011-11-03 35 views
20

C#中有沒有一種方法可以等待用戶在輸入未輸入的值之前輸入文本框?C#等待用戶在文本框中輸入完成

修正這個問題有點:

好吧,我有一個簡單的計算器,通過2

這裏相乘就是我想要它做的事:用戶輸入,比如1000的值到一個文本框,它自動顯示2000年

這裏是發生了什麼:只要用戶在1其乘以2,輸出2

+14

如何確定他們「已完成打字?」我不認爲C#會爲至少另外幾個版本的心靈感應事件添加處理程序... – Donut

+1

這裏的問題是您必須定義「完成」。是否當他們停止鍵入3秒,5等...最簡單的方法是使用一個標記,如回車或點擊一個按鈕 – JaredPar

+0

你可以等待一段時間,只是猜測用戶已經結束鍵入或texbox沒有焦點再也...否則你不能 – evilone

回答

2

您可以使用文本框onChange()事件。如果文本在文本框中發生更改,請檢查輸入的值是否是數字,並根據其他值計算總值。

+1

onChange()不是VS2015 c#下的文本框事件。 – Jhollman

+10

@Jhollman我在2011年回答了這個問題。那麼,那麼就沒有Visual Studio 2015. – evilone

+1

這是怎麼回事?此外,爲什麼這是選擇的答案? – Krythic

0

如果您基於類似標籤或返回的按鍵觸發事件,該怎麼辦?

+0

我猜標籤或返回將工作如何將這些類型的事件添加到我的代碼 – user990951

+0

選項卡將導致'LostFocus'事件,請參閱http://msdn.microsoft.com/en-us /library/system.windows.forms.control.lostfocus.aspx瞭解更多詳情。 – esskar

+0

是的,lostfocus會最好,然後觸發你的事件 –

1

您想要爲相關文本框使用句柄LeaveLostFocus事件。我假設你使用WinForm,即使你沒有在你的問題中說明它。

39

現在我將「完成鍵入」定義爲「用戶鍵入了某些內容,但在某個時間後沒有鍵入任何內容」。把它作爲一個定義,我寫了一個從TextBox派生出來的小類,將它擴展爲DelayedTextChanged事件。我不確定它是否完整且無錯誤,但是它滿足了一個小小的煙霧測試。隨意更改和/或使用它。我把它叫做MyTextBox因爲我現在無法想出一個更好的名字。您可以使用DelayedTextChangedTimeout屬性更改等待超時。默認值是10000ms(= 10秒)。

public class MyTextBox : TextBox 
{ 
    private Timer m_delayedTextChangedTimer; 

    public event EventHandler DelayedTextChanged; 

    public MyTextBox() : base() 
    { 
     this.DelayedTextChangedTimeout = 10 * 1000; // 10 seconds 
    } 

    protected override void Dispose(bool disposing) 
    { 
     if (m_delayedTextChangedTimer != null) 
     { 
      m_delayedTextChangedTimer.Stop(); 
      if (disposing) 
       m_delayedTextChangedTimer.Dispose(); 
     } 

     base.Dispose(disposing);    
    } 

    public int DelayedTextChangedTimeout { get; set; } 

    protected virtual void OnDelayedTextChanged(EventArgs e) 
    { 
     if (this.DelayedTextChanged != null) 
      this.DelayedTextChanged(this, e); 
    } 

    protected override void OnTextChanged(EventArgs e) 
    { 
     this.InitializeDelayedTextChangedEvent(); 
     base.OnTextChanged(e);    
    }     

    private void InitializeDelayedTextChangedEvent() 
    { 
     if (m_delayedTextChangedTimer != null) 
      m_delayedTextChangedTimer.Stop(); 

     if (m_delayedTextChangedTimer == null || m_delayedTextChangedTimer.Interval != this.DelayedTextChangedTimeout) 
     {     
      m_delayedTextChangedTimer = new Timer(); 
      m_delayedTextChangedTimer.Tick += new EventHandler(HandleDelayedTextChangedTimerTick); 
      m_delayedTextChangedTimer.Interval = this.DelayedTextChangedTimeout; 
     } 

     m_delayedTextChangedTimer.Start(); 
    } 

    private void HandleDelayedTextChangedTimerTick(object sender, EventArgs e) 
    { 
     Timer timer = sender as Timer; 
     timer.Stop(); 

     this.OnDelayedTextChanged(EventArgs.Empty); 
    } 
} 
1

我不知道onChange()是否只存在於舊版本的c#中,但我找不到它!

檢測下工作時,用戶無論點擊回車鍵或切換到該文本框的,但改變一些文字後才:

//--- this block deals with user editing the textBoxInputFile --- // 
    private Boolean textChanged = false; 
    private void textBoxInputFile_TextChanged(object sender, EventArgs e) { 
     textChanged = true; 
    } 
    private void textBoxInputFile_Leave(object sender, EventArgs e) { 
     if (textChanged) { 
      fileNameChanged(); 
     } 
     textChanged = false; 
    } 
    private void textBoxInputFile_KeyDown(object sender, KeyEventArgs e) { 
     if (textChanged & e.KeyCode == Keys.Enter) { 
      fileNameChanged(); 
     } 
     textChanged = false; 
    } 
    //--- end block --- // 
12

另一種簡單的解決方案是將一個計時器添加到您的形式,Interval屬性設置爲250,然後使用計時器的Tick事件如下:

private void timer1_Tick(object sender, EventArgs e) 
{ 
    timer1.Stop(); 
    Calculate(); // method to calculate value 
} 

private void txtNumber_TextChanged(object sender, EventArgs e) 
{ 
    timer1.Stop(); 
    timer1.Start(); 
} 
6

如果您正在使用WPF和.NET 4.5或更高版本上有一個名爲控制的結合部的新屬性「延遲」。它定義了源更新後的時間範圍。

<TextBox Text="{Binding Name, Delay=500}" /> 

這意味着源僅在500毫秒後更新。據我所知,它在TextBox輸入後更新結束。順便說一句。這個屬性也可以在其他場景中有用,例如。列表框等

+0

如果您希望在輸入時更新源代碼,短暫停頓後,還需要綁定中的「UpdateSourceTrigger = PropertyChanged」。 – MgSam

3

我面臨同樣的挑戰,這裏是我的簡單方法。這工作沒有問題。

public partial class Form2 : Form 
    { 
     static int VALIDATION_DELAY = 1500; 
     System.Threading.Timer timer = null; 
     public Form2() 
     { 
      InitializeComponent(); 
     } 

     private void textBox1_TextChanged(object sender, EventArgs e) 
     { 
      TextBox origin = sender as TextBox; 
      if (!origin.ContainsFocus) 
       return; 

      DisposeTimer(); 
      timer = new System.Threading.Timer(TimerElapsed, null, VALIDATION_DELAY, VALIDATION_DELAY); 

     } 
     private void TimerElapsed(Object obj) 
     { 
      CheckSyntaxAndReport(); 
      DisposeTimer();    
     } 

     private void DisposeTimer() 
     { 
      if (timer != null) 
      { 
       timer.Dispose(); 
       timer = null; 
      } 
     } 

     private void CheckSyntaxAndReport() 
     {    
      this.Invoke(new Action(() => 
      { 
       string s = textBox1.Text.ToUpper(); //Do everything on the UI thread itself 
       label1.Text = s; 
      } 
       ));    
     } 
    } 
1

在UWP,我通過使靜態lastTimeOfTyping和檢查的時間當「框TextChanged」事件發生做了延遲檢查。當新的「TextChanged」時間匹配並等待,直到靜態lastTimeOfTyping匹配,然後執行所需的功能。

private const int millisecondsToWait = 500; 
    private static DateTime s_lastTimeOfTyping; 
    private void SearchField_OnTextChanged(object sender, TextChangedEventArgs e) 
    { 
     var latestTimeOfTyping = DateTime.Now; 
     var text = ((TextBox)sender).Text; 
     Task.Run(()=>DelayedCheck(latestTimeOfTyping, text)); 
     s_lastTimeOfTyping = latestTimeOfTyping; 
    } 

    private async Task DelayedCheck(DateTime latestTimeOfTyping, string text) 
    { 
     await Task.Delay(millisecondsToWait); 
     if (latestTimeOfTyping.Equals(s_lastTimeOfTyping)) 
     { 
      // Execute your function here after last text change 
      // Will need to bring back to the UI if doing UI changes 
     } 
    }