本文共 4249 字,大约阅读时间需要 14 分钟。
WEB前端最常见驱动方式就是事件了, 所有交互等等都是通过事件,前端的常见事件有:
UI事件;焦点事件;鼠标事件;滚轮事件;文本事件;键盘事件;变动事件;
现在网页上有一个输入框, 如果我们要对用户输入的字符串进行过滤, 或者是截获用户的输入进行处理的话, 我们要肿么办
同学们纷纷举手说:“老师,我知道,是使用添加事件“,
老师也很欣慰地点了点头, 这群家伙真的是越来越聪明了,
老师又问了”如果要取消用户的输入怎么办了“,
坐在最前排眼睛最小的同学急忙说”ev.preventDefault(),ev.returnValue = false;"
老师又说“不错啊,都学会抢答了啊, 我裤子都脱了, 你就答这个2?”
过了一秒钟, 又一位同学主动跑到黑板这边写了如下的代码:
MAKER Log:data
"哎哟,不错哦,这个*x"老师说道:"这个就是我们最常用的方法, 直接为元素绑定了keypress事件,然后通过这个事件的回调对用户的输入进行处理";
如果在事件里面的代码多了, 我们又可以把事件的代码单独取出来作为一个函数:
MAKER Log:data
看起来清楚多了是吧, 但是在大的项目中(我说的是如果哇), 我们想要充分解耦代码, 可以事件里面的代码全部重新分开:
函数1 :console.log( code );
函数2:
if(code > 80) {
console.log("code>80");
};
函数3: if(ev.shiftKey === true) { console.log("shift key is pressed!") }; 好吧,现在问题来了.... 现在有要上菜了哇, JS中的自定义事件, 充分利用JS的事件机制, 抄自百科:对于自定义事件最需要了解的一点是,您的代码必须导致这些事件发生。这些事件不会为响应用户或系统的动作而自动发生,即使能够编写导致事件确实以这种方式发生的代码也不例外。包含自定义事件的类模块还必须包括一个唤起事件的公有方法。这个方法通过调用 RaiseEvent 语句并传入为事件定义的任何参数来唤起事件。这些参数按顺序传入为响应事件而运行的事件过程中 自定义事件就是一种的设计模式,比如订阅者发布者模式, 观察者模式等等, 都是自定义事件基础上的模式(个人观点, 勿拍砖), 关键是很多大神写代码喜欢用这一种模式写, 那么我们也可以借鉴, 这样就够了; 我们现在把上面那段通过自定义事件的方式写出来:
MAKER data
楼主你他妈在逗我? 这么多
实现要懂JS的继承:
//d为目标对象, b为一个函数对象; var __extends = this.__extends || function (d, b) { //继承了静态属性 for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; function __() { this.constructor = d; } //继承了原型 __.prototype = b.prototype; d.prototype = new __(); };
其次呢, 自定义事件的代码要懂, 很多地方都有用到;
var EventEmitter = (function () { function EventEmitter() { this._events = {}; } EventEmitter.prototype.emit = function (type) { var _this = this; var args = []; for (var _i = 0; _i < (arguments.length - 1); _i++) { args[_i] = arguments[_i + 1]; } // If there is no 'error' event listener then throw. if (type === 'error') { if (!this._events[type] || (Array.isArray(this._events[type]) && !this._events[type].length)) { if (args[0] instanceof Error) { throw args[0]; } else { throw new Error("Uncaught, unspecified 'error' event."); } return false; } } if (this._events[type]) { this._events[type].forEach(function (handler) { return handler.apply(_this, args); }); return true; } return false; }; EventEmitter.prototype.addListener = function (type, listener) { if ('function' !== typeof listener) { throw new Error('addListener only takes instances of Function'); } var events = this._events; var listeners = events[type]; if (!listeners) listeners = events[type] = []; else if (listeners.indexOf(listener) >= 0) return this; listeners.push(listener); return this; }; EventEmitter.prototype.removeListener = function (type, listener) { var events = this._events; if (!events[type]) return this; var listeners = events[type]; var i = listeners.indexOf(listener); if (i >= 0) listeners.splice(i, 1); return this; }; return EventEmitter; })();
最后通过组合继承, 实现了一个自定义事件类方法:
var TextEvent = (function(Emiter) { __extends(TextEvent, Emiter); function TextEvent() { Emiter.apply(this); }; return TextEvent; }.call(TextEvent,EventEmitter));
我们通过实例化TextEvent, 为这个实例添加自定义的方法;
在onkeypress的事件回调触发自定义事件textEvent.emit("keypress",ev), 最后的最后只要为textEvent绑定自定义事件即可,这样做的优势就是: 我们可以通过removeListener去除事件, 事件函数也可以直接复用, 很灵活;
D
转载地址:http://eexlx.baihongyu.com/