如果我this
在构造函数和{Binding RelativeSource={RelativeSource Self}}
XAML中将 Window 的 DataContext 设置为,那么我可以通过在代码隐藏的 Loaded 事件中放置断点来看到 DataContext 引用正确的对象实例(即 MainWindow)。但是,Window 的子元素 exampleButton 的 Command 绑定为 null。断言失败。
当我删除 XAML DataContext 设置(并且仅依赖于构造函数设置)时,exampleButton 的命令会正确使用 DataContext。
为什么在 XAML 场景中 exampleButton 的 Command 绑定为 null?
主窗口.xaml
<Window x:Class="MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Example"
SizeToContent="WidthAndHeight"
x:Name="mainWindow"
DataContext="{Binding RelativeSource={RelativeSource Self}}"
Loaded="mainWindow_Loaded">
<Button x:Name="exampleButton" Command="{Binding Path=ExampleCommand}" Content="Click"/>
</Window>
主窗口.xaml.cs
public partial class MainWindow : Window
{
public ICommand ExampleCommand { get; }
public MainWindow()
{
InitializeComponent();
DataContext = this;
ExampleCommand = new DelegateCommand(x => { throw new ApplicationException(); });
}
private void mainWindow_Loaded(object sender, RoutedEventArgs e)
{
Debug.Assert(mainWindow == this);
Debug.Assert(mainWindow.DataContext == this);
Debug.Assert(exampleButton.DataContext == this);
Debug.Assert(exampleButton.Command == ExampleCommand); //<-- FAIL
}
}
为什么在 XAML 场景中 exampleButton 的 Command 绑定为 null?
因为在方法返回并设置该属性ExampleCommand
时,该属性实际上具有 null 值。InitializeComponent()
DataContext
如果您想在此之后将属性设置为新值,则该类必须实现INotifyPropertyChanged接口以使目标属性自动刷新:
public partial class MainWindow : Window, INotifyPropertyChanged
{
public MainWindow()
{
InitializeComponent();
ExampleCommand = new RelayCommand<object>(x => { throw new ApplicationException(); });
}
private ICommand _exampleCommand;
public ICommand ExampleCommand
{
get { return _exampleCommand; }
set { _exampleCommand = value; NotifyPropertyChanged(); }
}
private void mainWindow_Loaded(object sender, RoutedEventArgs e)
{
Debug.Assert(exampleButton.DataContext == this);
Debug.Assert(exampleButton.Command == ExampleCommand); //<-- FAIL
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
{
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句