具有多个文本块的 XAML 样式按钮
本文关键字:XAML 样式 按钮 文本 | 更新日期: 2023-09-27 18:32:59
我设计了一个包含两个TextBlock
的Button
元素。一个带有实际文本,另一个带有图标(来自Segoe UI符号)。
这是样式的代码:
<Style x:Key="ButtonSettingsStyle" TargetType="Button">
<Setter Property="Content" Value=""/>
<Setter Property="Background" Value="Transparent"/>
<Setter Property="Foreground" Value="White"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="Button">
<StackPanel Background="Transparent" Orientation="Horizontal" Height="60">
<VisualStateManager.VisualStateGroups>
...
</VisualStateManager.VisualStateGroups>
<TextBlock
x:Name="Icon"
Text=""
Margin="10,0,5,0"
Width="40"
Foreground="{TemplateBinding Foreground}"
FontSize="32"
VerticalAlignment="Center"
RenderTransformOrigin="0.5,0.5"
FontFamily="Segoe UI Symbol"></TextBlock>
<TextBlock
x:Name="Text"
Text="{TemplateBinding Content}"
VerticalAlignment="Center"
Style="{StaticResource TextBlockListBoldItem}"
Foreground="{TemplateBinding Foreground}" />
</StackPanel>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
问题:
我还希望 Icon-TextBlock 有一个自定义图标,因此是一个自定义Text
属性,并且可能像这样使用(我真的不知道这应该如何工作):
<Button Style="{StaticResource ButtonSettingsStyle}" Content="Settings" IconContent="" />
我怎样才能做到这一点?Content
-Setter 已经分配给 Text-TextBlock ...
感谢您的帮助!
编辑:我同意@meilke评论,但问题是你需要一个依赖属性来设置模板绑定,所以请参阅下面的新类 ButtonWithIcon
您应该从 Button 继承并添加一个名为 IconContent 的依赖项属性:
public class ButtonWithIcon : Button
{
public static readonly DependencyProperty IconContentProperty =
DependencyProperty.Register("IconContent", typeof (string), typeof (ButtonWithIcon), new PropertyMetadata(default(Icon)));
public string IconContent
{
get { return (string) GetValue(IconContentProperty); }
set { SetValue(IconContentProperty, value); }
}
}
并像这样使用它:
<Style x:Key="ButtonSettingsStyle" TargetType="local:ButtonWithIcon">
<Setter Property="Content" Value=""/>
<Setter Property="Background" Value="Transparent"/>
<Setter Property="Foreground" Value="White"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="local:ButtonWithIcon">
<StackPanel Background="Transparent" Orientation="Horizontal" Height="60">
<VisualStateManager.VisualStateGroups>
...
</VisualStateManager.VisualStateGroups>
<TextBlock
x:Name="Icon"
Text="{Binding IconContent, RelativeSource={RelativeSource TemplatedParent}}"
Margin="10,0,5,0"
Width="40"
Foreground="{TemplateBinding Foreground}"
FontSize="32"
VerticalAlignment="Center"
RenderTransformOrigin="0.5,0.5"
FontFamily="Segoe UI Symbol"></TextBlock>
<TextBlock
x:Name="Text"
Text="{TemplateBinding Content}"
VerticalAlignment="Center"
Style="{StaticResource TextBlockListBoldItem}"
Foreground="{TemplateBinding Foreground}" />
</StackPanel>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<local:ButtonWithIcon Style="{StaticResource ButtonSettingsStyle}" Content="Settings" IconContent="" />
如果不想对 Button 进行子类化以添加自己的属性,则可以使用 Tag 属性或附加属性。
请注意,如果使用附加属性,则需要绑定到TemplatedParent
而不是使用 TemplateBinding
:
{Binding RelativeSource={RelativeSource Mode=TemplatedParent},
Path=local:AttachedProperties.IconContent}
我不知道你为什么要限制你的按钮只接受文本。通常,按钮接受任何内容并使用内容演示器。就个人而言,我会将 IconContent 属性键入为object
并像这样定义模板:
<ContentPresenter x:Name="Icon" Content="{TemplateBinding IconContent}" />
<ContentPresenter x:Name="Text" />
然后像这样设置:
<Button>
<Button.IconContent>
<TextBlock Style="{StaticResource IconTextBlockStyle}" Text="" />
</Button.IconContent>
</Button>
具有自定义属性的子类Button
IconContent
来实现这一点。
这是新类:
public class MyButton : Button
{
public static readonly DependencyProperty IconContentProperty =
DependencyProperty.Register("IconContent", typeof (string), typeof (ButtonWithIcon), new PropertyMetadata(default(Icon)));
public string IconContent
{
get { return (string) GetValue(IconContentProperty); }
set { SetValue(IconContentProperty, value); }
}
}
以下是调整后的样式(请注意IconContent
的新TemplateBinding
):
<Style x:Key="ButtonSettingsStyle" TargetType="local:MyButton">
<Setter Property="Content" Value=""/>
<Setter Property="Background" Value="Transparent"/>
<Setter Property="Foreground" Value="White"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="local:MyButton">
<StackPanel Background="Transparent" Orientation="Horizontal" Height="60">
<VisualStateManager.VisualStateGroups>
...
</VisualStateManager.VisualStateGroups>
<TextBlock
x:Name="Icon"
Text="{TemplateBinding IconContent}"
Margin="10,0,5,0"
Width="40"
Foreground="{TemplateBinding Foreground}"
FontSize="32"
VerticalAlignment="Center"
RenderTransformOrigin="0.5,0.5"
FontFamily="Segoe UI Symbol"></TextBlock>
<TextBlock
x:Name="Text"
Text="{TemplateBinding Content}"
VerticalAlignment="Center"
Style="{StaticResource TextBlockListBoldItem}"
Foreground="{TemplateBinding Foreground}" />
</StackPanel>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
这是用法:
<local:MyButton Style="{StaticResource ButtonSettingsStyle}" Content="Settings" IconContent="" />