【问题标题】:WPF Style with multiple contents具有多个内容的 WPF 样式
【发布时间】:2019-01-27 15:36:30
【问题描述】:

我创建了一个样式,它创建一个标签为一个圆圈,中间有文本。

<Style x:Key="RoundedLabelStyle" TargetType="{x:Type Label}">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="Label">
                <Grid Height="Auto" Width="Auto" HorizontalAlignment="{TemplateBinding HorizontalAlignment}" VerticalAlignment="{TemplateBinding VerticalAlignment}">
                    <Ellipse x:Name="cp" Margin="0,0,0,0" Fill="{TemplateBinding Background}" Height="{TemplateBinding Width}" Width="{TemplateBinding Width}" Stroke="Black" StrokeThickness="2" />
                    <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center">
                        <ContentPresenter.Content>
                            <Border Padding="10">
                                <ContentPresenter Content="{TemplateBinding Content}"/>                                            
                            </Border>
                        </ContentPresenter.Content>
                    </ContentPresenter>
                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

它是这样使用的:

<Label Style="{StaticResource RoundedButtonStyle}" Content="{Binding CountValue}" HorizontalAlignment="Center" VerticalAlignment="Center"  Background="Red" BorderBrush="Red" BorderThickness="3" Height="100" Width="100" FontSize="20" FontWeight="Bold" />

这很好用。

但是,我想通过在不同位置设置两个文本字段来向此标签添加更多信息。

  1. 第一个已经存在并显示在椭圆的中心。

  2. 我想添加一个显示在椭圆下方的。

如果可能的话,我希望能够在纯 xaml 中实现它,并像这样使用它,其中与 SecondLabelText 的绑定显示在 Ellipse 下:

<Label Style="{StaticResource RoundedButtonStyle}" Content="{Binding CountValue}" SecondContent="{Binding SecondLabelText}" HorizontalAlignment="Center" VerticalAlignment="Center"  Background="Red" BorderBrush="Red" BorderThickness="3" Height="100" Width="100" FontSize="20" FontWeight="Bold" />

我可以将标签添加到样式中,但是如何设置两个单独的内容?

【问题讨论】:

  • 一个标签元素只有一个内容。如果您需要多个内容,请创建自定义控件。作为“次要内容”的解决方法,人们经常使用 Tag 属性。
  • @Clemens Tag 是个好主意。谢谢。
  • 只需创建您自己的用户控件。关注this 文章了解技巧。您可以根据需要绑定任意数量的属性

标签: c# .net wpf xaml


【解决方案1】:

不知道这对你有没有用;离开并将其创建为自定义用户控件作为一种练习,您可以创建一个新的用户控件,设置 2 个属性来接收 2 个内容:

using System.Windows;
using System.Windows.Controls;

namespace Custom_Control_Elipse_2_labels
{
    /// <summary>
    /// Interaction logic for EllipseWithTwoLabels.xaml
    /// </summary>
    public partial class EllipseWithTwoLabels : UserControl
    {

        public static readonly DependencyProperty Content1Property = DependencyProperty.Register("Content1", typeof(string), typeof(EllipseWithTwoLabels));
        public static readonly DependencyProperty Content2Property = DependencyProperty.Register("Content2", typeof(string), typeof(EllipseWithTwoLabels));
        public EllipseWithTwoLabels()
        {
            InitializeComponent();
            DataContext = this;
        }

        public string Content1
        {
            get => (string) GetValue(Content1Property);
            set => SetValue(Content1Property,value);
        }
        public string Content2
        {
            get => (string)GetValue(Content2Property);
            set => SetValue(Content2Property, value);
        }
    }
}

用户控件的 .xaml 是

<Grid>
        <Label Content="{Binding Content1}" Style="{StaticResource RoundedButtonStyle}" HorizontalAlignment="Center" VerticalAlignment="Center"  Background="Red" BorderBrush="Red" BorderThickness="3" Height="100" Width="100" FontSize="20" FontWeight="Bold" ></Label>
        <Label Content="{Binding Content2}" Margin="0,150,0,0"  HorizontalAlignment="Center" VerticalAlignment="Center" ></Label>
    </Grid>

然后您可以将其导入到任何视图中以用于:(

xmlns:local="clr-namespace:Custom_Control_Elipse_2_labels" 

并与 xaml 一起使用:

 <local:EllipseWithTwoLabels Height="300" Width="300" Content1="Content #1" Content2="Content #2"/>

这是完成它的一种方法:)

它提供了这样的东西:

【讨论】:

  • 作为建议,我会告诉你不要将DataContext 设置为root。此外,在 XAML 中执行此操作,这样您就有了 IntelliSense。阅读this 了解原因
【解决方案2】:

您可以使用例如标签的Tag 属性来存储额外的数据

<Label Style="{StaticResource RoundedLabelStyle}" Content="Content" Tag="Content#2"/>

在模板中只需绑定到Tag 属性

<ContentPresenter Content="{TemplateBinding Tag}"/>

更好的方法是使用AttachedProperty。这允许您声明任意数量的额外内容,而无需创建新类型的控件

public class LabelExtension 
{
    public static readonly DependencyProperty SecondContentProperty = DependencyProperty.RegisterAttached(
        "SecondContent", typeof(object), typeof(LabelExtension));

    public static void SetSecondContent(UIElement element, object value)
    {
        element.SetValue(SecondContentProperty, value);
    }
    public static object GetSecondContent(UIElement element)
    {
        return (object)element.GetValue(SecondContentProperty);
    }
}

设置在控件上

<Label Style="{StaticResource RoundedLabelStyle}" Content="Content" local:LabelExtension.SecondContent="Content#2"/>

在模板中使用

<ContentPresenter Content="{TemplateBinding local:LabelExtension.SecondContent}"/>

完整的标签样式示例

<Style x:Key="RoundedLabelStyle" TargetType="{x:Type Label}">
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="Label">
                        <Grid Height="Auto" Width="Auto" HorizontalAlignment="{TemplateBinding HorizontalAlignment}" VerticalAlignment="{TemplateBinding VerticalAlignment}">
                            <Ellipse x:Name="cp" Margin="0,0,0,0" Fill="{TemplateBinding Background}" Height="{TemplateBinding Width}" Width="{TemplateBinding Width}" Stroke="Black" StrokeThickness="2" />
                            <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center">
                                <ContentPresenter.Content>
                                    <Border Padding="10">
                                        <StackPanel>
                                            <ContentPresenter Content="{TemplateBinding Content}"/>
                                            <ContentPresenter Content="{TemplateBinding Tag}"/>
                                            <ContentPresenter Content="{TemplateBinding local:LabelExtension.SecondContent}"/>
                                        </StackPanel>
                                    </Border>
                                </ContentPresenter.Content>
                            </ContentPresenter>
                        </Grid>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>

【讨论】:

    猜你喜欢
    • 2011-08-09
    • 2010-12-11
    • 1970-01-01
    • 1970-01-01
    • 2012-03-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多