【问题标题】:Changing checkmark color of a checkbox in a WPF ListView更改 WPF ListView 中复选框的复选标记颜色
【发布时间】:2020-12-02 10:13:58
【问题描述】:

我正在尝试更改 WPF 列表视图中复选框的复选标记的颜色。我从另一篇文章中获得了以下 XAML 代码。不幸的是,我对整个框架不够熟悉,无法理解我需要在我的 ListView 中添加的地方。有没有人能给我一些提示。非常感谢。

<Style x:Key="{x:Static GridView.GridViewScrollViewerStyleKey}" TargetType="ScrollViewer">
    <Setter Property="Template">
        <Setter.Value>

            <ControlTemplate TargetType="CheckBox">
                <Grid>
                    <Path x:Name="Equis" Opacity="0" Stroke="Red" Fill="Red" Stretch="UniformToFill" StrokeThickness="20" Data="M 30,100 L 80,140 L 160,60" Margin="0,0,2,2" />
                    <ContentPresenter Margin="4" HorizontalAlignment="Left" VerticalAlignment="Top" />
                </Grid>
                <ControlTemplate.Triggers>
                    <Trigger Property="IsChecked" Value="true">
                        <Setter TargetName="Equis" Property="Opacity" Value="1" />
                    </Trigger>
                    <Trigger Property="IsChecked" Value="false">
                        <Setter TargetName="Equis" Property="Opacity" Value="0" />
                    </Trigger>
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

这里是 GridViewColumn 中复选框的 XAML(工作正常)

<GridViewColumn Header="HeaderName" Width="35">

    <GridViewColumn.CellTemplate>
        <DataTemplate>
            <CheckBox x:Name="CheckBoxName" IsChecked="{Binding Object}" HorizontalAlignment="Center"/>
        </DataTemplate>
    </GridViewColumn.CellTemplate>

</GridViewColumn>

【问题讨论】:

  • 其实我不知道上面的代码(这只是另一篇文章中的一个例子)是否放在我的 XAML 中...

标签: c# wpf listview checkbox controltemplate


【解决方案1】:

您只需要您显示的样式的 ControlTemplate 部分。您需要使用x:Key="MyCheckBoxTemplate" 给它一个密钥。然后您可以使用Template="{StaticResource MyCheckBoxTemplate}" 将其应用于您自己的 CellTemplate 中的 CheckBox。

一个完整的例子如下。在此,我更改了问题中的示例ControlTemplate,因为它在选择复选框时绘制了一个相当令人讨厌的大红色裂分。我让它用红色画了一个小得多的复选标记:

XAML:

<Window x:Class="WpfApp11.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApp11"
        mc:Ignorable="d"
        Title="MainWindow" Height="450" Width="800">
    <Window.Resources>
        <ControlTemplate TargetType="CheckBox" x:Key="MyCheckBoxTemplate">
            <StackPanel Orientation="Horizontal">
                <Path x:Name="Equis" 
                      Stroke="Red" 
                      StrokeThickness="3" 
                      Height="17" Width="19" Stretch="None" 
                      Margin="0,0,2,2"
                      Opacity="1"
                      >
                    <Path.Data>
                        <PathGeometry>
                            <PathFigure StartPoint="3,10">
                                <LineSegment Point="8,14" />
                                <LineSegment Point="16,6" />
                            </PathFigure>
                        </PathGeometry>
                    </Path.Data>
                </Path>
                <ContentPresenter Margin="4" HorizontalAlignment="Left" VerticalAlignment="Top" />
            </StackPanel>
            <ControlTemplate.Triggers>
                <Trigger Property="IsChecked" Value="true">
                    <Setter TargetName="Equis" Property="Opacity" Value="1" />
                </Trigger>
                <Trigger Property="IsChecked" Value="false">
                    <Setter TargetName="Equis" Property="Opacity" Value="0" />
                </Trigger>
            </ControlTemplate.Triggers>
        </ControlTemplate>
    </Window.Resources>
    <ListView Margin="5" ItemsSource="{Binding Products}">
        <ListView.View>
            <GridView>
                <GridView.Columns>
                    <GridViewColumn Header="Checked" DisplayMemberBinding="{Binding IsChecked}" />
                    <GridViewColumn Header="Name" DisplayMemberBinding="{Binding ShortName}" />
                    <GridViewColumn Header="ID" DisplayMemberBinding="{Binding ID}" />
                    <GridViewColumn Header="HeaderName" Width="35">
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <CheckBox x:Name="CheckBoxName" Template="{StaticResource MyCheckBoxTemplate}"
                                          IsChecked="{Binding IsChecked}" HorizontalAlignment="Center"/>
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                </GridView.Columns>
            </GridView>
        </ListView.View>
    </ListView>
</Window>

C#:

using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Windows;

namespace WpfApp11
{
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
            CreateProducts();
            DataContext = this;
        }

        public ObservableCollection<Product> Products { get; set; }

        private void CreateProducts()
        {
            Products = new ObservableCollection<Product>
            {
                new Product{ShortName="My First Product", ID = 1},
                new Product{ShortName="My Second Product", ID = 2, IsChecked= true},
                new Product{ShortName="My Third Product", ID = 3},
                new Product{ShortName="My Fourth Product", ID = 4, IsChecked = true},
                new Product{ShortName="My Fifth Product", ID = 5}
           };
        }
    }

    public class Product : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        private string shortName;
        public string ShortName
        {
            get { return shortName; }
            set
            {
                shortName = value;
                PropertyChanged?.Invoke(this,
                    new PropertyChangedEventArgs(nameof(ShortName)));
            }
        }

        private int id;
        public int ID
        {
            get { return id; }
            set
            {
                id = value;
                PropertyChanged?.Invoke(this,
                   new PropertyChangedEventArgs(nameof(ID)));
            }
        }

        private bool isChecked;
        public bool IsChecked
        {
            get { return isChecked; }
            set
            {
                isChecked = value;
                PropertyChanged?.Invoke(this,
                    new PropertyChangedEventArgs(nameof(IsChecked)));
            }
        }
    }
}

【讨论】:

    【解决方案2】:

    您需要重新模板化整个控件。看看这个例子:

    <CheckBox x:Name="CheckBoxName" IsChecked="{Binding Object}" HorizontalAlignment="Center">
        <CheckBox.Resources>
            <Style x:Key="FocusVisual">
                <Setter Property="Control.Template">
                    <Setter.Value>
                        <ControlTemplate>
                            <Rectangle Margin="2" SnapsToDevicePixels="true" Stroke="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}" StrokeThickness="1" StrokeDashArray="1 2"/>
                        </ControlTemplate>
                    </Setter.Value>
                </Setter>
            </Style>
            <SolidColorBrush x:Key="OptionMark.Static.Background" Color="#FFFFFFFF"/>
            <SolidColorBrush x:Key="OptionMark.Static.Border" Color="#FF707070"/>
            <Style x:Key="OptionMarkFocusVisual">
                <Setter Property="Control.Template">
                    <Setter.Value>
                        <ControlTemplate>
                            <Rectangle Margin="14,0,0,0" SnapsToDevicePixels="true" Stroke="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}" StrokeThickness="1" StrokeDashArray="1 2"/>
                        </ControlTemplate>
                    </Setter.Value>
                </Setter>
            </Style>
            <SolidColorBrush x:Key="OptionMark.MouseOver.Background" Color="#FFF3F9FF"/>
            <SolidColorBrush x:Key="OptionMark.MouseOver.Border" Color="#FF5593FF"/>
            <SolidColorBrush x:Key="OptionMark.MouseOver.Glyph" Color="Red"/>
            <SolidColorBrush x:Key="OptionMark.Disabled.Background" Color="#FFE6E6E6"/>
            <SolidColorBrush x:Key="OptionMark.Disabled.Border" Color="#FFBCBCBC"/>
            <SolidColorBrush x:Key="OptionMark.Disabled.Glyph" Color="#FF707070"/>
            <SolidColorBrush x:Key="OptionMark.Pressed.Background" Color="#FFD9ECFF"/>
            <SolidColorBrush x:Key="OptionMark.Pressed.Border" Color="#FF3C77DD"/>
            <SolidColorBrush x:Key="OptionMark.Pressed.Glyph" Color="Red"/>
            <SolidColorBrush x:Key="OptionMark.Static.Glyph" Color="Red"/>
        </CheckBox.Resources>
        <CheckBox.Style>
            <Style TargetType="{x:Type CheckBox}">
                <Setter Property="FocusVisualStyle" Value="{StaticResource FocusVisual}"/>
                <Setter Property="Background" Value="{StaticResource OptionMark.Static.Background}"/>
                <Setter Property="BorderBrush" Value="{StaticResource OptionMark.Static.Border}"/>
                <Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
                <Setter Property="BorderThickness" Value="1"/>
                <Setter Property="Template">
                    <Setter.Value>
                        <ControlTemplate TargetType="{x:Type CheckBox}">
                            <Grid x:Name="templateRoot" Background="Transparent" SnapsToDevicePixels="True">
                                <Grid.ColumnDefinitions>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="*"/>
                                </Grid.ColumnDefinitions>
                                <Border x:Name="checkBoxBorder" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="1" VerticalAlignment="{TemplateBinding VerticalContentAlignment}">
                                    <Grid x:Name="markGrid">
                                        <Path x:Name="optionMark" Data="F1 M 9.97498,1.22334L 4.6983,9.09834L 4.52164,9.09834L 0,5.19331L 1.27664,3.52165L 4.255,6.08833L 8.33331,1.52588e-005L 9.97498,1.22334 Z " Fill="{StaticResource OptionMark.Static.Glyph}" Margin="1" Opacity="0" Stretch="None"/>
                                        <Rectangle x:Name="indeterminateMark" Fill="{StaticResource OptionMark.Static.Glyph}" Margin="2" Opacity="0"/>
                                    </Grid>
                                </Border>
                                <ContentPresenter x:Name="contentPresenter" Grid.Column="1" Focusable="False" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="{TemplateBinding Padding}" RecognizesAccessKey="True" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
                            </Grid>
                            <ControlTemplate.Triggers>
                                <Trigger Property="HasContent" Value="true">
                                    <Setter Property="FocusVisualStyle" Value="{StaticResource OptionMarkFocusVisual}"/>
                                    <Setter Property="Padding" Value="4,-1,0,0"/>
                                </Trigger>
                                <Trigger Property="IsMouseOver" Value="true">
                                    <Setter Property="Background" TargetName="checkBoxBorder" Value="{StaticResource OptionMark.MouseOver.Background}"/>
                                    <Setter Property="BorderBrush" TargetName="checkBoxBorder" Value="{StaticResource OptionMark.MouseOver.Border}"/>
                                    <Setter Property="Fill" TargetName="optionMark" Value="{StaticResource OptionMark.MouseOver.Glyph}"/>
                                    <Setter Property="Fill" TargetName="indeterminateMark" Value="{StaticResource OptionMark.MouseOver.Glyph}"/>
                                </Trigger>
                                <Trigger Property="IsEnabled" Value="false">
                                    <Setter Property="Background" TargetName="checkBoxBorder" Value="{StaticResource OptionMark.Disabled.Background}"/>
                                    <Setter Property="BorderBrush" TargetName="checkBoxBorder" Value="{StaticResource OptionMark.Disabled.Border}"/>
                                    <Setter Property="Fill" TargetName="optionMark" Value="{StaticResource OptionMark.Disabled.Glyph}"/>
                                    <Setter Property="Fill" TargetName="indeterminateMark" Value="{StaticResource OptionMark.Disabled.Glyph}"/>
                                </Trigger>
                                <Trigger Property="IsPressed" Value="true">
                                    <Setter Property="Background" TargetName="checkBoxBorder" Value="{StaticResource OptionMark.Pressed.Background}"/>
                                    <Setter Property="BorderBrush" TargetName="checkBoxBorder" Value="{StaticResource OptionMark.Pressed.Border}"/>
                                    <Setter Property="Fill" TargetName="optionMark" Value="{StaticResource OptionMark.Pressed.Glyph}"/>
                                    <Setter Property="Fill" TargetName="indeterminateMark" Value="{StaticResource OptionMark.Pressed.Glyph}"/>
                                </Trigger>
                                <Trigger Property="IsChecked" Value="true">
                                    <Setter Property="Opacity" TargetName="optionMark" Value="1"/>
                                    <Setter Property="Opacity" TargetName="indeterminateMark" Value="0"/>
                                </Trigger>
                                <Trigger Property="IsChecked" Value="{x:Null}">
                                    <Setter Property="Opacity" TargetName="optionMark" Value="0"/>
                                    <Setter Property="Opacity" TargetName="indeterminateMark" Value="1"/>
                                </Trigger>
                            </ControlTemplate.Triggers>
                        </ControlTemplate>
                    </Setter.Value>
                </Setter>
            </Style>
        </CheckBox.Style>
    </CheckBox>
    

    复选标记的颜色由OptionMark.MouseOver.GlyphOptionMark.Pressed.GlyphOptionMark.Static.Glyph 资源定义。您可以将其中的Color 设置为任何您想要的。

    【讨论】:

    • 非常感谢您的回复。我应该在 中添加 部分还是作为 的一部分?
    • @Norbert:只需将CellTemplate 中的CheckBox 元素替换为我的答案即可。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-07-20
    • 2015-06-22
    • 2015-02-09
    • 1970-01-01
    • 2021-08-18
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多