【发布时间】:2014-11-14 14:09:23
【问题描述】:
我创建了一个自定义控件,它继承自 DataGrid,并以与 HeaderedContentControl 具有标题相同的方式添加标题属性。
[Bindable(true)]
public Object Header
{
get { return (Object)GetValue(HeaderProperty); }
set { SetValue(HeaderProperty, value); }
}
// Using a DependencyProperty as the backing store for Header. This enables animation, styling, binding, etc...
public static readonly DependencyProperty HeaderProperty =
DependencyProperty.Register("Header", typeof(Object), typeof(ExtendedDataGrid), new PropertyMetadata(null, HeaderProperty_Changed));
private static void HeaderProperty_Changed(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
ExtendedDataGrid ctrl = (ExtendedDataGrid)d;
ctrl.OnHeaderChanged(e.OldValue, e.NewValue);
}
protected virtual void OnHeaderChanged(object oldValue, object newValue)
{
RemoveLogicalChild(oldValue);
AddLogicalChild(newValue);
}
控件模板将 ContentPresenter 内容绑定到 HeaderProperty。 (这是在 DataGrid ControlTemplate 内的 Scrollviewer ControlTemplate 内,所以我不能使用 ContentSource)
<ContentPresenter Grid.Row="0" Grid.ColumnSpan="99"
Margin="0"
Content="{Binding Header, RelativeSource={RelativeSource AncestorType{x:Type extended:ExtendedDataGrid}}}"/>
内容已正确设置为 header 属性。
我发现内容展示器没有继承DataGrid DataContext,所以我必须单独设置DataContext。这意味着标头内的任何绑定都不会按预期绑定,因为标头中所有元素的 DataContext 为空。我可以从 ContentPresenter 实现中看到,它在 Initialise 时专门将 DataContext 设置为 null,所以我明白为什么会发生这种情况。
问题
但是,我不明白并且我有兴趣知道的部分是,许多其他控件中的 ContentPresenter 元素如何正确继承 DataContext 而没有(据我所见)任何不同的代码/xaml?例如 Button ContentPresenter 或 HeaderContentControl ContentPresenters。
【问题讨论】:
-
在控制模板中你必须使用
TemplateBinding。 -
请解释这对我有什么帮助。正如我所说,ContentPresenter 在 ScrollViewer ControlTemplate 内,因此 TemplateBinding 会给我不正确的结果。
-
ButtonsContentPresenter正在使用TemplateBinding(100% 确定)。我试图了解您可能会问什么(如果这不是绑定问题)并且无法理解;)@ 987654331@?可以设置yes,被Button继承,但在Button控件模板中没有使用。那么再一次,你的问题是什么? -
问题是关于 ContentPresenter 上的 DataContext,如果您查看默认的 Button Style msdn.microsoft.com/en-us/library/ms753328(v=vs.110).aspx ContentPresenter 没有 DataContext 或 Content 集。我知道找到内容是因为 ContentPresenter 的默认 ContentSource 是 Content,但我不知道 DataContext 如何正确地从父级(在本例中为按钮)继承,但它不在我的示例 ContentPresenter 上。