第一,命令模式: 
(1)用于消除调用者和接收者之间直接的耦合的模式,并且可以对(调用这个过程进行留痕操作)
(2)真的不要乱用这个模式,以为他使你简单调用写法变得非常的复杂和有些难以理解。

(3)你的业务出现了 (回退操作)(重做操作)的需求的时候你就要考虑使用这个模式了。
命令的原理:
一种情况为发出者直接作用于执行者,这样耦合度很高,另外一种情况为,在发出者和执行者之间增加一个用存储命令的命令访问库也即命令命令模式。

第二,现在我们通过一个需求来学习该模式
需求为:
1.有一个"添加流程的按钮"单击的时候 就会添加一个新的文本当做流程的描述
2.有"返回","重做" 2个按钮来完成相应的任务。
第三,界面为
<body>
<input type="text" id="flow">
<input type="button" value="添加新流程" onclick="API.addFlow()">
<br>
<input type="button" value="ctrl+z回退" onclick="API.ret()">
<input type="button" value="ctrl+z+x重做" onclick="API.again()">
<div id= "div01"></div> <script src="Js/设计模式第三部分/命令模式/keymaster.min.js"></script>
<script src="Js/设计模式第三部分/命令模式/uuid.js"></script>
<script src="Js/设计模式第三部分/命令模式/(18)命令模式.js"></script>
</body>

效果为,

根据上述图我们逐步完成
步骤一,定义主应用程序----接收者
 function manager() {
this.addFlow=function (id,value) {
//1.得到目标节点
var div=document.getElementById("div01");
var newFlow=document.createElement("div");
newFlow.setAttribute("id",id);
newFlow.innerHTML=value;
div.appendChild(newFlow); }
}

步骤二,为对象(执行者)建立命令访问库 ---意思是可以通过extcute方法访问到addFlow方法

 manager.prototype.extcute=(function () {
/*command 命令对象
* */
return function (command) {
return this[command.method](command.id,command.value);
} })();
步骤三,初始化主类
  var ma = new manager();//可以用该对象,调用其的东西
//用于存储"调用对象命令的"集合
var commands = new Array();
//集合的游标--初始化在末尾
var index = commands.length;

步骤四,客户端----发出者

  var API=function () {
this.addFlow=function () {
//把调用封装起来
var command={
method:"addFlow",
id:new UUID().createUUID(),//产生id的插件
value:document.getElementById("flow").value
};
//把调用对象保存起来,用于回退和重做作用
commands.push(command);
//重新定位游标---赋值记录
index = commands.length;
//调用
ma.extcute(command);
};
/**
* 用于返回的方法
*/
this.ret=function () {
if(index-<){
alert("已经到了最后一步了...");
}else {
var all=document.getElementById("div01").childNodes;
document.getElementById("div01").removeChild(all[all.length-]);
index=index-;
}
};
/**
* 用于重做的方法
*/
this.again=function () {
if(index>=commands.length){
alert("已经到了最前面一步了,不能进行重做...");
}else {
var command=commands[index];//获取当前的命令位置
ma.extcute(command);
index=index+;
}
}
}

步骤五,实例化客户端

API=new API();//实例化

这样html中的事件就可以起作用了。

在这里我们使用插件来让其功能支持自定义的键盘事件,插件名称为:keymaster.js

首先,如html中一样引入文件,

然后值调用key添加自定义的键盘事件

//添加支持ctrl+z--返回
key("ctrl+z",function () { API.ret();
});
//重做---
key("ctrl+shift+x",function () {
API.again(); })

为此我们可以使用键盘的指定组合实现和鼠标点击一样的效果。

这里需要说明一下客户端的API中的id值,也是通过插件来动态生成的------插件名称为:uuid.js。这里附上源码

/*

uuid.js - Version 0.2
JavaScript Class to create a UUID like identifier Copyright (C) 2006-2008, Erik Giberti (AF-Design), All rights reserved. This program is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free Software
Foundation; either version 2 of the License, or (at your option) any later
version. This program is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with
this program; if not, write to the Free Software Foundation, Inc., 59 Temple
Place, Suite 330, Boston, MA 02111-1307 USA The latest version of this file can be downloaded from
http://www.af-design.com/resources/javascript_uuid.php HISTORY:
6/5/06 - Initial Release
5/22/08 - Updated code to run faster, removed randrange(min,max) in favor of
a simpler rand(max) function. Reduced overhead by using getTime()
method of date class (suggestion by James Hall). KNOWN ISSUES:
- Still no way to get MAC address in JavaScript
- Research into other versions of UUID show promising possibilities
(more research needed)
- Documentation needs improvement */ // On creation of a UUID object, set it's initial value
function UUID(){
this.id = this.createUUID();
} // When asked what this Object is, lie and return it's value
UUID.prototype.valueOf = function(){ return this.id; }
UUID.prototype.toString = function(){ return this.id; } //
// INSTANCE SPECIFIC METHODS
// UUID.prototype.createUUID = function(){
//
// Loose interpretation of the specification DCE 1.1: Remote Procedure Call
// described at http://www.opengroup.org/onlinepubs/009629399/apdxa.htm#tagtcjh_37
// since JavaScript doesn't allow access to internal systems, the last 48 bits
// of the node section is made up using a series of random numbers (6 octets long).
//
var dg = new Date(, , , , , , );
var dc = new Date();
var t = dc.getTime() - dg.getTime();
var h = '-';
var tl = UUID.getIntegerBits(t,,);
var tm = UUID.getIntegerBits(t,,);
var thv = UUID.getIntegerBits(t,,) + ''; // version 1, security version is 2
var csar = UUID.getIntegerBits(UUID.rand(),,);
var csl = UUID.getIntegerBits(UUID.rand(),,); // since detection of anything about the machine/browser is far to buggy,
// include some more random numbers here
// if NIC or an IP can be obtained reliably, that should be put in
// here instead.
var n = UUID.getIntegerBits(UUID.rand(),,) +
UUID.getIntegerBits(UUID.rand(),,) +
UUID.getIntegerBits(UUID.rand(),,) +
UUID.getIntegerBits(UUID.rand(),,) +
UUID.getIntegerBits(UUID.rand(),,); // this last number is two octets long
return tl + h + tm + h + thv + h + csar + csl + h + n;
} //
// GENERAL METHODS (Not instance specific)
// // Pull out only certain bits from a very large integer, used to get the time
// code information for the first part of a UUID. Will return zero's if there
// aren't enough bits to shift where it needs to.
UUID.getIntegerBits = function(val,start,end){
var base16 = UUID.returnBase(val,);
var quadArray = new Array();
var quadString = '';
var i = ;
for(i=;i<base16.length;i++){
quadArray.push(base16.substring(i,i+));
}
for(i=Math.floor(start/);i<=Math.floor(end/);i++){
if(!quadArray[i] || quadArray[i] == '') quadString += '';
else quadString += quadArray[i];
}
return quadString;
} // Numeric Base Conversion algorithm from irt.org
// In base 16: 0=0, 5=5, 10=A, 15=F
UUID.returnBase = function(number, base){
//
// Copyright 1996-2006 irt.org, All Rights Reserved.
//
// Downloaded from: http://www.irt.org/script/146.htm
// modified to work in this class by Erik Giberti
var convert = ['','','','','','','','','','','A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'];
if (number < base) var output = convert[number];
else {
var MSD = '' + Math.floor(number / base);
var LSD = number - MSD*base;
if (MSD >= base) var output = this.returnBase(MSD,base) + convert[LSD];
else var output = convert[MSD] + convert[LSD];
}
return output;
} // pick a random number within a range of numbers
// int b rand(int a); where 0 <= b <= a
UUID.rand = function(max){
return Math.floor(Math.random() * max);
} // end of UUID class file

JavaScript命令模式的更多相关文章

  1. javascript设计模式学习之九——命令模式

    一.命令模式使用场景及定义 命令模式常见的使用场景是:有时候需要向某些对象发送请求,但是并不知道请求的接受者是谁,也不知道请求的具体操作是什么.此时希望用一种松耦合的方式来设计程序,使得请求的发送者和 ...

  2. 读书笔记之 - javascript 设计模式 - 命令模式

    本章研究的是一种封装方法调用的方式.命令模式与普通函数有所不同.它可以用来对方法调用进行参数化处理和传送,经过这样处理过的方法调用可以在任何需要的时候执行. 它也可以用来消除调用操作的对象和实现操作的 ...

  3. JavaScript设计模式之命令模式

    一.命令模式概念 命令模式(Command)的定义是:用来对方法调用进行参数化处理和传送,经过这样处理过的方法调用可以在任何需要的时候执行.也就是说该模式旨在将函数的调用.请求和操作封装成一个单一的对 ...

  4. 《JavaScript设计模式与开发实践》读书笔记之命令模式

    1.命令模式 1.1 传统的命令模式 命令模式的应用场景:请求的发送者和请求接收者消除彼此耦合关系 以页面点击按钮为例 点击按钮后,借助命令对象,解开按钮和负责具体行为对象之间的耦合 <body ...

  5. javascript设计模式详解之命令模式

    每种设计模式的出现都是为了弥补语言在某方面的不足,解决特定环境下的问题.思想是相通的.只不过不同的设计语言有其特定的实现.对javascript这种动态语言来说,弱类型的特性,与生俱来的多态性,导致某 ...

  6. 再起航,我的学习笔记之JavaScript设计模式21(命令模式)

    命令模式 概念描述 命令模式(Command): 将请求与实现解耦并封装成独立的对象,从而使不同的请求对客户端的实现参数化 示例代码 命令模式我们可以看成是将创建模块的逻辑封装在一个对象里,这个对象提 ...

  7. javascript设计模式——命令模式

    前面的话 假设有一个快餐店,而我是该餐厅的点餐服务员,那么我一天的工作应该是这样的:当某位客人点餐或者打来订餐电话后,我会把他的需求都写在清单上,然后交给厨房,客人不用关心是哪些厨师帮他炒菜.餐厅还可 ...

  8. JavaScript 设计模式之命令模式

    一.命令模式概念解读 1.命令模式概念文字解读 命令模式(Command)的定义是:用来对方法调用进行参数化处理和传送,经过这样处理过的方法调用可以在任何需要的时候执行.也就是说该模式旨在将函数的调用 ...

  9. JavaScript设计模式-21.命令模式

    <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...

随机推荐

  1. 团队作业3-需求改进&原型设计

    选题:实验室报修系统 实验室设备经常会发生这样或那样的故障,靠值班人员登记设备故障现象,维护人员查看故障记录,进行维修,然后登记维修过程与内容,以备日后复查,用这种方式进行设备运营管理,它仅仅起到一个 ...

  2. 201521123027 <java程序设计>第八周学习总结

    1.本周学习总结 1.1思维导图 2.书面作业 Q1.List中指定元素的删除(题目4-1) 1.1 实验总结 总结:判断List中是否存在指定元素,需要用到equals方法,若存在就用remove进 ...

  3. 201521123032 《Java程序设计》第2周学习总结

    1. 本周学习总结 本周java回顾了各种数据类型,在java中使用浮点型会不精确,改用double行就好.学习了string的类型,string的对象是不可变的,创建之后不能再修改,在string的 ...

  4. 201521123072《Java程序设计》第1周学习总结

    201521123072<Java程序设计>第1周学习总结 标签(空格分隔): JAVA学习 1,本周学习总结 了解了JDK,JRE,JVM,学会使用cmd中一些简单的命令 了解了Java ...

  5. JAVA课设---五子棋

    1.团队博客链接 JAVA课设-五子棋-团队博客 2.个人负责模块: ①对鼠标事件的处理 , 此模块需处理五子棋的放置问题.颜色转换问题.以及当五子连线时弹出窗口显示结果. ②对MainFrame中主 ...

  6. Java课设(学生信息管理系统)

    1.团队课程设计博客链接 http://www.cnblogs.com/Min21/p/7064093.html 2.个人负责模板或任务说明 设计登陆界面和学生信息界面的设计,学生信息的显示.退出等功 ...

  7. Java课程设计-定时器

    Java课程设计--定时器 1.团队课程设计博客链接 团队博客地址 2.个人负责模块或任务说明 框架构建 时间设置面板,倒计时面板 按钮设置 3.自己的代码提交记录截图 4.自己负责模块或任务详细说明 ...

  8. Shiro第六篇【验证码、记住我】

    验证码 在登陆的时候,我们一般都设置有验证码,但是我们如果使用Shiro的话,那么Shiro默认的是使用FormAuthenticationFilter进行表单认证. 而我们的验证校验的功能应该加在F ...

  9. org.springframework.core.NestedIOException: ASM ClassReader failed to parse class file - probably du

    如果出现类似下面的错误,原因就是JDK版本太高了,我换成1.7就没事了 Caused by: org.springframework.core.NestedIOException: ASM Class ...

  10. XML功能

    REF:https://www.baidu.com/link?url=_-UY8rZVAORlesKTth0F7C8LbvXCL4lSwz6vmQVnTEgmT06NFGdoaD9FbuEQhR7xG ...