Параметры WPF ObjectDataProvider - PullRequest
       48

Параметры WPF ObjectDataProvider

0 голосов
/ 29 октября 2018

У меня есть ObjectDataProvider для получения списка членов перечисления:

<ObjectDataProvider x:Key="GetEnumContents" MethodName="GetValues" ObjectType="{x:Type System:Enum}">
    <ObjectDataProvider.MethodParameters>
         <x:Type TypeName="Data:Status"/>
    </ObjectDataProvider.MethodParameters>
</ObjectDataProvider>

, который я затем использую с:

<ComboBox SelectedItem="{Binding Status, UpdateSourceTrigger=PropertyChanged}" ItemsSource="{Binding Source={StaticResource GetEnumContents}}" />

В том же окне я бы хотел иметь поле со списком для другого перечисления. Как передать тип enum из объявления ComboBox?

Я видел решения подобных проблем, например:

Path="MethodParameters[0]"

но здесь я не хочу связывать параметр с чем-либо, я просто хочу жестко закодировать его в объявлении ComboBox.

Есть идеи?

1 Ответ

0 голосов
/ 29 октября 2018

ObjectDataProvider не поддерживает такую ​​функциональность, но вы можете «подделать» ее с помощью умного злоупотребления использованием Binding и IValueConverter.

Сначала IValueConverter:

class EnumConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        return Enum.GetValues((Type)parameter);
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

Вот как вы его используете:

<Window
    x:Class="EnumTest.MainWindow"
    [...snip...]
    xmlns:local="clr-namespace:EnumTest"
    Title="MainWindow"
    Width="800"
    Height="450"
    mc:Ignorable="d">
    <Window.Resources>
        <local:EnumConverter x:Key="EnumConverter" />
    </Window.Resources>
    <StackPanel>
        <ComboBox ItemsSource="{Binding Converter={StaticResource EnumConverter}, ConverterParameter={x:Type local:MyEnum1}}" />
        <ComboBox ItemsSource="{Binding Converter={StaticResource EnumConverter}, ConverterParameter={x:Type local:MyEnum2}}" />
    </StackPanel>
</Window>

Некоторые контрольные перечисления:

enum MyEnum1
{
    Red,
    Green,
    Blue,
}

enum MyEnum2
{
    Cat,
    Dog,
    Fish,
    Bird,
}

Это дает следующий вывод: enter image description here enter image description here

Это использует тот факт, что вы можете передать дополнительный параметр в IValueConverter, который я использую для передачи Type перечисления в преобразователь. Преобразователь просто вызывает Enum.GetNames для этого аргумента и возвращает результат. Фактический Binding будет фактически привязан к тому, чем будет DataContext из ComboBox. EnumConverter просто счастливо игнорирует его и вместо этого работает с параметром.


UPDATE

Работает еще лучше, привязываясь непосредственно к типу, полностью пропуская ConverterParameter, вот так:

<ComboBox ItemsSource="{Binding Source={x:Type local:MyEnum1}, Converter={StaticResource EnumConverter}}" />

С настройками преобразователя:

public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
    return Enum.GetValues((Type)value);
}

Тот же результат с меньшим набором текста и более легким для понимания кодом.

...