TextBox and default Button binding does update too

2019-01-09 05:20发布

问题:

I've got a simple WPF dialog with these two controls:

<TextBox Text="{Binding MyText}"/>
<Button Command="{Binding MyCommand}" IsDefault="True"/>

Now, when I enter some text in the TextBox and click the button using the mouse, everything works like expected: the TextBox will set MyText and MyCommand is called.

But when I enter some text and hit enter to "click" the default button, it does not work. Since on hitting enter the focus does not leave the TextBox, the binding will not be refresh MyText. So when MyCommand is called (which works), MyText will contain old data.

How do I fix this in MVVM? In classic code-behind I probably just would call "MyButton.Focus()" in the MyCommand handler, but in MVVM the MyCommand handler does know nothing about the button.

So what now`?

回答1:

Add the UpdateSourceTrigger to your TextBox with the value PropertyChanged. The default behavior of the Textbox is to update the source, when it´s lost focus.

<TextBox Text="{Binding MyText, UpdateSourceTrigger=PropertyChanged}"/>


回答2:

Try this. This code moves focus on the button clicked. Thus binding completes before command processed.

    public App()
    {
        EventManager.RegisterClassHandler(typeof(Button), Button.ClickEvent, new RoutedEventHandler(GenericButtonClickHandler));
    }

    void GenericButtonClickHandler(object sender, RoutedEventArgs e)
    {
        var button = sender as Button;
        if (button == null)
            return;
        if (button.IsDefault)
            button.Focus();
    }


回答3:

One Solution ist, to create your own Class OKButton that calls Me.Focus in the OnClick-Method. This will be called before the Click_Event and before any Command that is bound to the button. You just have to remember to use an OKButton instead of setting IsDefault=True

Public Class OKButton
  Inherits System.Windows.Controls.Button

  Public Sub New()
  MyBase.New()
  Me.Content = "OK"
  Me.IsDefault = True
  End Sub

  Protected Overrides Sub OnClick()
  Me.Focus()
  MyBase.OnClick()
  End Sub
End Class


标签: wpf mvvm binding