WPF系列之二:解耦View层控件事件与ViewModel层事件的响应
以前的做法:
1.当项目的时间比较紧迫的时候,对UI层中控件的事件的处理,往往采取的是类似Winform中最简单的做法,直接做一个事件的Handler直接去调用VM层的方法。
2.控件只有一个Command属性,其它的事件的处理方法没有办法和ViewModel层进行解耦的时候往往也采取上面提到的方法。
如下图所示:


新的做法:
为了实现事件的处理与View层的解耦,我们可以利用WPF提供的附加属性来为需要的事件添加附加行为。附加属性扮演了一个在View层与Model层牵线的角色。
需要下面三个步骤来实现(以Load事件为例):
1.在ViewModel中定义一个Command属性
winloadedCommand = new DelegateCommand(this.executeWinloadedCommand, this.canWinloadedCommand);
实例化Command
定义ICommand类型的command
#region
private ICommand winloadedCommand;
public ICommand WinloadedCommand
{
get { return winloadedCommand; }
set
{
if (winloadedCommand != value)
{
winloadedCommand = value;
OnPropertyChagned("WinloadedCommand");
}
}
}
private void executeWinloadedCommand()
{
CalculatingStatus = "The WinloadedCommand has been called!";
}
private bool canWinloadedCommand()
{
return true;
}
#endregion
WinloadedCommand
2.定义一个CommandBehaviors类,在其中定义一个ICommand类型的附加属性,并在PropertyChangedCallback的回调中链接事件与实际的command实例之间的调用。
public static class CommandBehaviors
{
public static ICommand GetWindowLoadCommand(DependencyObject obj)
{
return (ICommand)obj.GetValue(WindowLoadCommandProperty);
}
public static void SetWindowLoadCommand(DependencyObject obj, ICommand value)
{
obj.SetValue(WindowLoadCommandProperty, value);
}
// Using a DependencyProperty as the backing store for WindowLoadCommand. This enables animation, styling, binding, etc...
public static readonly DependencyProperty WindowLoadCommandProperty =
DependencyProperty.RegisterAttached("WindowLoadCommand", typeof(ICommand), typeof(CommandBehaviors), new PropertyMetadata(null, OnWindowLoadedCommandPropertyChanged));
public static void OnWindowLoadedCommandPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var frameworkElement = d as FrameworkElement;
if (frameworkElement != null && e.NewValue is ICommand)
{
frameworkElement.Loaded
+= (obj, args) =>
{
if ((e.NewValue as ICommand).CanExecute(obj))
{
(e.NewValue as ICommand).Execute(null);
}
};
}
}
}
CommandBehaviors
3.在xaml中进行Binding

大功告成,运行示例如下:

思考1:如何实现带有参数的调用?Event-〉Command
1.如果参数数据来源于控件本身的属性,可以在链接Event与Command时直接传递参数
2.如果数据来自外界,可以在CommandBehaviors类中定义额外的附加属性,然后将参数绑定到此属性上面,当调用command时,检查该属性。
完毕。
作者:Andy Zeng
欢迎任何形式的转载,但请务必注明出处。
http://www.cnblogs.com/andyzeng/p/3708276.html
WPF系列之二:解耦View层控件事件与ViewModel层事件的响应的更多相关文章
- WPF自定义控件(二)の重写原生控件样式模板
话外篇: 要写一个圆形控件,用Clip,重写模板,去除样式引用圆形图片可以有这三种方式. 开发过程中,我们有时候用WPF原生的控件就能实现自己的需求,但是样式.风格并不能满足我们的需求,那么我们该怎么 ...
- [WPF系列]-使用Binding来同步不同控件的Dependency property
简介 项目中经常会用到,同步两个控件的值,本文就简单列举两种方式来同步不同控件的两个Dependency Property. 示例 效果图: 只使用C#代码: //获取slider1的ValueDep ...
- WPF系列教程——(二)使用Prism实现MVVM设计模式 - 简书
原文:WPF系列教程--(二)使用Prism实现MVVM设计模式 - 简书 本文假设你已经知道MVVM设计模式是什么,所以直接进入正题,今天我们就用Prism来实现WPF的MVVM设计模式,百度上关于 ...
- WPF基础知识、界面布局及控件Binding(转)
WPF是和WinForm对应的,而其核心是数据驱动事件,在开发中显示的是UI界面和逻辑关系相分离的一种开放语言.UI界面是在XAML语言环境下开发人员可以进行一些自主设计的前台界面,逻辑关系还是基于c ...
- WPF基础知识、界面布局及控件Binding
WPF是和WinForm对应的,而其核心是数据驱动事件,在开发中显示的是UI界面和逻辑关系相分离的一种开放语言.UI界面是在XAML语言环境下开发人员可以进行一些自主设计的前台界面,逻辑关系还是基于c ...
- 【转】带checkbox的ListView实现(二)——自定义Checkable控件的实现方法
原文网址:http://blog.csdn.net/harvic880925/article/details/40475367 前言:前一篇文章给大家展示了传统的Listview的写法,但有的时候我们 ...
- WPF 实现跑马灯效果的Label控件,数据绑定方式实现
原文:WPF 实现跑马灯效果的Label控件,数据绑定方式实现 项目中需要使用数据绑定的方式实现跑马灯效果的Label,故重构了Label控件:具体代码如下 using System; using S ...
- WPF中自定义的DataTemplate中的控件,在Window_Loaded事件中加载机制初探
原文:WPF中自定义的DataTemplate中的控件,在Window_Loaded事件中加载机制初探 最近因为项目需要,开始学习如何使用WPF开发桌面程序.使用WPF一段时间之后,感 ...
- WPF 程序如何移动焦点到其他控件
原文:WPF 程序如何移动焦点到其他控件 WPF 中可以使用 UIElement.Focus() 将焦点设置到某个特定的控件,也可以使用 TraversalRequest 仅仅移动焦点.本文介绍如何在 ...
- 我教女朋友学编程Html系列(6)—Html常用表单控件
做过网页的人都知道,html表单控件十分重要.基本上我们注册会员.登录用户,都需要填写用户名.密码,那些框框都是表单控件. 本来今天就想写一些常用的html表单控件,于是开始搜资料,找到了一个网页,作 ...
随机推荐
- pip安装Crypto注意事项
pip install PyCrypto 1.使用pip install Crypto的方式安装的文件夹名称为crypto,而内部引用都用的Crypto路径,因此pip安装后,需要将文件夹名称修改为C ...
- 移动端rem用法总结
先介绍一下这个近年来突起的黑马 CSS3中新增的属性,从IE9开始兼容,手机端都兼容.参考的是<html>这个标签的font-size.rem中的r就是root根的意思.所以rem要比em ...
- CentOS 6.7下创建桌面快捷方式
CentOS 6.7下创建桌面快捷方式如下: 1 在桌面右键,选择“创建启动器" 2 在弹出菜单中,填写名称(显示在桌面上的名字),命令(可执行程序的路径) 3 点击弹出菜单左边的图标,选择 ...
- Java访问控制
转自:菜鸟教程
- C#高级编程(第六版)学习:第三十一章:Windows窗体
第三十一章 Windows窗体 创建Windows窗体应用程序 在文本编辑器中输入: /* * form.cs * a simple windows form * */ using System; u ...
- C++ Primer Plus学习:第二章
C++入门第二章:开始学习C++ 进入C++ 首先,以下是一个C++程序: //myfirst.cpp 显示一行文字 #include<iostream> //预处理器编译指令 int m ...
- Java实现的词频统计
要求: 1.读取文件: 2.记录出现的词汇及出现频率: 3.按照频率降序排列: 4.输出结果. 概要: 1.读取的文件路径是默认的,为了方便调试,将要统计的文章.段落复制到文本中即可:2.只支持英文: ...
- pixi.js tools
pixi群 881784250 Awesome pixi.js tools A list of useful libs/resources/tools for renowned html5 rende ...
- 51nod-1222-最小公倍数计数
题意 给到 \(a,b\) ,求 \[ \sum _{i=a}^b\sum _x\sum _y[x\le y][\text{lcm}(x,y)=i] \] 即最小公倍数在 \([a,b]\) 中的有序 ...
- day4 列表 增删改查 元组
增lis=["a","b","c",5,7,4]lis.append("s")#在列表的末尾追加lis.extend(& ...