如何在MVVM模式中使用WPF转换器?

Edw*_*uay 17 wpf mvvm

假设我有一个绑定到ViewModel A的View,它有一个可观察的集合Customers.

这个MVVM模式的一个优点是我还可以将View绑定到ViewModel B,后者用不同的数据填充它.

但是如果在我的View转换器转换器中显示我的客户,例如我有一个接受合同的"ContractToCustomerConverter"并返回要显示的相应客户.

这个问题是转换器存在于MVVM模式之外,因此不知道我的ViewModel有另一个客户来源.

  • 有没有办法让View将ViewModel传递给Converter,以便它参与MVVM模式提供的解耦?
  • 有没有办法让我以某种方式在我的ViewModel中包含转换器,以便转换器使用ViewModel可用的当前依赖项?
  • 或者转换器只是美化代码隐藏,因此没有在MVVM模式中使用,所以如果你使用MVVM,那么你只需要创建自己的"转换器"(ViewModel类上的方法),它们返回像Image对象,Visibility对象,FlowDocuments之类的东西.等在视图上使用,而不是使用转换器?

(我在看到MVVM模板工具包下载附带的WPF演示应用程序中使用转换器后遇到了这些问题,解压后请参阅"Messenger Sample".)

Tho*_*que 12

我通常在MVVM中根本不使用转换器,除了纯UI任务(例如BooleanToVisibilityConverter).恕我直言,您应该在ContractViewModel中声明CustomerViewModel类型的Customer属性,而不是使用ContractToCustomerConverter


Edw*_*uay 11

这次谈话中,有一条评论同意Kent的立场,而不是完全使用转换器,这很有趣:

ViewModel基本上是类固醇的值转换器.它需要"原始"数据并将其转换为呈现友好的内容,反之亦然.如果您发现自己将元素的属性绑定到ViewModel的属性,并且您正在使用值转换器,请停止!为什么不在ViewModel上创建一个公开"格式化"数据的属性,然后完全删除值转换器?

这次谈话中:

我可以在MVVM架构中看到用于值转换器的唯一地方是跨元素绑定.如果我将面板的可见性绑定到CheckBox的IsChecked,那么我将需要使用BooleanToVisibilityConverter.


Ken*_*art 8

转换器应该很少与MVVM一起使用.事实上,我努力不使用它们.VM应该执行视图完成任务所需的所有操作.如果视图需要Customer基于a Contract,则CustomerVM上应该有一个属性,每当Contract更改时由VM逻辑更新.

这个MVVM模式的一个优点是我还可以将View绑定到ViewModel B,后者用不同的数据填充它.

我对这个说法提出异议 根据我的经验,视图不是在不同的VM类型之间共享,也不是MVVM的目标.

  • 好的,我看到你不应该在不同的虚拟机之间共享关于视图的观点,但ViewModel应该能够由不同的视图共享,因此MVVM的可测试性的优势,对吧?您应该能够将模拟视图和模型模型连接到ViewModel,以确保它从模拟模型接收的所有数据组合都生成暴露给视图的正确属性值.你同意吗? (3认同)

jas*_*son 5

对于那些在视图中实际上没有说"非平凡转换器"的人,你如何处理以下内容?

假设我有一个气候传感器模型,它代表给定位置的各种仪器(气压计,湿度计,温度计等)的时间序列读数.

假设我的视图模型从我的模型中公开了一个可观察的传感器集合.

我有一个包含WPF工具包的视图,该工具包DataGrid绑定到视图模型,其ItemsSource属性设置为可观察的传感器集合.如何为给定的传感器表示每种仪器的视图?通过显示小图(认为爱德华托佛特火花这里),其生成通过使用转换器的时间序列变换为图像源(TimeSeriesToSparklineConverter)

以下是我对MVVM的看法:模型将数据暴露给View Models.视图模型将行为,模型数据和状态公开给View.视图可以直观地表示模型数据,并为符合视图模型状态的行为提供界面.

因此,我不相信迷你图像在模型中(模型是数据,而不是它的特定视觉表示).我也不相信迷你图像会出现在视图模型中(如果我的视图想要以不同的方式表示数据,比如显示系列的最小值,最大值,平均值,标准偏差等的网格行?).因此,在我看来,View应该处理将数据转换为所需表示的工作.

因此,如果我想在命令行界面而不是WPF GUI中公开某些视图模型的行为,模型数据和给定状态,我不希望我的模型或我的视图模型包含图像.这是错的吗?我们有一个SensorCollectionGUIViewModel和一个SensorCollectionCommandLineViewModel?这对我来说似乎是错的:我认为视图模型是视图的抽象表示,而不是具体的,并且与这些名称所暗示的特定技术相关联.

这就是我对MVVM不断发展的理解.那么对于那些不使用转换器的人来说,你在这做什么?

  • 我看到你描述的问题是这样的:使用一个值转换器,你可以制作一个ClimateSensorToSparklineGraphConverter,它采用一系列气候传感器并输出一个图像.对于像创建位图图像这样的东西,你不会用DataTemplate和包含ViewModels的ViewModel集合来做这件事,在某些时候你需要C#代码来创建图像.问题出现在转换器中,您还可以访问例如Users集合以确定允许当前用户查看的内容.这会破坏MVVM,因为ViewModel应该注入用户. (3认同)