目前,我试图在FlowDocument环境中模仿ContentControl控件的行为。我喜欢ContentControl,因为它允许根据内容的类型在不同的模板中显示内容。 E.g:
<ContentControl Content={Binding}/>
将使用在ResourceDictionary的XAML中定义的DataTemplates:
<DataTemplate DataType={x:Type local:Person}>...</DataType>
<DataTemplate DataType={x:Type local:Pet}>...</DataType>
现在为我的FlowDocument替代方案复制此行为,我开始搜索互联网。我遇到了Create Flexible UIs With Flow Documents And Data Binding这真的帮了很多忙。作为开始,我按如下方式更改了ItemsContent:
public class TemplatedContent : Section
{
private static readonly DependencyProperty ContentProperty = DependencyProperty.Register("Content", typeof(object), typeof(TemplatedContent), new PropertyMetadata(OnContentChanged));
private static readonly DependencyProperty TemplateProperty = DependencyProperty.Register("Template", typeof(DataTemplate), typeof(TemplatedContent), new PropertyMetadata(OnTemplateChanged));
public TemplatedContent()
{
//Helpers.FixupDataContext(this);
Loaded += TemplatedContent_Loaded;
}
private void TemplatedContent_Loaded(object sender, RoutedEventArgs e)
{
GenerateContent(Template, Content);
}
public object Content
{
get { return GetValue(ContentProperty); }
set { SetValue(ContentProperty, value); }
}
public DataTemplate Template
{
get { return (DataTemplate)GetValue(TemplateProperty); }
set { SetValue(TemplateProperty, value); }
}
private void GenerateContent(DataTemplate template, object content)
{
Blocks.Clear();
if (template != null && content != null)
{
FrameworkContentElement element = Helpers.LoadDataTemplate(template);
element.DataContext = content;
//Helpers.UnFixupDataContext(element);
Blocks.Add(Helpers.ConvertToBlock(content, element));
}
}
private void GenerateContent()
{
GenerateContent(Template, Content);
}
private void OnContentChanged(object newValue)
{
if (IsLoaded)
GenerateContent(Template, newValue);
}
private void OnTemplateChanged(DataTemplate newValue)
{
if (IsLoaded)
GenerateContent(newValue, Content);
}
private static void OnContentChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
((TemplatedContent)d).OnContentChanged(e.NewValue);
}
private static void OnTemplateChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
((TemplatedContent)d).OnTemplateChanged((DataTemplate)e.NewValue);
}
}
正如您所看到的那样,这是一个非常基本的代码安静,当我以下列方式使用它时,它可以按预期工作:
<FlowDocument>
<local:TemplatedContent Content={Binding}>
<local:TemplatedContent.Template>
<DataTemplate DataType={x:Type local:Person}>...</DataTemplate>
</local:TemplatedContent.Template>
</local:TemplatedContent>
</FlowDocument>
这很好但是为了支持不同内容类型的多个模板,我需要在资源字典中定义DataTemplates:
<FlowDocument>
<local:TemplatedContent Content={Binding}>
</local:TemplatedContent>
</FlowDocument>
并在资源词典中高高举起:
<DataTemplate DataType={x:Type local:Person}>...</DataTemplate>
现在,TemplatedContent无法找到DataTemplate。这怎么可能?如果我正确理解DependencyProperty的理论,它应该在xaml树中查找与内容类型匹配的条目吗?它没有。在线设置断点时:
private static void OnTemplateChanged
它从未被召唤过。
我希望你的专家可以帮助我进一步解决这个问题!
提前多多谢意!
答案 0 :(得分:0)
您需要在资源字典中定义模板,如下所示:
<FlowDocument>
<FlowDocument.Resources>
<DataTemplate x:Key="MyDataTemplate">
<!-- Contents of template go here -->
</DataTemplate>
</FlowDocument.Resources>
<!-- document content here -->
</FlowDocument>
现在使用StaticResource
标记扩展程序完成对模板的引用:
<local:TemplateContent Content="{Binding}" Template="{StaticResource MyDataTemplate}" />
希望这有帮助!