WPF - 使用变量/参数创建可重用的样式 [英] WPF - Create reusable style with variables/parameters
问题描述
我有一个包含多个 TabItem 的 WPF 应用程序.每个 TabItem 彼此不同,有一个文本和一个图标.
I have an WPF application which contains several TabItems. Each TabItem is different from each other, with a text and an icon.
TabItem 的样式是这样定义的:
This is how the TabItem´s style is defined:
<TabItem.Style>
<Style TargetType="TabItem">
<Setter Property="Header">
<Setter.Value>
<StackPanel Orientation="Horizontal">
<Image Margin="10,0,0,0" Height="40" Width="40" Source="Images/IconLeafGrey.png"/>
<TextBlock Text="This is the heading" VerticalAlignment="Center" Style="{StaticResource Heading2}" Margin="10,0,0,0"/>
</StackPanel>
</Setter.Value>
</Setter>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type TabItem}">
<Grid>
<Border Name="Border" BorderBrush="Black" BorderThickness="1,1,1,1" CornerRadius="6,6,0,0" >
<Border.Background>
<LinearGradientBrush StartPoint="0.5,0" EndPoint="0.5,1">
<GradientStop Color="#f5f7f8" Offset="0.0" />
<GradientStop Color="#c5d0dd" Offset="1.0" />
</LinearGradientBrush>
</Border.Background>
<ContentPresenter Name="ContentSite" VerticalAlignment="Center" HorizontalAlignment="Left" ContentSource="Header" Margin="5,2,0,2"/>
</Border>
</Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" TargetName="Border">
<Setter.Value>
<LinearGradientBrush StartPoint="0.5,0" EndPoint="0.5,1">
<LinearGradientBrush.GradientStops>
<GradientStop Color="#ebedee" Offset="0.0" />
<GradientStop Color="#88a2bd" Offset="1.0" />
</LinearGradientBrush.GradientStops>
</LinearGradientBrush>
</Setter.Value>
</Setter>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Header">
<Setter.Value>
<StackPanel Orientation="Horizontal">
<Image Margin="10,0,0,0" Height="40" Width="40" Source="Images/IconLeaf.png"/>
<TextBlock Text="This is the heading" VerticalAlignment="Center" Style="{StaticResource Heading2}" Margin="10,0,0,0"/>
</StackPanel>
</Setter.Value>
</Setter>
</Trigger>
</Style.Triggers>
</Style>
</TabItem.Style>
因此,我不想为每个 TabItem 编写这个 XAML 标记,而是想在我的 ResourceDictionary 中定义一次这种样式,但将 Icon 和 Text 属性作为可选参数.所以我之后可以像这样定义一个 TabItem:
So instead of writing this XAML markup for each TabItem, I would like to define this style once in my ResourceDictionary, but with the Icon and the Text property as optional parameters. So I afterwards could define a TabItem like this:
<TabItem Width="250" Height="60" Style="{StaticResource CustomTabItem}" >
我读过,样式不能直接接受这样的参数,但应该可以通过某种绑定来实现.我还没有找到确切的方法,所以我真的希望你能帮忙.
I´ve read that it isnt directly possible for a style to accept parameters like this, but it should be posible with some sort of binding. I havent found out exactly how though, so I really hope you can help.
亲切的问候.
推荐答案
一种方法是,如果您有固定数量的 TabItems
并且不想生成 TabItems
通过 ItemsSource
Binding
在 TabControl 上.然后在您的 TabItem.Style
中,您可以使用 Resource
键来获取文本和来源,例如:
One way of doing it would be, if you have fixed number of TabItems
and you dont want to generate the TabItems
through ItemsSource
Binding
on TabControl. Then in your TabItem.Style
you can use Resource
keys to get the Text and Source like:
<StackPanel Orientation="Horizontal">
<Image Margin="10,0,0,0" Height="40" Width="40" Source="{DynamicResource Image1}"/>
<TextBlock Text="{DynamicResource Header}" VerticalAlignment="Center" Style="{StaticResource Heading2}" Margin="10,0,0,0"/>
</StackPanel>
对于您的 TabItems,您可以定义这些资源:
and for your TabItems you can define these resources:
<TabItem Width="250" Height="60" Style="{StaticResource CustomTabItem}">
<TabItem.Resources>
<System:String x:Key="Header">TabItem1</System:String>
<System:String x:Key="Image1">image/1.png</System:String>
<System:String x:Key="Image2">image/2.png</System:String>
</TabItem.Resources>
</TabItem>
<TabItem Width="250" Height="60" Style="{StaticResource CustomTabItem}">
<TabItem.Resources>
<System:String x:Key="Header">TabItem2</System:String>
<System:String x:Key="Image1">image/3.png</System:String>
<System:String x:Key="Image2">image/4.png</System:String>
</TabItem.Resources>
</TabItem>
此外,您还需要更新您的 Style
以设置 HeaderTemplate
而不是 Header
Also you will need to update your Style
to set the HeaderTemplate
instead of Header
<Style x:Key="CustomTabItem" TargetType="TabItem">
<Setter Property="HeaderTemplate">
<Setter.Value>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Image x:Name="HeaderImage" Margin="10,0,0,0" Height="40" Width="40" Source="Images/IconLeafGrey.png"/>
<TextBlock Text="{DynamicResource Header}" VerticalAlignment="Center" Margin="10,0,0,0"/>
</StackPanel>
<DataTemplate.Triggers>
<DataTrigger Binding="{Binding IsSelected, RelativeSource={RelativeSource AncestorType={x:Type TabItem}}}" Value="true">
<Setter TargetName="HeaderImage" Property="Source" Value="Images/IconLeaf.png"/>
</DataTrigger>
</DataTemplate.Triggers>
</DataTemplate>
</Setter.Value>
</Setter>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type TabItem}">
<Grid>
<Border Name="Border" BorderBrush="Black" BorderThickness="1,1,1,1" CornerRadius="6,6,0,0" >
<Border.Background>
<LinearGradientBrush StartPoint="0.5,0" EndPoint="0.5,1">
<GradientStop Color="#f5f7f8" Offset="0.0" />
<GradientStop Color="#c5d0dd" Offset="1.0" />
</LinearGradientBrush>
</Border.Background>
<ContentPresenter Name="ContentSite" VerticalAlignment="Center" HorizontalAlignment="Left" ContentSource="Header" Margin="5,2,0,2"/>
</Border>
</Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="Background" TargetName="Border">
<Setter.Value>
<LinearGradientBrush StartPoint="0.5,0" EndPoint="0.5,1">
<LinearGradientBrush.GradientStops>
<GradientStop Color="#ebedee" Offset="0.0" />
<GradientStop Color="#88a2bd" Offset="1.0" />
</LinearGradientBrush.GradientStops>
</LinearGradientBrush>
</Setter.Value>
</Setter>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
这篇关于WPF - 使用变量/参数创建可重用的样式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!