我正在编写一个项目,其中包含一个WPF窗口,该窗口包含一个列表框。我试图让列表框中的一些特定行被绘制,一些特定行根据列表中的项目字段有彩色边框。
<ListBox Name="Tasks" HorizontalAlignment="Left" ItemsSource="{Binding Path=Tasks,Mode=TwoWay}" Height="199" Margin="303,97,0,0" VerticalAlignment="Top" Width="439" RenderTransformOrigin="0.5,0.5">
<ListBox.RenderTransform>
<TransformGroup>
<ScaleTransform/>
<SkewTransform/>
<RotateTransform Angle="0.294"/>
<TranslateTransform/>
</TransformGroup>
</ListBox.RenderTransform>
</ListBox>
ItemsControl有一个特殊的功能,可以为控件中显示的项目选择模板。在下面的示例中,我说明了DataTemplateSelector的使用。
首先是XAML。在Resource部分,为你想在ListBox中显示的不同类型的项目定义了不同的数据模板,并且有一个DataTemplateSelector的引用(在后面的C#代码中定义)。
<Window x:Class="TestWpfApp.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:TestWpfApp"
mc:Ignorable="d"
x:Name="DataWindow"
WindowState="Maximized"
Title="MainWindow" Height="450" Width="800">
<Window.Resources>
<!-- The data template selector -->
<local:DataItemTemplateSelector x:Key="DataItemTemplateSelector"/>
<!-- Data template for a normal data item -->
<DataTemplate x:Key="NormalDatatemplate">
<Border Width="200"
Margin="0"
Background="White"
BorderThickness="2"
Padding="3"
BorderBrush="Transparent">
<TextBlock VerticalAlignment="Center"
HorizontalAlignment="Stretch"
FontSize="20"
Foreground="Black"
Background="Transparent"
Text="{Binding Path=Header}"/>
</Border>
</DataTemplate>
<!-- Data template for a special data item -->
<DataTemplate x:Key="SpecialDatatemplate">
<Border Width="200"
Margin="0"
Background="Yellow"
BorderThickness="2"
Padding="3"
BorderBrush="Blue">
<TextBlock VerticalAlignment="Center"
HorizontalAlignment="Stretch"
FontSize="20"
Foreground="Black"
Background="Transparent"
Text="{Binding Path=Header}"/>
</Border>
</DataTemplate>
</Window.Resources>
<Grid>
<ListBox x:Name="DataListBox"
Margin="50"
Width="Auto"
Height="Auto"
HorizontalAlignment="Center"
VerticalAlignment="Top"
ItemsSource="{Binding ElementName=DataWindow, Path=DataList}"
ItemTemplateSelector="{StaticResource ResourceKey=DataItemTemplateSelector}"/>
</Grid>
</Window>
然后是C#代码,那里定义了DataItemTemplateSelector和带有一些testdata的DataList。
using System.Collections.Generic;
using System.Windows;
using System.Windows.Controls;
namespace TestWpfApp
{
// Different types of items on the list
public enum DataItemType
{
Normal,
Special
}
// Items on the list
public class DataItem
{
public string Header { set; get; }
public DataItemType DataType { set; get; }
}
// Data template selector for items on the list
public class DataItemTemplateSelector : DataTemplateSelector
{
public override DataTemplate SelectTemplate(object dataItem, DependencyObject container)
{
// Check that everyting is OK
if ((dataItem != null) && (dataItem is DataItem))
{
// Switch on the data type
switch (((DataItem)(dataItem)).DataType)
{
case DataItemType.Normal:
// Return the data template for a normal data item
return Application.Current.MainWindow.FindResource("NormalDatatemplate") as DataTemplate;
case DataItemType.Special:
// Return the data template for a special data item
return Application.Current.MainWindow.FindResource("SpecialDatatemplate") as DataTemplate;
default:
return null;
}
}
return null;
}
}
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
// The list of data to show in the list box
public List<DataItem> DataList { set; get; }
// The constructor of the main window
public MainWindow()
{
// Some test data
this.DataList = new List<DataItem>();
this.DataList.Add(new DataItem() { Header = "Item 1", DataType = DataItemType.Normal });
this.DataList.Add(new DataItem() { Header = "Item 2", DataType = DataItemType.Normal });
this.DataList.Add(new DataItem() { Header = "Item 3", DataType = DataItemType.Special });
this.DataList.Add(new DataItem() { Header = "Item 4", DataType = DataItemType.Normal });
// Initializing the window
InitializeComponent();
}
}
}
我希望你能理解使用DataTemplateSelector的想法,然后你就可以为你的ListBox和其中不同类型的项目设置样式了