2010-05-24 5 views
7

При попытке сделать что-то более сложное, я столкнулся с поведением, которое я не совсем понимаю.TextChanged Events - Почему это не приводит к бесконечному циклу?

Используйте следующий код, приведенный ниже, для обработки события textChanged.

private void textChanged(object sender, TextChangedEventArgs e) 
    { 
     TextBox current = sender as TextBox; 
     current.Text = current.Text + "+"; 
    } 

Теперь, введя символ в текстовом поле (скажем, А) приведет событие получения споткнулся дважды (добавление двух «+» с) с окончательным текстом, отображаемым быть только A +.

Мои два вопроса: почему это событие произошло только дважды? И почему только первый прогон через событие фактически устанавливает текст текстового поля?

Заранее спасибо!

+2

почему вопрос, который, кажется, имеет мало смысла иметь 3 upvotes менее чем за 4 минуты? Я не понимаю .... –

+0

... поднялся до 5 голосов, а затем вернулся к 3? hmmmmm ... –

+1

Событие TextBox.TextChanged возникает при изменении TextBox.Text. Образец кода, однако, изменяет текст во время этого уведомления, что должно привести к дальнейшему повышению TextChanged, который затем приведет к новому изменению текста, который будет ... -> Бесконечная рекурсия.
Я не знал, что этот специальный случай явно обрабатывается классом TextBox - описанный эффект НЕ будет происходить. Вместо этого TextChanged будет подниматься только один раз. Я кое-чему научился через этот вопрос и поэтому поддержал его. – Matthias

ответ

7

Ну - установив свойство Text в то время как она изменяется/в то время как только изменилась, кажется, поймана TextBox класса явно:

Просто использовать отражатель, чтобы заглянуть внутрь TextBox.OnTextPropertyChanged (укороченный):

TextBox box = (TextBox) d; 
if (!box._isInsideTextContentChange) 
{ 
    string newValue = (string) e.NewValue; 
    //... 
    box._isInsideTextContentChange = true; 
    try 
    { 
     using (box.TextSelectionInternal.DeclareChangeBlock()) 
     { 
      //... 
     } //Probably raises TextChanged here 
    } 
    finally 
    { 
     box._isInsideTextContentChange = false; 
    } 
    //... 
} 

поле _isInsideTextContentChange устанавливается истина перед TextChanged событие получает г aised. При изменении значения Text, событие TextChanged, следовательно, не поднимается снова.

Поэтому: Feature ;-)

Смежные вопросы