WPF自学入门(十)WPF MVVM简单介绍
前面文章中,我们已经知道,WPF技术的主要特点是数据驱动UI,所以在使用WPF技术开发的过程中是以数据为核心的,WPF提供了数据绑定机制,当数据发生变化时,WPF会自动发出通知去更新UI。
我们不管是NET中还是WPF中使用模式目的就是想达到高内聚低耦合。在WPF开发中,经典的编程模式是MVVM,是为WPF量身定做的模式,该模式充分利用了WPF的数据绑定机制,最大限度地降低了Xmal文件和CS文件的耦合度,也就是UI显示和逻辑代码的耦合度,如需要更换界面时,逻辑代码修改很少,甚至不用修改。与WinForm开发相比,我们一般在后置代码中会使用控件的名字来操作控件的属性来更新UI,而在WPF中通常是通过数据绑定来更新UI;在响应用户操作上,WinForm是通过控件的事件来处理,而WPF可以使用命令绑定的方式来处理,耦合度将降低。
一、MVVM介绍
MVVM是Model-View-ViewModel(模型-视图-视图模型)的缩写形式,它通常被用于WPF或Silverlight开发。我们可以通过下图来直观的理解MVVM模式:
1、View就是用xaml实现的界面,负责与用户交互,接收用户输入,把数据展现给用户。
2、ViewModel是一个C#类,负责收集需要绑定的数据和命令,聚合Model对象,通过View类的DataContext属性绑定到View,同时也可以处理一些UI逻辑。
3、Model,就是系统中的对象,可包含属性和行为。
三者之间的关系:View对应一个ViewModel,ViewModel可以聚合N个Model,ViewModel可以对应多个View
二、MVVM的优势
MVVM的根本思想就是界面和业务功能进行分离,View的职责就是负责如何显示数据及发送命令,ViewModel的功能就是如何提供数据和执行命令。各司其职,互不影响。在实际的业务场景中我们经常会遇到客户对界面提出建议要求修改,使用MVVM模式开发,当设计的界面不满足客户时,我们仅仅只需要对View作修改,不会影响到ViewModel中的功能代码,减少了犯错的机会。随着功能地增加,系统越来越复杂,相应地程序中会增加View和ViewModel文件,将复杂的界面分离成局部的View,局部的View对应局部的ViewModel,功能点散落在各个ViewModel中,每个ViewModel只专注自己职能之内的事情。ViewModel包含了View要显示的数据,并且知道View的交互代码,所以ViewModel就像一个无形的View。使用MVVM架构具有以下优势
1、易维护
2、灵活扩展
3、易测试
4、用户界面设计师与程序开发者能更好的合作
三、MVVM简单示例
为了让大家直观地了解MVVM的编程模式,下面会用到前面讲到的数据绑定以及命令等知识。
新建WPF项目,名称WPFMVVMDemo。添加用户类,如下图
在WPF术语中,这个叫“模型”,GUI是“视图”。不可思议的是“视图模型”,通过数据绑定将它们绑在一起,它真的是一个很好的适配器能将模型变成某种WPF框架可以使用的东西。所以这个就是“模型”。
接下来我们会非常容易理解创建视图模型:
请注意这个视图模型不是十分正确的。因为我们在视图模型里暴露了属性,我们显然会想使在代码里改变的用户名和公司名自动的显示在视图上
后台代码:
运行结果:
这里我们点击更新按钮不会有任何反应,因为还没有实现数据绑定。此时视图不会收到任何的关于属性改变的通知。要解决这个问题我们必须实现名称为INotifyPropertyChanged的接口。任何实现了这个接口的类,当属性发生改变的时候会通知所有监听者,所以我们需要修改视图模型NameViewModel类:
这里会产生多个事件。首先,我们检查了我们是否真的改变了属性。第二,如果值已经改变,我们向所有监听者注册PropertyChanged事件。现在我们有了一个模型Name和一个视图模型NameViewModel。我们只需要在定义视图。只需要修改视图MainWindow:
运行结果:
本文的demo下载地址:WPFMVVMDemo1.zip
WPF自学入门(十)WPF MVVM简单介绍的更多相关文章
- WPF自学入门(十一)WPF MVVM模式Command命令 WPF自学入门(十)WPF MVVM简单介绍
WPF自学入门(十一)WPF MVVM模式Command命令 在WPF自学入门(十)WPF MVVM简单介绍中的示例似乎运行起来没有什么问题,也可以进行更新.但是这并不是我们使用MVVM的正确方式 ...
- WPF自学入门(六)WPF带标题的内容控件简单介绍
在WPF自学入门(二)WPF-XAML布局控件的文章中分别介绍StackPanel,WarpPanel,DockPanel,Grid,Canvas五种布局容器的使用,可以让我们大致了解容器可以使用在什 ...
- WPF自学入门(十二)WPF MVVM模式提取函数
我们平时在写代码时为了不重复写代码,会进行复制代码或者写通用方法.今天我们就来把上传做的函数提取成为通用的方法调用.把上次写的函数提取为两个主要的文件:ObserableObject和RelayCom ...
- WPF自学入门(十一)WPF MVVM模式Command命令
在WPF自学入门(十)WPF MVVM简单介绍中的示例似乎运行起来没有什么问题,也可以进行更新.但是这并不是我们使用MVVM的正确方式.正如上一篇文章中在开始说的,MVVM的目的是为了最大限度地降低了 ...
- WPF自学入门(三)WPF路由事件之内置路由事件
有没有想过在.NET中已经有了事件机制,为什么在WPF中不直接使用.NET事件要加入路由事件来取代事件呢?最直观的原因就是典型的WPF应用程序使用很多元素关联和组合起来,是否还记得在WPF自学入门(一 ...
- WPF MVVM简单介绍
前面文章中,我们已经知道,WPF技术的主要特点是数据驱动UI,所以在使用WPF技术开发的过程中是以数据为核心的,WPF提供了数据绑定机制,当数据发生变化时,WPF会自动发出通知去更新UI. 我们不管 ...
- WPF快速入门系列(8)——MVVM快速入门
一.引言 在前面介绍了WPF一些核心的内容,其中包括WPF布局.依赖属性.路由事件.绑定.命令.资源样式和模板.然而,在WPF还衍生出了一种很好的编程框架,即WVVM,在Web端开发有MVC,在WPF ...
- WPF自学入门(二)WPF-XAML布局控件
上一篇介绍了xaml基本知识,我们已经知道了WPF简单的语法.那么接下来,我们要认识一下WPF的布局容器.布局容器可以使控件按照分类显示,我们一起来看看WPF里面可以使用哪些布局容器用来布局. 在WP ...
- WPF自学入门(一)WPF-XAML基本知识
一.基本概念 1.XAML是派生自XML的可扩展应用程序标记语言(Extensible Application Markup Language)由微软创造应用在WPF,Silverlight等开发技术 ...
随机推荐
- linux系统文件系统重要知识介绍
[root@Asterplus:~]$ls -lhitotal 48K3684713 -rw------- 1 root root 5.9K Jul 1 00:23 anaconda-ks.cfg36 ...
- haproxy的stick table复制
在上一篇文章中,分析了haproxy的stick table特性和用法,其中特性之一也是很实用的特性是stick table支持在haproxy多个节点之间进行复制(replication). 本文仅 ...
- js中url跳转问题
问题描述:列表中有不同的企业名字,每个企业名字都有一个不同的链接,用id做为参数区分.点击不同的名字,根据id的不同跳转到对应的详情页,设置连接如下: 1. url = http://localhos ...
- java多线程的常见例子
收藏 http://blog.csdn.net/wenzhi20102321/article/details/52524545
- Docker下redis的主从、持久化配置
Docker下redis的主从.持久化配置 redis是k-v型nosql数据库,支持字符串(string).列表(list).集合(set).散列(hash).有序集合(zset:形如member: ...
- python多线程、多进程以及GIL
多线程 使用threading模块创建线程 传入一个函数 这种方式是最基本的,即调用threading中的Thread类的构造函数,然后指定参数target=func,再使用返回的Thread的实例调 ...
- react-native简单demo:实现加载豆瓣电影列表
https://github.com/axel10/react-native-douban' 相关随笔: react-native 开发环境搭建 http://www.cnblogs.com/axel ...
- 怎么修改无法启动的docker容器的配置?
原因: 由于错误的配置导致原来可以启动的docker容器不能启动了.相信很多人的做法是删除容器重建一个,这样也是可以的,但是你的配置和插件就得重新安装,非常麻烦.最小的代价当然是修改原来的配置让他能启 ...
- 关于browser-sync(在多个设备上进行网页调试)的问题点总结
最近在看响应式网站的开发视频,其中有一部分非常有用,就是在多个设备上进行网页调试,通过使用browser-sync来实现,具体的步骤可以参照官网(http://www.browsersync.cn/) ...
- JS获取当前周
var now = new Date() var weekFirstDay = new Date(now- (now.getDay() - 1) * 86400000) var firstMonth ...