WPF TemplateBinding vs RelativeSource TemplatedParent
这两个绑定有什么区别 :
<ControlTemplate TargetType="{x:Type Button}"> <Border BorderBrush="{TemplateBinding Property=Background}"> <ContentPresenter /> </Border> </ControlTemplate>
和
<ControlTemplate TargetType="{x:Type Button}"> <Border BorderBrush="{Binding RelativeSource={RelativeSource TemplatedParent}, Path=Background}"> <ContentPresenter /> </Border> </ControlTemplate>
?
TemplateBinding是不完全相同的事情。 MSDN文档通常由需要testing单音节软件特性的软件特性的人撰写,因此细微之处不太正确。
在编译时根据控件模板中指定的types来评估TemplateBindings。 这允许编译模板更快的实例化。 只要摸索模板绑定的名称,你会看到编译器会标记它。
绑定标记在运行时parsing。 虽然执行速度较慢,但绑定将parsing在模板声明的types上不可见的属性名称。 由于速度较慢,我将指出它的相对性,因为绑定操作占用的应用程序的CPU很less。 如果你在高速爆炸控制模板,你可能会注意到它。
作为练习的问题,尽可能使用TemplateBinding,但不要害怕Binding。
TemplateBinding – 比使用常规绑定更有限制
- 比绑定更高效,但function更less
- 只在ControlTemplate的可视化树内工作
- 不适用于Freezables上的属性
- 在ControlTemplate的触发器中不起作用
- 提供设置属性的快捷方式(而不是详细),例如{TemplateBinding targetProperty}
常规绑定 – 不具有TemplateBinding的上述限制
- 尊重父项属性
- 重置目标值以清除任何显式设置的值
- 例如:<Ellipse Fill =“{Binding RelativeSource = {RelativeSource TemplatedParent},Path = Background}”/>
还有一件事 – TemplateBindings不允许值转换。 他们不允许你通过一个转换器,并不会自动将int转换为string,例如(这是正常的绑定)。
TemplateBinding是与TemplatedParent绑定的简写,但它不公开Binding类的所有function,例如,您无法从TemplateBinding控制Binding.Mode。
RelativeSource TemplatedParent
此模式可以将给定的ControlTemplate属性绑定到ControlTemplate所应用的控件的属性。 为了更好地理解这个问题,下面是一个例子
<Window.Resources> <ControlTemplate x:Key="template"> <Canvas> <Canvas.RenderTransform> <RotateTransform Angle="20"/> </Canvas.RenderTransform> <Ellipse Height="100" Width="150" Fill="{Binding RelativeSource={RelativeSource TemplatedParent}, Path=Background}"> </Ellipse> <ContentPresenter Margin="35" Content="{Binding RelativeSource={RelativeSource TemplatedParent},Path=Content}"/> </Canvas> </ControlTemplate> </Window.Resources> <Canvas Name="Parent0"> <Button Margin="50" Template="{StaticResource template}" Height="0" Canvas.Left="0" Canvas.Top="0" Width="0"> <TextBlock FontSize="22">Click me</TextBlock> </Button> </Canvas>
如果我想将给定控件的属性应用于其控件模板,那么我可以使用TemplatedParent模式。 这个标记扩展也是类似的,它是TemplateBinding,它是第一个的简写,但是TemplateBinding是在编译时在TemplatedParent的对比度下计算的,而TemplatedParent是在第一次运行时间之后被评估的。 正如你可以在下图所示,背景和内容是从button内部应用到控制模板。
我认为TemplateBinding不支持Freezabletypes(其中包括画笔对象)。 解决问题。 可以使用TemplatedParent
它们以类似的方式使用,但它们有一些差异。 这里是TemplateBinding文档的链接: http : //msdn.microsoft.com/en-us/library/ms742882.aspx