如何将类与Dictionary <string,object>属性绑定到datagrid </string,object>

时间:2013-12-18 15:35:47

标签: wpf datagrid .net-3.5

我有一个场景,我必须动态获取数据并将其存储在字典中以供显示。

这就是我的模型的样子:

public class ViewModel
{
   public Guid Id { get; set; }
   public string Name { get; set; }
   public Dictionary<string,object> CustomFields { get; set; }
}

我将我的视图模型绑定到DataGrid,我有两个为Id和Name定义的列。

如何为字典中的数据生成列?

我无法使用动态对象,因为我正在使用.net 3.5。

这就是我的XAML的样子:

<Window x:Class="MyClass"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:tk="http://schemas.microsoft.com/wpf/2008/toolkit" 
        xmlns:viewmodel="clr-namespace:MyViewModel"
        xmlns:model="clr-namespace:MyModel"
        xmlns:sys="clr-namespace:System;assembly=mscorlib"
        Title="List Of Projects" Height="600" Width="600">

<Window.DataContext>
    <viewmodel:SomeViewModel></viewmodel:SomeViewModel>
</Window.DataContext>

<tk:DataGrid Grid.Row="1" Grid.Column="0" Grid.ColumnSpan="2" x:Name="dgData" ItemsSource="{Binding ListOfObjects}"  VerticalContentAlignment="Stretch" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"  AutoGenerateColumns="False"  SelectionMode="Single" CanUserAddRows="False" CanUserDeleteRows="False" >

<tk:DataGrid.Columns>
   <tk:DataGridTextColumn Header="Id"  Binding="{Binding Id}" IsReadOnly="True"></tk:DataGridTextColumn>

   <tk:DataGridTextColumn Header="Name"  Binding="{Binding Name}" IsReadOnly="True"></tk:DataGridTextColumn>
</tk:DataGrid.Columns>

</tk:DataGrid>

</Window>

1 个答案:

答案 0 :(得分:0)

使用转换器:

CS:

public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
        this.DataContext = this;
    }


    public Dictionary<int, string> MyDictionary 
    {
        get
        {
            var dic = new Dictionary<int, string>();
            dic.Add(1,"11111");
            dic.Add(2,"22222");
            dic.Add(3,"33333");
            dic.Add(4,"44444");

            return dic;                
        }
    }
}

public class DictionaryConverter : IMultiValueConverter
{
    public object Convert(object[] values, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        DataGridRow row = (DataGridRow)values[0];
        IDictionary<int,string> dic = (IDictionary<int,string>)values[1];

        bool isId = bool.Parse(parameter.ToString());

        var index = row.GetIndex();

        KeyValuePair<int,string> kv = dic.ElementAt(index);

        return isId ? kv.Key.ToString() : kv.Value;
    }

    public object[] ConvertBack(object value, Type[] targetTypes, object parameter, System.Globalization.CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

XAML:

   <DataGrid AutoGenerateColumns="False" ItemsSource="{Binding MyDictionary}" CanUserAddRows="False">
        <DataGrid.Resources>
            <loc:DictionaryConverter x:Key="dicConverter" />
        </DataGrid.Resources>

        <DataGrid.Columns>
            <DataGridTextColumn Header="ID">
                <DataGridTextColumn.Binding>
                    <MultiBinding Converter="{StaticResource dicConverter}" ConverterParameter="True">
                        <Binding Path="." RelativeSource="{RelativeSource AncestorType=DataGridRow}" />
                        <Binding Path="ItemsSource" RelativeSource="{RelativeSource AncestorType=DataGrid}" />
                    </MultiBinding>
                </DataGridTextColumn.Binding>                    
            </DataGridTextColumn>

            <DataGridTextColumn Header="Name">
                <DataGridTextColumn.Binding>
                    <MultiBinding Converter="{StaticResource dicConverter}" ConverterParameter="False">
                        <Binding Path="." RelativeSource="{RelativeSource AncestorType=DataGridRow}" />
                        <Binding Path="ItemsSource" RelativeSource="{RelativeSource AncestorType=DataGrid}" />
                    </MultiBinding>
                </DataGridTextColumn.Binding>
            </DataGridTextColumn>
        </DataGrid.Columns>
    </DataGrid>