WPF: MVVM говорит нет конвертерам, но мне нужны хорошие значения перечисления

на уровне модели я определил перечисление:

public enum MemberStatus
{
    ActiveMember = 0,
    InactiveMember = 1, 
    Associate = 2,
    BoardMember = 3,
    Alumni = 4
}

на мой взгляд, у меня есть поле со списком, которое заполнено этими значениями перечисления:

<UserControl.Resources>

  <ObjectDataProvider 
      x:Key="memberStatusesDataProvider" 
      ObjectType="{x:Type system:Enum}" 
      MethodName="GetValues">
    <ObjectDataProvider.MethodParameters>
      <x:Type TypeName="model:MemberStatus" />
    </ObjectDataProvider.MethodParameters>
  </ObjectDataProvider>

</UserControl.Resources>
...
<ComboBox 
    ItemsSource="{Binding Source={StaticResource memberStatusesDataProvider}}" 
    SelectedItem="{Binding Path=Status}" />
...

это приводит к получению поля со списком с вариантами, которые точно такие же, как значения, определенные в перечислении. Хотя это была моя первоначальная цель, я хочу более приятную презентацию для пользователя, что-то вроде этого:

  • выбор поля со списком :
    • активный член
    • неактивные
    • связать
    • член правления
    • выпускники

кроме того, если язык в приложении изменяется, мне нужны значения перечисления на этом языке. Чтобы справиться с этим, первое, что пришло мне на ум, - создать конвертер для MemberStatus enum значения. Я нашел это beuatiful статьи по теме: http://www.codeproject.com/KB/WPF/FriendlyEnums.aspx но Шаблон MVVM говорит, что не должно быть необходимости создавать их почти вообще - и я согласен с этим. Однако это утверждение не работает в мою пользу в данном примере.

как это должно быть сделано? Спасибо.

4 ответов


мнение, что MVVM делает преобразователи стоимости устаревшими, похоже, пришло от Джоша Смита, который говорит в своем блоге философия MVVM:

... класс ViewModel по существу является преобразователь значения на стероидах, таким образом оказание в разделе ivalueconverter интерфейс не имеет значения для большинства фурнитура.

то, что я беру из этого (и я согласен с ним за то, что это стоит), - это модель представления, ответственная за все преобразования из взгляд модели на мир к взглядам, делая конвертер устаревшим.

наличие перечисления (которое является очень ориентированным на данные типом данных) в модели, подверженной воздействию пользовательского интерфейса, определенно является запахом - если только по причине, которую вы видите, показывая пользователю менее идеальную информацию.

поместите отображение из перечисления в строку пользовательского интерфейса в модель представления.


преобразователи полезны для гораздо большего, чем преобразование enums. Конвертеры также больше многоразовые чем один viewmodel есть.

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

  • или, может быть, я хочу, чтобы преобразовать string до DateTime и снова все через привязку данных. Может быть, я хочу преобразовать все в верхний регистр. То есть мой любимый BoolToVisibilityConverter.

Я бы не хотел ставить явные прямые или косвенные код по всему моему VMs просто, чтобы сохранить некоторые группы меньшинств счастливы. Я бы сказал, что они забывают, что конвертеры легко доступны из Expression Blend.

преобразователи являются неотъемлемой частью WPF и suppliment привязки между view и viewmodel.

Я не вижу причин, почему вы не можете использовать их для enums.


в MVVM-это не набор в камне, а в какой части WPF-это и есть-не разрешается. Конвертеры можно использовать, если они легко достигают вашей цели. Я бы даже предложил сделать шаг дальше и сделать MarkupExtension поставить значения enum и их строковые эквиваленты. Вы можете сохранить строки в DescriptionAttribute для каждого значения перечисления.


Я не согласен с тем, что MVVM делает ValueConverters устаревшими. Существует более чем достаточно сценариев, в которых реализация ValueConverter имеет больше смысла как реализация преобразования в классе ViewModel.

вас может заинтересовать BookLibrary пример применения WPF Application Framework (WAF). Он показывает, как перечисление может быть локализовано в приложении MVVM. Пожалуйста, взгляните на библиотеку.Демонстрация / Преобразователи / класс LanguageToStringConverter.