是什么触发了UI上的绑定?

Tom*_*try 0 c# data-binding wpf

我在WPF窗口中有一个TextBox,我从后面的代码中填充(在用户从OpenFileDialog中选择一个后,使用文件名).

虽然我的TextBox.Text绑定到我的ViewModel类中的String属性,但是当文本设置为TextBox.Text时,不会填充该属性.

如果我输入TextBox,则会填充属性,因此必须有一些事件触发或在用户输入期间发生的事情,而不是我通过代码设置值时.

我错过了正确绑定的步骤是什么?

另外,属性上的set方法是在属性更改时调用还是UI?或两者?如果更改UI调用set方法,该方法触发PropertyChanged事件以更新UI,那么什么会永久停止此循环?

(我知道我可以直接设置属性,但我觉得我对绑定缺乏了解,我希望这有助于填补一些空白.)

我的示例代码:

<Window x:Class="ConfigurationViewer.ViewerWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="clr-namespace:ConfigurationViewer"
    Title="Configuration Viewer" Height="512" Width="714" >
    <Window.DataContext>
        <local:TaskViewModel x:Name="_model"/>
    </Window.DataContext>
    <DockPanel>
        <StackPanel DockPanel.Dock="Top" Orientation="Horizontal">
            <TextBlock Text="Configuration file" Margin="2" VerticalAlignment="Center" />
            <TextBox Height="29" Margin="2" Name="textFilePath" Width="277" Text="{Binding Path=ConfigurationPath}" />
            <Button Content="Browse ..." Margin="2" Name="buttonBrowseFile" Width="98" Click="buttonBrowseFile_Click" />
            <Button Content="Open" Margin="2" Name="buttonOpenFile" Width="98" Click="buttonOpenFile_Click"  />
        </StackPanel>
    </DockPanel>
</Window>
Run Code Online (Sandbox Code Playgroud)
    public partial class ViewerWindow : Window
    {
        public ViewerWindow()
        {
            InitializeComponent();
        }

        private void buttonBrowseFile_Click(object sender, RoutedEventArgs e)
        {
            OpenFileDialog openDialog = new OpenFileDialog();
            openDialog.Multiselect = false;
            openDialog.InitialDirectory = textFilePath.Text;

            Nullable<Boolean> ok = openDialog.ShowDialog();
            if (ok == true)
            {
                textFilePath.Text = openDialog.FileName;
            }
        }

        private void buttonOpenFile_Click(object sender, RoutedEventArgs e)
        {
        }
    }
Run Code Online (Sandbox Code Playgroud)
    public class TaskViewModel : INotifyPropertyChanged
    {
        private String _configurationPath = String.Empty;
        public String ConfigurationPath
        {
            get { return _configurationPath; }
            set
            {
                _configurationPath = value;
                OnPropertyChanged("ConfigurationPath");
            }
        }

        public event PropertyChangedEventHandler PropertyChanged;

        private void OnPropertyChanged(String prop)
        {
            PropertyChangedEventHandler handler = this.PropertyChanged;
            if (handler != null)
            {
                var e = new PropertyChangedEventArgs(prop);
                handler(this, e);
            }
        }
    }
Run Code Online (Sandbox Code Playgroud)

Cle*_*ens 6

设置TextBox.Text属性时未更新ViewModel属性的原因是Binding 的UpdateSourceTrigger属性设置为LostFocus.这是TextBox.Text属性上绑定的默认值.

如果将其更改为PropertyChanged,ViewModel属性将按预期更新:

<TextBox Text="{Binding ConfigurationPath, UpdateSourceTrigger=PropertyChanged}"/>
Run Code Online (Sandbox Code Playgroud)

当然,WPF绑定系统会注意避免无限更新循环.