0

ユーザーコントロール(DataGridView)にDataGridがあります。このユーザーコントロールは、アプリケーションのどこからでもDataGridのItemsSourceへのバインディングを伝播し、リストKで埋めます。

この例では、カスタム属性を持ついくつかのプロパティを持つKのクラスを定義しましょう。

public class Foo
{
    [Enumeration(IsEnum=true, EnumerationType=typeof(MessageType))] //MessageType is enumeration and is consisted of values: 'Error', 'Warning' and 'Info'
    public MessageType MessageType { get; set; }

    [Enumeration(IsEnum=true, EnumerationType=typeof(FooType))] //FooType is enumeration and is consisted of values: 'Sweet' and 'Salty'
    public FooType FooType { get; set; }
 }

DataGridには、列を自動生成するためのイベントがあります。

private void OnAutoGeneratingColumn(object sender, DataGridAutoGeneratingColumnEventArgs e)
    {
        foreach (Attribute attribute in (e.PropertyDescriptor as System.ComponentModel.PropertyDescriptor).Attributes)
        {
            Utilities.EnumerationAttribute enumAttribute = attribute as Utilities.EnumerationAttribute;

            if (enumAttribute != null
                && enumAttribute.IsEnum)
            {
                DataGridTemplateColumn templateColumn = new DataGridTemplateColumn();

                templateColumn.CellTemplate = (DataTemplate)Resources["enumTemplate"];

                e.Column = templateColumn;
            }
        }
        e.Column.IsReadOnly = true;
   }

「enumTemplate」のリソースは、MergedDictionaryでDataTemplateとして定義されています

<DataTemplate x:Key="enumTemplate">
    <StackPanel>
        <ComboBox/>
    </StackPanel>
</DataTemplate>

私がやろうとしていたのは、グリッドが生成する各ComboBoxのItemsSourceを、string []型のEnum.GetNames(enumAttribute.EnumerationType)の戻り値で設定することです。

ここには多くの匿名性があり、プロパティの名前、それらのタイプ、またはこのDataGridが実行時に表示するオブジェクトのタイプさえわかりません。

私はこれにいくつかの試みをしました...タイプListのプロパティDataSourcesListを定義するような>ここでNamedArrayはコンボボックスを満たすアイテムとプロパティの名前(e.PropertyNameから)を保持し、コンボボックスに使用するNamedArrayを知ることができます生成されている...次のようなもの:

 DataSourcesList.Add(new DataSourceWithMappedName<System.Object>() { MappedName = e.PropertyName, SourceList = Enum.GetNames(enumAttribute.EnumerationType) });

そして、DataTemplateを変更します。

<DataTemplate x:Key="enumTemplate">
    <DataTemplate.Resources>
        <converters:IListToItemsSource x:Key="ilistToItemsSource"/>
    </DataTemplate.Resources>
    <StackPanel>
        <ComboBox ItemsSource="{Binding DataSourcesList, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type local:DataGridView}}, Converter={StaticResource ilistToItemsSource}, ConverterParameter={Binding somethingButAllInVaine}}"/>
    </StackPanel>
</DataTemplate>

、ただし、ConverterParameterはDependencyObjectではなく、バインドできないため、これを行うことはできません。

たぶん、列挙型だけでなく、コレクションのバインドにも同じ原則を後で使用する必要があることを述べる必要があります。

ですから、一般的なGridViewでの一般的なComboBox表現の解決策を誰かが手伝ってくれませんか。

Tnxとハッピーコーディング。

4

1 に答える 1

1

DataTemplateおそらく、コードで設定する方が簡単でしょう。を定義することから始めて、を から得られるdatatemplateに設定します。ComboBox ItemSource Binding SourceList of StringEnum.GetNames()

コードウェイ

        // Create template
        DataTemplate newTemplate = new DataTemplate();
        FrameworkElementFactory stackFactory = new FrameworkElementFactory(typeof(StackPanel));
        FrameworkElementFactory comboFactory = new FrameworkElementFactory(typeof(ComboBox));
        Binding newBinding = new Binding();
        newBinding.Source = Enum.GetNames(typeof(enumAttribute.EnumerationType));
        comboFactory.SetBinding(ComboBox.ItemsSourceProperty, newBinding);
        stackFactory.AppendChild(comboFactory);
        newTemplate.VisualTree = stackFactory;

        // Set the template
        templateColumn.CellTemplate = newTemplate;

XAML / コード ウェイ*

<CollectionViewSource x:Key="EnumCollection"/>

<DataTemplate x:Key="enumTemplate"> 
    <StackPanel>
        <ComboBox ItemsSource="{Binding Source={StaticResource EnumCollection}}" />
    </StackPanel>
</DataTemplate>

コード (必ず を設定してくださいCollection Source):

CollectionViewSource enumCollection = (CollectionViewSource)this.FindResource("EnumCollection");
enumCollection.Source =Enum.GetNames(typeof(enumAttribute.EnumerationType));

純粋なXaml

<ObjectDataProvider x:Key="EnumCollection"
                    MethodName="GetValues"
                    ObjectType="{x:Type sys:Enum}">
    <ObjectDataProvider.MethodParameters>
        <x:Type TypeName="YourEnum" />
    </ObjectDataProvider.MethodParameters>
</ObjectDataProvider>

<DataTemplate x:Key="enumTemplate"> 
    <StackPanel>
        <ComboBox ItemsSource="{Binding Source={StaticResource EnumCollection}}" />
    </StackPanel>
</DataTemplate>
于 2012-09-07T19:03:57.000 に答える