【发布时间】:2011-04-09 01:55:59
【问题描述】:
我们刚刚开始使用 XAML,但仍在与基本问题作斗争: 来自 CSS,我们希望使用自定义控件模板定义通用按钮样式,然后使用“基于”让第二个样式继承第一个样式的所有内容。然后,第二个样式应该覆盖诸如“前景色”之类的属性(有效)还有我们自定义模板中子元素的属性,例如包含的边框元素的“背景颜色”等(这不起作用)。
处理此类事情的一般方法是什么?层叠样式可以走多远?
干杯!
【问题讨论】:
我们刚刚开始使用 XAML,但仍在与基本问题作斗争: 来自 CSS,我们希望使用自定义控件模板定义通用按钮样式,然后使用“基于”让第二个样式继承第一个样式的所有内容。然后,第二个样式应该覆盖诸如“前景色”之类的属性(有效)还有我们自定义模板中子元素的属性,例如包含的边框元素的“背景颜色”等(这不起作用)。
处理此类事情的一般方法是什么?层叠样式可以走多远?
干杯!
【问题讨论】:
您可以使用没有键引用的继承样式:
<Grid>
<Grid.Resources>
<!-- Definition of default appearance of a button -->
<Style TargetType="Button" x:Key="Default">
<Setter Property="Background" Value="Red"></Setter>
<Setter Property="FontFamily" Value="Segoe Black" />
<Setter Property="HorizontalAlignment" Value="Center" />
<Setter Property="FontSize" Value="32pt" />
<Setter Property="Foreground" Value="#777777" />
</Style>
<!-- Define general style that based is base on the default style of the button without a key reference-->
<Style TargetType="Button" BasedOn="{StaticResource Default}"/>
<!-- In sub style override the properties you need -->
<Style BasedOn="{StaticResource Default}" TargetType="Button" x:Key="SubButton" >
<Setter Property="FontSize" Value="8pt" />
</Style>
</Grid.Resources>
<Button Content="Main" Height="51" HorizontalAlignment="Left" Margin="154,72,0,0" Name="button1" VerticalAlignment="Top" Width="141" />
<Button Content="Sub" Style="{StaticResource SubButton}" Height="51" HorizontalAlignment="Left" Margin="154,162,0,0" Name="button2" VerticalAlignment="Top" Width="141" />
</Grid>
【讨论】:
我有(在我的 WPF 应用程序中)在 App.xaml 的 ResourceDictionary 中定义的默认(基本)样式(在启动项目中)。例如如下按钮。
<Style TargetType="Button">
<Setter Property="Margin" Value="5"/>
<Setter Property="FontWeight" Value="DemiBold"/>
<Setter Property="FontSize" Value="16"/>
</Style>
在所有视图中,我都使用(默认)这种通用样式(自动继承)!当我需要更改或添加一些默认样式(在 App.xaml 中定义)的属性时,我会根据默认样式创建新样式。
<Style TargetType="Button" BasedOn="{StaticResource {x:Type Button}}">
<!-- change -->
<Setter Property="Margin" Value="10" />
<!-- add -->
<Setter Property="Foreground" Value="Red" />
</Style>
当我需要隐藏或强烈重新定义默认样式(在某些视图中)时,我会创建新样式(基于任何内容)。
<Style TargetType="Button"/>
当然,您可以在 App.xaml 或特定视图中继续继承。您可以基于默认样式创建新的 named 样式,并按名称使用新样式。例如 RedButton 和 GreenButton 样式。
<Style TargetType="Button" BasedOn="{StaticResource {x:Type Button}}" x:Key="RedButton">
<Setter Property="Foreground" Value="Red" />
</Style>
<Style TargetType="Button" BasedOn="{StaticResource {x:Type Button}}" x:Key="GreenButton">
<Setter Property="Foreground" Value="Green" />
</Style>
等等……
注意:改为在 App.xaml 中定义您的样式,您可以使用仅包含样式的独立库 (dll) 以及从您的库到 App.xaml ResourceDictionary.MergedDictionaries 的 ResourceDictionary。
【讨论】:
制作可自定义控件模板的标准方法是在模板中使用 TemplateBinding 绑定到控件的属性,然后在子样式中设置这些属性。
例如,这将创建一个带有边框控件的按钮模板,并将边框的背景绑定到按钮的背景属性。通过设置其他样式的Button 的Background 属性,可以改变Border 的Background 属性。
<StackPanel>
<StackPanel.Resources>
<Style x:Key="BaseButtonStyle" TargetType="Button">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="Button">
<Border
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
Background="{TemplateBinding Background}">
<ContentPresenter/>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="BlueButtonStyle" TargetType="Button"
BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Background" Value="Blue"/>
</Style>
<Style x:Key="RedButtonStyle" TargetType="Button"
BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Background" Value="Red"/>
</Style>
</StackPanel.Resources>
<Button Style="{StaticResource RedButtonStyle}">Red</Button>
<Button Style="{StaticResource BlueButtonStyle}">Blue</Button>
</StackPanel>
Control 上的许多属性旨在用于控件模板,如果更改它们不会影响其他行为。它们是 BorderBrush、BorderThickness、Background、Padding、HorizontalContentAlignment 和 VerticalContentAlignment。
【讨论】: