4

Учитывая следующий сценарий:ViewModel к ViewModel связи

  1. ViewModelA запускает ViewModelB (через общий контроллер, конечно же, что использует IoC и DI для разрешения типов, необходимых).
  2. ViewModelB необходимо установить значение свойства в ViewModelA.

Неправильно ли просто вводить ViewModelA в ViewModelB через инсталляцию конструктора и просто устанавливать свойство напрямую?

Или ...

Если систему обмена сообщений как EventAggregator от Prism можно использовать для обработки всех связей между ViewModels?

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

ответ

1

Предлагаю вам прочитать this question (and my answer), так как это похоже, но не совсем ваша проблема. Он имеет дело с сообщением свойств между родительскими/дочерними объектами ViewModel.

Давайте посмотрим на простой пример:

  • ViewModelA является родителем и должен представить Сумму некоторого свойства на B
  • ViewModelB является ребенок и имеет свойство, которое нуждается в суммирующий

Таким образом, пользователь делает запрос на редактирование свойства на B и запрос успешно завершен, поэтому B предположительно изменяет значение его свойства и запускает событие PropertyChanged.

ViewModelA может подписаться на мероприятия для всех детей, но, пройдя этот путь, мне это не нравится. Когда детей добавляются и удаляются, у вас есть много бухгалтерии.

Ввод А в В является более чистым, но у вас все еще есть много бухгалтерии. Что делать, если у вас есть действие «Очистить детей» на A? Вы должны помнить, что нужно правильно избавиться от родительских отношений от B до A во всех случаях. Тем не менее, это лучше событий, на мой взгляд, потому что это более явное.

Лично мне нравится идея обмена сообщениями. Я больше знаком с посланником MVVM Light, чем с Призмами, но это та же самая идея ... глобальная шина сообщений. В любое время любой B может сказать: «Я изменил свою собственность!» а затем А прослушивает уведомление и сам вычисляет. Я думаю, что это ваше самое чистое решение с гораздо меньшим количеством бухгалтерии.

+0

В результате я создал MessagingService, который обертывает действия Publish/Subscribe/Unsubscribe EventAggregator. MessagingService вводится в класс ViewModelBase, который я использую, чтобы любой ViewModel в моем приложении мог его использовать. –

+0

@ Крис Суэйн - Мне это нравится. Это подход, который я буду использовать в будущем, если бы мне пришлось иметь ViewModel для связи ViewModel. Однако в моей недавней работе я избегал всех случаев этого, заставляя все общение через Модель. Когда что-то изменяется в Модели, мой Ведущий знает об этом и сообщает ViewModel верхнего уровня, что что-то могло измениться. Затем он передает уведомление по дереву и всем дочерним, внукам и т. Д., ViewModels проверяет свои данные модели, чтобы увидеть, есть ли какие-либо изменения. –

2

Я считаю, что это запах кода, если вам нужны двусторонние ссылки. Часто вы можете заменить одну из ссылок событием.

Позвольте ViewModelB поднять событие, на которое указывает ViewModelA. Полная система обмена сообщениями, подобная той, что найдена в Prism, безусловно, является вариантом, но в вашем сценарии это звучит как «нормальное» событие, которое будет прекрасно.

+0

Я согласен с тем, что в простейшем случае опция события - это путь. Однако мое приложение довольно велико. Таким образом, я закончил работу с решением для обмена сообщениями, так как обмен сообщениями неизбежно понадобился в другом месте приложения. –

0

Вы можете найти примеры применения WPF Application Framework (WAF) Полезно. ViewModels не знают друг о друге. Посредничество между ними осуществляется Controllers.Таким образом, вы можете предотвратить циклические зависимости между объектами ViewModel.

0

Я предлагаю использовать гораздо более светлое выделенное решение Messaging под названием «Light Message Bus». Это не часть какой-либо другой ;-) MVVM framework, но независимый компонент. И я заработал это мгновенно менее чем за 3 минуты.