nds*_*dsc 28 c# silverlight domain-driven-design prism mvvm
我花了很多时间尝试为以下挑战找到一个优雅的解决方案.我一直无法找到解决问题的解决方案.
我有一个简单的View,ViewModel和Model设置.为了便于解释,我会保持简单.
Model
有一个名为Title
String类型的属性.Model
是在DataContext的View
.View
有TextBlock
这就是数据绑定到Title
的模型.ViewModel
有一个名为方法Save()
,将保存Model
到Server
Server
可推到所做的更改Model
到现在为止还挺好.现在我需要进行两项调整才能使模型与a保持同步Server
.服务器的类型并不重要.只要知道我需要调用Save()
才能将模型推送到Server.
调整1:
Model.Title
属性将需要调用RaisePropertyChanged()
,以转换为所做的更改Model
由Server
到View
.这很好用,因为它Model
是DataContextView
还不错.
调整2:
Save()
保存从所做的更改View
对Model
上Server
.这是我被卡住的地方.当模型被更改时,我可以处理调用Save()的Model.PropertyChanged
事件,ViewModel
但这会使它回显服务器所做的更改.我正在寻找一个优雅而合理的解决方案,如果有意义,我愿意改变我的架构.
Jon*_*Jon 69
在过去,我编写了一个支持从多个位置"实时"编辑数据对象的应用程序:应用程序的许多实例可以同时编辑同一个对象,当有人将更改推送到服务器时,其他所有人都会得到通知, (在最简单的场景中)立即看到这些变化.以下是它的设计总结.
视图始终绑定到ViewModels.我知道这是很多样板,但直接绑定到模型是不可接受的,除了最简单的场景; 它也不符合MVVM的精神.
ViewModels 全权负责推动变革.这显然包括推动对服务器的更改,但它也可能包括将更改推送到应用程序的其他组件.
要做到这一点,ViewModels可能希望克隆它们包装的模型,以便它们可以向应用程序的其余部分提供事务语义(即,您可以选择何时将更改推送到应用程序的其余部分,即您如果每个人都直接绑定到同一个Model实例,则无法执行此操作.隔离这样的改变需要还是更多的工作,但它也开辟了强大的可能性(例如,撤消更改很简单:就是不把他们).
ViewModels依赖于某种数据服务.数据服务是位于数据存储和使用者之间的应用程序组件,用于处理它们之间的所有通信.每当ViewModel克隆其模型时,它还会订阅数据服务公开的相应"数据存储已更改"事件.
这允许ViewModels通知其他ViewModel已推送到数据存储并做出适当反应的"他们的"模型的更改.通过适当的抽象,数据存储也可以是任何东西(例如,该特定应用程序中的WCF服务).
创建ViewModel并为其分配Model的所有权.它立即克隆模型并将此克隆公开给View.它依赖于数据服务,它告诉DS它想要订阅更新此特定模型的通知.ViewModel不知道识别其模型("主键")是什么,但它不需要,因为这是DS的责任.
当用户完成编辑时,他们与View进行交互,后者在VM上调用Command.然后,VM调用DS,推送对其克隆模型所做的更改.
DS会保留更改并另外引发一个事件,通知所有其他感兴趣的VM已经对模型X进行了更改; 模型的新版本作为事件参数的一部分提供.
已分配相同模型所有权的其他VM现在知道外部更改已到达.他们现在可以决定如何更新包含手头所有拼图的视图(模型的"先前"版本,克隆;"脏"版本,克隆;以及"当前"版本,作为事件参数的一部分被推动了).
INotifyPropertyChanged
仅由View使用; 如果ViewModel想要知道模型是否"脏",它总是可以将克隆与原始版本进行比较(如果它已被保留,如果可能的话,我建议这样做).this
作为参数传递给"推送更改"调用,则服务器可以选择不为引发此更改的ViewModel引发"模型已更改"事件.即使它没有,ViewModel也可以选择不做任何事情,如果它看到模型的"当前"版本与其自己的克隆相同.希望这可以帮助; 如果需要,我可以提供更多说明.
我建议将控制器添加到MVVM混合(MVCVM?)以简化更新模式.
控制器侦听更高级别的更改,并在Model和ViewModel之间传播更改.
保持清洁的基本规则是:
正如在另一个答案中提到的,你DataContext
应该是VM(或它的属性),而不是模型.指向DataModel使得很难分离关注点(例如,用于测试驱动开发).
大多数其他解决方案将逻辑放在ViewModels中,这是"不对",但我发现控制器的好处一直被忽视.认为MVVM的缩写!:)
归档时间: |
|
查看次数: |
15432 次 |
最近记录: |