在ControlTemplate中扩展子元素

时间:2012-03-07 17:57:30

标签: wpf dependency-properties controltemplate expander

我正在尝试扩展Expander标题(ToggleButton部分)以允许更多自定义功能。使用ControlTemplates扩展WPF控件相当新,我现在已经接受了,我将不得不完全取代Expander的模板(不能重用原来定义的组件,甚至样式,这使得这很多在我看来很讨厌 - 但这不是问题所在。)

但是,我想介绍一些改变组件外观和工作方式的属性。所以我创建了一个新的Expander子类型,它只是定义了我想要使用的新依赖属性。但我注意到,鉴于我想在模板中使用ToggleButton中的那些属性,它们嵌套在Expander的内部,我不能使用那些属性。所以我也必须子类型ToggleButton,同样定义该类型的依赖属性,并使Expander的模板将值传递给ToggleButton模板。

所以我最终在命名空间中有两个新类型(在Expander子类型中嵌套新的ToggleButton类型不起作用?),Expander模板的完整副本只改变了一行(其中ToggleButton是插入,传递新属性),然后是ToggleButton模板的实际所需更改。

问题就出现了:有没有办法让这个变得不那么复杂?为了减少为扩展另一个模板的子组件而需要完成的工作量?或者只是一种在ToggleButton模板中使用父级(Expander)属性的方法,而不必对那个属性进行子类型化?

2 个答案:

答案 0 :(得分:0)

我总是谷歌的默认风格:扩展器风格wpf msdn。 这几乎总是引导我到适当的msdn页面,其中包含控件的默认controltemplate和样式。 这次它引导我:http://msdn.microsoft.com/en-us/library/ms753296(v=vs.85).aspx

编辑(澄清):

如果我需要更改复杂的样式控件,我会复制MSDN上提供的原始样式或示例样式,并在需要更改的位置更改它,因为它节省了我很多时间。 此外,我提供了这个样式的.NET 3.0版本的URL,并非没有理由。该风格的.NET 4版本使用VisualStateManager,这使得熟悉WPF的人的例子对于这种情况来说太复杂了,甚至Expression Blend 4也不生成VisualStateManager而只生成已知的触发器。 只是为了完整性: .NET 4:http://msdn.microsoft.com/en-us/library/ms753296(v=vs.100).aspx .NET 3.5:http://msdn.microsoft.com/en-us/library/ms753296(v=vs.90).aspx

答案 1 :(得分:0)

我最终使用了评论中建议的 jberger

使用以下绑定表达式我不需要将DependencyProperties复制到ToggleButton的另一个组件中,但只能访问嵌套模板中的Expander属性:

{Binding CustomProperty, RelativeSource={RelativeSource
    FindAncestor, AncestorType=local:CustomExpander}}

可悲的是,但正如预期的那样,显然无法重用默认的模板部件。但是在这种情况下,我可以省略原始模板中我在副本中不需要的部分。例如,非默认扩展的不同样式(即Top除外),因为我的扩展器专门用于该布局。

然而,这使得ExpandDirection属性无效,但我个人可以接受。这可能会导致一个后续问题;如果我们应该从头开始构建组件(基于Expander的基础,而不是Expander本身。)