1

我将我的 DataGrid 绑定到从 IMyInterface 派生的不同类型的对象的集合。我需要按对象的真实类型对 DataGrid 进行分组,并根据每种类型的属性在每个组中自动生成列,因为这些类型具有不同的属性。

请帮忙。

我正在添加一些我现有的代码:

XAML:

<Style x:Key="GroupHeaderStyle" TargetType="{x:Type GroupItem}">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type GroupItem}">
                <Expander IsExpanded="False" 
                    Background="White"
                    Foreground="Black">
                    <Expander.Header>
                        <StackPanel Orientation="Horizontal">
                            <TextBlock Text="{Binding Name}"/>
                            <TextBlock Text="{Binding Path=ItemCount}" Padding="10, 0, 10, 0"/>
                            <TextBlock Text="Item(s)"/>
                        </StackPanel>
                    </Expander.Header>
                    <ItemsPresenter />
                </Expander>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

...

<DataGrid Grid.Row="1" Grid.Column="2" Name="DgPendingMessages" ItemsSource="{Binding }" AutoGenerateColumns="False"
    IsReadOnly="True" MaxHeight="400">
    <DataGrid.GroupStyle>
        <GroupStyle ContainerStyle="{StaticResource GroupHeaderStyle}">
            <GroupStyle.Panel>
                <ItemsPanelTemplate>
                    <DataGridRowsPresenter />
                </ItemsPanelTemplate>
            </GroupStyle.Panel>
        </GroupStyle>
    </DataGrid.GroupStyle>

    <DataGrid.Columns>
        <DataGridTextColumn Binding="{Binding TheMessage}" Header="Pending Message" />
    </DataGrid.Columns>
</DataGrid>

代码隐藏:

public class PendingMessage
{
    //public IMyInterface TheMessage { get; set; }
    public string TheMessage { get; set; }
    public string MessageType { get; set; }
}

PendingMessage 是我的模型类,它包含真实 Message 对象的字符串表示形式和 Message 对象的原始类型(用于按它对 DataGrid 进行分组)。

Message 对象可以是从 IMyInterface 派生的任何类型。

var collectionPendingMessages = new ListCollectionView(PendingMessages);
collectionPendingMessages.GroupDescriptions.Add(new PropertyGroupDescription("MessageType"));
DgPendingMessages.ItemsSource = collectionPendingMessages;

而不是真正的 Message 对象的字符串表示,我想要这样的东西:

A型:3件

N 栏 | Z 栏 | X 栏 | T 列

数据 | 数据 | 数据 | 数据

数据 | 数据 | 数据 | 数据

数据 | 数据 | 数据 | 数据


B型:4件

N 栏 | S 栏 | U 列

数据 | 数据 | 数据

数据 | 数据 | 数据

数据 | 数据 | 数据

数据 | 数据 | 数据


C型:3件

N 栏 | Z 栏 | X 栏 | T 列 | U 列

数据 | 数据 | 数据 | 数据 | 数据

数据 | 数据 | 数据 | 数据 | 数据

数据 | 数据 | 数据 | 数据 | 数据

4

1 回答 1

1

我以前一直在努力解决这个问题。如果您基本上将 XAML 用于您的视图,那么对我有用的一个选项是在运行时动态生成您需要的 XAML。感觉有点难看,但似乎确实有效。

这是我的一个项目中的一个代码隐藏类。希望它足够接近您的问题以提供帮助:

public partial class SetupPanel : UserControl
{
    public SetupPanel()
    {
        InitializeComponent();
    }

    protected override void OnRender(System.Windows.Media.DrawingContext drawingContext)
    {
        AddParticipantGridViewColumns();
        base.OnRender(drawingContext);
    }

    public void AddParticipantGridViewColumns()
    {
        ...
        for (var blockIndex = 0; blockIndex < blockColumnCount; blockIndex++)
        {
            var column = BuildParticipantGridViewColumn(blockIndex);
            dataGrid.Columns.Add(column);
        }
    }

    private DataGridTemplateColumn BuildParticipantGridViewColumn(int blockIndex)
    {
        var columnXaml = string.Format(@"
            <DataGridTemplateColumn
                xmlns=""http://schemas.microsoft.com/winfx/2006/xaml/presentation""
                xmlns:x=""http://schemas.microsoft.com/winfx/2006/xaml""
                Header=""Block {1}"">
                <DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <TextBlock Text=""{{Binding BlockViewModels[{0}].ConditionLabel}}""
                                   Foreground=""{{Binding BlockViewModels[{0}].TextBrush}}"" />
                    </DataTemplate>
                </DataGridTemplateColumn.CellTemplate>
            </DataGridTemplateColumn>",
            blockIndex, blockIndex + 1);
        var column = (DataGridTemplateColumn)XamlReader.Parse(columnXaml);
        return column;
    }
}

更新

再次阅读您的问题,您可能需要做的就是使用AutoGenerateColumns="true"您的 DataGrid。但是,这仅在您不想自定义列的外观时才有效。


更新 2

查看您更新的问题,看起来您真正需要做的就是将消息放入DataTable对象中,这允许您在运行时构建列并动态填充数据。然后您可以使用 AutoGenerateColumns,或者,如果您需要更多自定义,请使用 XAML 生成(如我在上面发布的)将列添加到 DataGrid。

于 2013-06-20T18:50:16.040 回答