none
怎样实现DataGrid同一列的不同行采用不同的数据模板? RRS feed

  • 问题

  • 假设DataGrid有col1和col2两列,col2的模板随col1列的值的数据类型而变,比如第一行col1列的值是日期型的,则col2列采用带DatePicker的模板,第二行col1列是枚举型的,则col2列采用带ComboBox的模板,等等,这样的功能如何实现呢?
    2014年5月28日 7:39

答案

  • 你好,

    你可以使用 DataTemplateSelector 去实现你的需求,一下是一个示例代码,我们需要在DataGrid中显示每一位学生是否通过测试,大于等于60就是Passed, 否则显示Failed。

    Student Class:

    public class Student
    {
            public Student(int id, String firstName, String lastName, Double percentage)
            {
                ID = id;
                FirstName = firstName;
                LastName = lastName;
                Percentage = percentage;
            }
    
            public int ID { get; set; }
            public String FirstName { get; set; }
            public String LastName { get; set; }
            public Double Percentage { get; set; }
    
    }

    DataTemplateSelector:

    public class GradeTemplateSelector : DataTemplateSelector
    {
            public DataTemplate PassedTemplate { get; set; }
            public DataTemplate FailedTemplate { get; set; }
            public override DataTemplate SelectTemplate(object item, DependencyObject container)
            {
                Student student = item as Student;
    
                if (student != null)
                {
                    if (student.Percentage >= 60) // 大于等于60分,返回PassedTemplate模板
                        return PassedTemplate;
                    else
                        return FailedTemplate; //返回FailedTemplate模板
                }
                else
                    return base.SelectTemplate(item, container);
            }
    }

    后台:

    ObservableCollection<Student> students = new ObservableCollection<Student>();
    public MainWindow()
    {
                InitializeComponent();
    
                students.Add(new Student(10, "Bob", "Smith", 80.5));
                students.Add(new Student(25, "James", "Brown", 77.9));
                students.Add(new Student(15, "Joe", "Martin", 52.4));
                students.Add(new Student(12, "Dona", "Taylor", 53.6));
                students.Add(new Student(18, "Peter", "Brian", 90.9));
                DataContext = students;
    }

    XAML(两套模版):

    <Window.Resources>
            <DataTemplate x:Key="PassedTemplate">
                <TextBlock Margin="2" Text="Passed" Foreground="Green"/>
            </DataTemplate>
            <DataTemplate x:Key="FailedTemplate">
                <TextBlock Margin="2" Text="Failed" Foreground="Red"/>
            </DataTemplate>
    </Window.Resources>
    
    <Grid>
            <DataGrid ItemsSource="{Binding}"
                      AlternationCount="2" AlternatingRowBackground="AliceBlue" AutoGenerateColumns="False">
                <DataGrid.Columns>
                    <DataGridTextColumn Header="Student ID" Binding="{Binding ID}"/>
                    <DataGridTextColumn Header="First Name" Binding="{Binding FirstName}"/>
                    <DataGridTextColumn Header="Last Name" Binding="{Binding LastName}"/>
                    <DataGridTemplateColumn Header="Percentage">
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <ProgressBar Margin="2" Minimum="0" Maximum="100" Value="{Binding Percentage}">
                                    <ProgressBar.ToolTip>
                                        <TextBlock Text="{Binding Percentage}"/>
                                    </ProgressBar.ToolTip>
                                </ProgressBar>
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>
                    <DataGridTemplateColumn Header="Grade">
                        <DataGridTemplateColumn.CellTemplateSelector>
                            <local:GradeTemplateSelector 
                                PassedTemplate="{StaticResource PassedTemplate}"
                                FailedTemplate="{StaticResource FailedTemplate}"/>
                        </DataGridTemplateColumn.CellTemplateSelector>
                    </DataGridTemplateColumn>
                </DataGrid.Columns>
            </DataGrid>
    </Grid>

    对于Grade列,我们使用了模板选择器,去根据Percentage列的数值来去选择相应模板,对于你想要根据数据类型来选择模板,完全可以修改DataTemplateSelector, 在重写SelectTemplate 方法中 判断数据类型,返回对应模板


    We are trying to better understand customer views on social support experience, so your participation in this interview project would be greatly appreciated if you have time. Thanks for helping make community forums a great place.
    Click HERE to participate the survey.

    2014年5月29日 8:13
    版主

全部回复

  • 你好,

    你可以使用 DataTemplateSelector 去实现你的需求,一下是一个示例代码,我们需要在DataGrid中显示每一位学生是否通过测试,大于等于60就是Passed, 否则显示Failed。

    Student Class:

    public class Student
    {
            public Student(int id, String firstName, String lastName, Double percentage)
            {
                ID = id;
                FirstName = firstName;
                LastName = lastName;
                Percentage = percentage;
            }
    
            public int ID { get; set; }
            public String FirstName { get; set; }
            public String LastName { get; set; }
            public Double Percentage { get; set; }
    
    }

    DataTemplateSelector:

    public class GradeTemplateSelector : DataTemplateSelector
    {
            public DataTemplate PassedTemplate { get; set; }
            public DataTemplate FailedTemplate { get; set; }
            public override DataTemplate SelectTemplate(object item, DependencyObject container)
            {
                Student student = item as Student;
    
                if (student != null)
                {
                    if (student.Percentage >= 60) // 大于等于60分,返回PassedTemplate模板
                        return PassedTemplate;
                    else
                        return FailedTemplate; //返回FailedTemplate模板
                }
                else
                    return base.SelectTemplate(item, container);
            }
    }

    后台:

    ObservableCollection<Student> students = new ObservableCollection<Student>();
    public MainWindow()
    {
                InitializeComponent();
    
                students.Add(new Student(10, "Bob", "Smith", 80.5));
                students.Add(new Student(25, "James", "Brown", 77.9));
                students.Add(new Student(15, "Joe", "Martin", 52.4));
                students.Add(new Student(12, "Dona", "Taylor", 53.6));
                students.Add(new Student(18, "Peter", "Brian", 90.9));
                DataContext = students;
    }

    XAML(两套模版):

    <Window.Resources>
            <DataTemplate x:Key="PassedTemplate">
                <TextBlock Margin="2" Text="Passed" Foreground="Green"/>
            </DataTemplate>
            <DataTemplate x:Key="FailedTemplate">
                <TextBlock Margin="2" Text="Failed" Foreground="Red"/>
            </DataTemplate>
    </Window.Resources>
    
    <Grid>
            <DataGrid ItemsSource="{Binding}"
                      AlternationCount="2" AlternatingRowBackground="AliceBlue" AutoGenerateColumns="False">
                <DataGrid.Columns>
                    <DataGridTextColumn Header="Student ID" Binding="{Binding ID}"/>
                    <DataGridTextColumn Header="First Name" Binding="{Binding FirstName}"/>
                    <DataGridTextColumn Header="Last Name" Binding="{Binding LastName}"/>
                    <DataGridTemplateColumn Header="Percentage">
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <ProgressBar Margin="2" Minimum="0" Maximum="100" Value="{Binding Percentage}">
                                    <ProgressBar.ToolTip>
                                        <TextBlock Text="{Binding Percentage}"/>
                                    </ProgressBar.ToolTip>
                                </ProgressBar>
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>
                    <DataGridTemplateColumn Header="Grade">
                        <DataGridTemplateColumn.CellTemplateSelector>
                            <local:GradeTemplateSelector 
                                PassedTemplate="{StaticResource PassedTemplate}"
                                FailedTemplate="{StaticResource FailedTemplate}"/>
                        </DataGridTemplateColumn.CellTemplateSelector>
                    </DataGridTemplateColumn>
                </DataGrid.Columns>
            </DataGrid>
    </Grid>

    对于Grade列,我们使用了模板选择器,去根据Percentage列的数值来去选择相应模板,对于你想要根据数据类型来选择模板,完全可以修改DataTemplateSelector, 在重写SelectTemplate 方法中 判断数据类型,返回对应模板


    We are trying to better understand customer views on social support experience, so your participation in this interview project would be greatly appreciated if you have time. Thanks for helping make community forums a great place.
    Click HERE to participate the survey.

    2014年5月29日 8:13
    版主
  • 非常感谢你写得如此详细,辛苦了,谢谢!
    2014年5月30日 10:01