【WPF】模板选择器

1. 新建DataTemplateSelectorDemo的WPF项目

项目布局如下:
在这里插入图片描述

2. App.xaml

<unity:PrismApplication x:Class="DataTemplateSelectorDemo.App"
                        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
                        xmlns:unity="http://prismlibrary.com/"
                        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
    <Application.Resources />
</unity:PrismApplication>

3. App.xaml.cs

using DataTemplateSelectorDemo.Views;
using Prism.Ioc;
using System.Windows;

namespace DataTemplateSelectorDemo
{
    public partial class App
    {
        protected override void RegisterTypes(IContainerRegistry containerRegistry)
        {
        }

        protected override Window CreateShell()
        {
            return this.Container.Resolve<MainWindowView>();
        }
    }
}

4. BooleanBrushConverter.cs

using System;
using System.Globalization;
using System.Windows.Data;
using System.Windows.Media;

namespace DataTemplateSelectorDemo.Common
{
    [ValueConversion(typeof(bool), typeof(Brush))]
    public class BooleanBrushConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            if (value is null)
                throw new ArgumentNullException(nameof(value));

            return (bool)value ? Brushes.LightGreen : Brushes.Red;
        }

        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}

5. CustomedTemplateSelector.cs

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

namespace DataTemplateSelectorDemo.Common
{
    public class CustomedTemplateSelector : DataTemplateSelector
    {
        public DataTemplate FoundTemplate { get; set; }
        public DataTemplate NotFoundTemplate { get; set; }

        public override DataTemplate SelectTemplate(object item, DependencyObject container)
        {
            return item is null ? this.NotFoundTemplate
                                : item is not Info ? this.NotFoundTemplate
                                                   : (item as Info).TemplateSwitch ? this.FoundTemplate
                                                                                   : this.NotFoundTemplate;
        }
    }
}

6. Info.cs

using Prism.Mvvm;

namespace DataTemplateSelectorDemo
{
    public class Info : BindableBase
    {
        private byte index;
        private bool isSelected;
        private string name;
        private bool templateSwitch;

        public byte Index
        {
            get => this.index;
            set => this.SetProperty(ref this.index, value);
        }

        public bool IsSelected
        {
            get => this.isSelected;
            set
            {
                if (this.SetProperty(ref this.isSelected, value))
                {
                    System.Console.WriteLine(" The property of IsSelected is changed.");
                }
            }
        }

        public string Name
        {
            get => this.name;
            set => this.SetProperty(ref this.name, value);
        }

        public bool TemplateSwitch
        {
            get => this.templateSwitch;
            set => this.SetProperty(ref this.templateSwitch, value);
        }
    }
}

7. MainWindowViewModel.cs

using System.Collections.ObjectModel;

namespace DataTemplateSelectorDemo.ViewModels
{
    public class MainWindowViewModel
    {
        public ObservableCollection<Info> InfoCollection { get; } = new ObservableCollection<Info>();

        public MainWindowViewModel()
        {
            this.InfoCollection.Add(new Info() { Index = 1, Name = "1111", IsSelected = true, TemplateSwitch = false });
            this.InfoCollection.Add(new Info() { Index = 2, Name = "2222", IsSelected = true, TemplateSwitch = true });
            this.InfoCollection.Add(new Info() { Index = 3, Name = "3333", IsSelected = false, TemplateSwitch = false });
            this.InfoCollection.Add(new Info() { Index = 4, Name = "4444", IsSelected = false, TemplateSwitch = true });
        }
    }
}

8. MainWindowView.xaml

<Window x:Class="DataTemplateSelectorDemo.Views.MainWindowView"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:common="clr-namespace:DataTemplateSelectorDemo.Common"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:prism="http://prismlibrary.com/"
        Title="MainWindow" Width="800" Height="450"
        prism:ViewModelLocator.AutoWireViewModel="True" mc:Ignorable="d">

    <!--  指定ColumnWidth="*"使得列完整填充,且等分  -->
    <DataGrid Margin="10" AutoGenerateColumns="False" CanUserAddRows="False" ColumnWidth="*" HeadersVisibility="Column" ItemsSource="{Binding Path=InfoCollection}">
        <DataGrid.Resources>
            <common:BooleanBrushConverter x:Key="BooleanBrushConverter" />

            <DataTemplate x:Key="FoundTemplate">
                <TextBlock FontSize="20" Foreground="LightGreen" Text="" />
            </DataTemplate>

            <DataTemplate x:Key="NotFoundTemplate">
                <TextBlock FontSize="20" Foreground="Red" Text="" />
            </DataTemplate>
        </DataGrid.Resources>

        <DataGrid.Columns>
            <DataGridTextColumn Binding="{Binding Path=Index}" Header="索引" />

            <DataGridTextColumn Binding="{Binding Path=Name}" Header="名称" />

            <DataGridTemplateColumn Header="属性转换器">
                <DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <TextBlock FontSize="20" Foreground="{Binding TemplateSwitch, Converter={StaticResource BooleanBrushConverter}}" Text="" />
                    </DataTemplate>
                </DataGridTemplateColumn.CellTemplate>
            </DataGridTemplateColumn>

            <DataGridTemplateColumn Header="数据触发器">
                <DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <Grid>
                            <TextBlock Name="found" FontSize="20" Foreground="LightGreen" Text="" />
                            <TextBlock Name="nofound" FontSize="20" Foreground="Red" Text="" />
                        </Grid>
                        <DataTemplate.Triggers>
                            <DataTrigger Binding="{Binding TemplateSwitch}" Value="True">
                                <Setter TargetName="found" Property="Visibility" Value="Visible" />
                                <Setter TargetName="nofound" Property="Visibility" Value="Collapsed" />
                            </DataTrigger>
                            <DataTrigger Binding="{Binding TemplateSwitch}" Value="False">
                                <Setter TargetName="found" Property="Visibility" Value="Collapsed" />
                                <Setter TargetName="nofound" Property="Visibility" Value="Visible" />
                            </DataTrigger>
                        </DataTemplate.Triggers>
                    </DataTemplate>
                </DataGridTemplateColumn.CellTemplate>
            </DataGridTemplateColumn>

            <DataGridTemplateColumn Header="模板选择器">
                <DataGridTemplateColumn.CellTemplateSelector>
                    <common:CustomedTemplateSelector FoundTemplate="{StaticResource FoundTemplate}" NotFoundTemplate="{StaticResource NotFoundTemplate}" />
                </DataGridTemplateColumn.CellTemplateSelector>
            </DataGridTemplateColumn>

            <DataGridTemplateColumn Header="选择与否">
                <DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <!--  需要指定UpdateSourceTrigger属性才能在后端接收到界面值改变  -->
                        <RadioButton GroupName="Reference" IsChecked="{Binding Path=IsSelected, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" />
                    </DataTemplate>
                </DataGridTemplateColumn.CellTemplate>
            </DataGridTemplateColumn>
        </DataGrid.Columns>
    </DataGrid>
</Window>

9. MainWindowView.xaml.cs

namespace DataTemplateSelectorDemo.Views
{
    public partial class MainWindowView
    {
        public MainWindowView()
        {
            this.InitializeComponent();
        }
    }
}

10. 效果

在这里插入图片描述

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
WPF中的DataTemplateSelector是一个非常有用的工具,它允许我们根据数据类型或其他条件来选择使用哪个DataTemplate来呈现数据。使用DataTemplateSelector的步骤如下: 1. 创建一个继承自DataTemplateSelector的类: ``` public class MyDataTemplateSelector : DataTemplateSelector { public override DataTemplate SelectTemplate(object item, DependencyObject container) { if (item is MyType1) { return (DataTemplate)Application.Current.Resources["MyType1Template"]; } else if (item is MyType2) { return (DataTemplate)Application.Current.Resources["MyType2Template"]; } else { return null; } } } ``` 2. 在XAML中使用DataTemplateSelector: ``` <ItemsControl ItemsSource="{Binding}"> <ItemsControl.ItemTemplateSelector> <local:MyDataTemplateSelector/> </ItemsControl.ItemTemplateSelector> </ItemsControl> ``` 动态绑定可以让我们在运行时动态地改变数据绑定的目标或源。使用动态绑定的步骤如下: 1. 创建一个继承自INotifyPropertyChanged接口的类,该类包含需要动态绑定的属性。 2. 在XAML中使用Binding对象绑定属性: ``` <TextBlock Text="{Binding MyProperty}"/> ``` 3. 在代码中动态更改属性的值: ``` MyObject.MyProperty = "New Value"; ``` DataTemplate.Triggers是一个非常有用的工具,它允许我们根据数据的某些属性来更改DataTemplate的样式。使用DataTemplate.Triggers的步骤如下: 1. 在DataTemplate中添加Trigger对象: ``` <DataTemplate x:Key="MyTemplate"> <Border BorderThickness="1" BorderBrush="Black"> <TextBlock Text="{Binding}"> <TextBlock.Style> <Style TargetType="{x:Type TextBlock}"> <Style.Triggers> <DataTrigger Binding="{Binding Path=Status}" Value="Error"> <Setter Property="Foreground" Value="Red"/> </DataTrigger> </Style.Triggers> </Style> </TextBlock.Style> </TextBlock> </Border> </DataTemplate> ``` 2. 在数据对象中添加属性: ``` public string Status { get; set; } ``` 3. 在代码中更改属性的值: ``` MyObject.Status = "Error"; ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

zhy29563

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值