c# - 在后面的代码中设置 DataContext 的顺序

标签 c# .net wpf data-binding

在代码隐藏中设置 DataContext 的正确方法是:

public ViewConstructor()
{
    InitializeComponent();
    DataContext = new MyViewModel();
}

public ViewConstructor()
{
    DataContext = new MyViewModel();
    InitializeComponent();
}

?

最佳答案

回答是:视情况而定

如果您的屏幕包含大量数据或复杂的数据驱动可视化,您可能希望推迟或错开其加载,这可能会使第一个选项更好。如果它是一个简单的数据绑定(bind)表单,则第二个选项可能更可取。或者它甚至可以忽略不计。一如既往,测量是在您的特定条件下回答问题的最佳方式。

让我们看看通过对绑定(bind)启用跟踪会发生什么。

<Window x:Class="WpfApplication9.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
    <Grid IsEnabled="{Binding IsEnabled, PresentationTraceSources.TraceLevel=High}" />
</Window>

第一个选项 - InitializeComponent 首先

public MainWindow()
{
    Debug.WriteLine("Initializing");
    InitializeComponent();
    Debug.WriteLine("Initialized");
    Debug.WriteLine("Setting DataContext");
    DataContext = new ViewModel();
    Debug.WriteLine("DataContext Set");
}

这里我们看到在 InitializeComponent 期间(加载 XAML 时)绑定(bind)尝试解析,但看到 DataContext 为 null,因此它们的评估是 推迟

调试输出:

Initializing
System.Windows.Data Warning: 56 : Created BindingExpression (hash=55924514) for Binding (hash=26055869)
System.Windows.Data Warning: 58 :   Path: 'IsEnabled'
System.Windows.Data Warning: 60 : BindingExpression (hash=55924514): Default mode resolved to OneWay
System.Windows.Data Warning: 61 : BindingExpression (hash=55924514): Default update trigger resolved to PropertyChanged
System.Windows.Data Warning: 62 : BindingExpression (hash=55924514): Attach to System.Windows.Controls.Grid.IsEnabled (hash=21411931)
System.Windows.Data Warning: 67 : BindingExpression (hash=55924514): Resolving source 
System.Windows.Data Warning: 70 : BindingExpression (hash=55924514): Found data context element: Grid (hash=21411931) (OK)
System.Windows.Data Warning: 71 : BindingExpression (hash=55924514): DataContext is null
System.Windows.Data Warning: 65 : BindingExpression (hash=55924514): Resolve source deferred
Initialized
Setting DataContext
DataContext Set
System.Windows.Data Warning: 67 : BindingExpression (hash=55924514): Resolving source 
System.Windows.Data Warning: 70 : BindingExpression (hash=55924514): Found data context element: Grid (hash=21411931) (OK)
System.Windows.Data Warning: 78 : BindingExpression (hash=55924514): Activate with root item ViewModel (hash=45063479)
System.Windows.Data Warning: 108 : BindingExpression (hash=55924514):   At level 0 - for ViewModel.IsEnabled found accessor ReflectPropertyDescriptor(IsEnabled)
System.Windows.Data Warning: 104 : BindingExpression (hash=55924514): Replace item at level 0 with ViewModel (hash=45063479), using accessor ReflectPropertyDescriptor(IsEnabled)
System.Windows.Data Warning: 101 : BindingExpression (hash=55924514): GetValue at level 0 from ViewModel (hash=45063479) using ReflectPropertyDescriptor(IsEnabled): 'False'
System.Windows.Data Warning: 80 : BindingExpression (hash=55924514): TransferValue - got raw value 'False'
System.Windows.Data Warning: 89 : BindingExpression (hash=55924514): TransferValue - using final value 'False'

第二个选项 - 首先设置 DataContext

public MainWindow()
{
    Debug.WriteLine("Setting DataContext");
    DataContext = new ViewModel();
    Debug.WriteLine("DataContext Set");
    Debug.WriteLine("Initializing");
    InitializeComponent();
    Debug.WriteLine("Initialized");
}

此处绑定(bind)在初始化期间立即求值。

调试输出:

Setting DataContext
DataContext Set
Initializing
System.Windows.Data Warning: 56 : Created BindingExpression (hash=27331439) for Binding (hash=41386841)
System.Windows.Data Warning: 58 :   Path: 'IsEnabled'
System.Windows.Data Warning: 60 : BindingExpression (hash=27331439): Default mode resolved to OneWay
System.Windows.Data Warning: 61 : BindingExpression (hash=27331439): Default update trigger resolved to PropertyChanged
System.Windows.Data Warning: 62 : BindingExpression (hash=27331439): Attach to System.Windows.Controls.Grid.IsEnabled (hash=16919637)
System.Windows.Data Warning: 67 : BindingExpression (hash=27331439): Resolving source 
System.Windows.Data Warning: 70 : BindingExpression (hash=27331439): Found data context element: Grid (hash=16919637) (OK)
System.Windows.Data Warning: 78 : BindingExpression (hash=27331439): Activate with root item ViewModel (hash=25445597)
System.Windows.Data Warning: 108 : BindingExpression (hash=27331439):   At level 0 - for ViewModel.IsEnabled found accessor ReflectPropertyDescriptor(IsEnabled)
System.Windows.Data Warning: 104 : BindingExpression (hash=27331439): Replace item at level 0 with ViewModel (hash=25445597), using accessor ReflectPropertyDescriptor(IsEnabled)
System.Windows.Data Warning: 101 : BindingExpression (hash=27331439): GetValue at level 0 from ViewModel (hash=25445597) using ReflectPropertyDescriptor(IsEnabled): 'False'
System.Windows.Data Warning: 80 : BindingExpression (hash=27331439): TransferValue - got raw value 'False'
System.Windows.Data Warning: 89 : BindingExpression (hash=27331439): TransferValue - using final value 'False'
Initialized

关于c# - 在后面的代码中设置 DataContext 的顺序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38524555/

相关文章:

C# - 抽象类扩展类和 new()?

javascript - IE文件上传问题

wpf - 使用MVVM在WPF中选择列表框的项目

c# - WPF 绑定(bind)列表框主/细节

wpf - 部署 WPF 应用程序时包括 xml 文件

c# - Controller.File() 的有效内容类型是什么?

c# - 何时使用 "async"而不是返回新的 Task.Run 任务?

c# - 模板控件中的 ContentPresenter 不起作用

.net - 用于创建类和将类移动到新文件的 Resharper 快捷方式

.net - 使用功能区作为选项卡控件