未设置DataContext时发生WPF绑定问题
我已经成功地创建了许多具有各种功能的UserControl,并将每个控件上的DataContext设置为'this'。 当我试图将它们分成更小的“内部”UserControl时,我总是会遇到问题。 问题是这样的:
当DataContext设置为'this'时,我可以绑定到后面的代码中的属性 - 他们不必是DependencyProperties。 当绑定到普通属性时,程序执行会在后面输入代码,我可以在其中执行像切换ListBox项目或其他我不能在xaml中执行的操作。
但是,当我创建一个新的'内部'用户控件在原始控件中托管并将这些属性移动到内部控件时,我现在必须将它们升级为DependencyProperties,以便我可以将它们从原始控件绑定到它们。 绑定到DependencyProperties时,程序执行永远不会输入代码,对我而言,这是问题所在。 顺便说一下,我不在内部控件中设置DataContext,而是设置根元素的Name属性,并在内部控件属性的绑定中使用ElementName = UserControlName语法。
我知道我可以将一个ValidateValueCallbackHandler添加到DependencyProperty中,以便在绑定值更改时访问后面的代码,但它必须是静态方法,所以我无法访问任何非静态成员(即我的整个类) 。
一个例子是我有一个DurationPicker控件,它在ListBoxes中显示TimeSegments对象。 TimeSegments对象基本上是TimeSegment对象的ObservableCollection,TimeSegment具有StartDate,EndDate和Duration属性。 我在DurationPicker控件中有一个MinutesPerSegment属性,该属性绑定到ComboBox的值。 它工作完美。 我可以更改ComboBox值,并且后面的代码会将正确数量的TimeSegment对象与正确的新值放在ListBox中。
然后我创建了包含TimeSegments对象和ListBox的内部控件来显示它。 现在MinutesPerSegment属性必须成为DependencyProperty,以便我可以从外部控件绑定到它,并且程序执行永远不会输入代码,所以现在我无法更改集合中的TimeSegment对象的数量。
还有一件事要注意。 我可以成功绑定到来自外部控件的内部控件的DependencyProperties - 我可以看到UI中显示的更改。 问题在于我需要执行程序来在更新某些绑定属性时输入代码。
什么是正确的方法来做到这一点? 非常感谢。
编辑 - 在这个例子中,如果我在外部控件中创建TimeSegments对象并将它们绑定到内部控件,那么它仍然可以工作。 这是因为外部控件中的MinutesPerSegment属性是一个普通属性...但是,我希望每个TimeSegments对象都在它自己的内部TimeSegmentsRow控件中处理......所以这个问题。
首先,你不需要设置DataContext
来this
只是为了使结合您的自定义控件的属性。 如果有人决定为您的控件设置另一个数据上下文,这是一个坏主意。 您可以使用相对绑定。
{Binding Path=PathToProperty,
RelativeSource={RelativeSource AncestorType=
{x:Type namespaceAlias:typeOfYourControl}}}
并在xaml中为您的自定义控件声明名称空间别名
xmlns:namespaceAlias="clr-namespace:YourLibraryNamespace;assembly=YourLibraryAssemblyName"
其次,wpf不会使用你的属性getter和setter来访问你的依赖属性,这就是为什么除了GetValue
和SetValue
之外不应该有任何额外的逻辑。 注册属性时可以指定PropertyChangedCallback,以便在属性更改时添加一些逻辑。
上一篇: WPF Binding problems when not setting DataContext
下一篇: WPF binding not applying to target after initialization