强制DataTemlate返回特定对象

时间:2017-09-22 17:42:34

标签: c# wpf custom-controls

我正在编写一个新的WPF控件来绘制和编辑很多形状,比方说成千上万。为此,我想让用户为他的数据定义DataTemplate。但此特定LoadContent DataTemplate必须返回特定类型IShape。我怎样才能做到这一点?

2 个答案:

答案 0 :(得分:2)

首先,模板的重点是支持插入任意可视化树。如果您对模板的组成有严格的要求,那么使用模板是错误的设计选择。

其次,模板必须描述Visual。如果您要绘制数十万个形状,将无法将它们表示为视觉效果。视觉效果相当重要

  1. 他们参与输入命中测试。的(!)
  2. 他们拥有依赖对象的所有开销。
    1. 他们参与继承背景。
    2. 他们必须将属性更改传达给其父级,即对于影响布局和渲染的属性。
    3. 它们可能包含动态资源引用,它们必须遵守更改。
  3. 他们可能会扩展更重UIElement甚至更重 FrameworkElement,这意味着:
    1. 他们参与布局。的(!)
    2. 路由事件通过它们传递,并可由它们处理。
    3. 他们可能正在使用数据绑定。
  4. 作为替代方案,我建议您提供一个界面,通过该界面可以提供几何数据,您可以有效地冻结,共享,重用和渲染。这将允许您坚持使用WPF中可用的最低级别的图形API集。但是,老实说,即使这可能还不够好。

    但有一件事是肯定的:在Visual Layer中展示所有这些形状是不可能的。我至少会实现某种形式的虚拟化,你只能有效地定位视图中的那些形状(四叉树或类似的?),只渲染视图中的几何体(带剪切),并使用缓存组合来避免不断重绘;再嵌纹;如果没有实际发生任何变化,则对几何进行原始抗锯齿处理。

答案 1 :(得分:1)

LoadContent的{​​{1}}方法返回模板内容的根元素。因此,如果用户(消费者)已经在模板中将DataTemplate作为根元素进行了实际定义,它将仅返回IShape

但是你不能真正强迫你的类的消费者将IShape类型的属性设置为保证包含DataTemplate的{​​{1}}。消费者也可以将属性设置为DataTemplate,仅包含IShape

如果DataTemplate方法返回Button以外的任何内容,则可以在类中抛出InvalidOperationException 运行时。但是,您无法在编译时进行任何保证。但这就是LoadContent的工作方式。

也许您应该考虑让用户设置IShape属性而不是DataTemplates属性。您可以IShape(或DataTemplate)某种IShapeShape

毕竟,ContentControl模板,可能包含任何UserControl