其他分享
首页 > 其他分享> > Ext事件机制

Ext事件机制

作者:互联网

在早期,不存在事件的概念,开发者用javascript的两个函数来模拟事件机制(window.setTimeout和window.setInterval),由于很多原因,如效率低下等,发明了最原始的0级dom事件模型,为元素添加一个事件,在事件上绑定一个处理函数。
缺点: 这种模型不能为元素的事件添加多个处理函数
例如:

	var inp = document.createElement('input');
	inp.id = 'inp1';
	inp.type = 'button';
	inp.value = '点击';
	// 添加点击事件处理函数
	inp.onclick = function(){
		alert('点击!!!click');
	};
	// 不能添加多个处理函数
//	inp.onclick = function(){
//		alert('点击!!!click2');
//	};
	
	// 渲染到页面
	document.body.appendChild(inp);
 element.addEventListener(type, listener, useCapture); // 添加事件
 element.removeEventListener(type, listener, useCapture); // 移除事件

使用方式如下:

window.onload = function(){
	var inp = document.createElement('input');
	inp.id = 'inp1';
	inp.value = '点击';
	inp.type = 'button';
	
	
	// type 事件类型
	// listener 为事件绑定的函数
	// useCapure 事件传播 true=捕获  false=冒泡
	inp.addEventListener('click', test1, false);
	inp.removeEventListener('click', test1, false);
	inp.addEventListener('click', test2, false);
	
	// 特殊浏览器 但IE11已经支持w3c标准
	// IE  attachEvent(); detachEvent();
	//	inp.attachEvent('onclick', test1);
	//	inp.attachEvent('onclick', test2);
	
	document.body.appendChild(inp);
};

function test1(){
	alert('test1');
};
function test2(){
	alert('test2');
}
window.onload = function(){
	var inp = document.createElement('input');
	inp.id = 'inp1';
	inp.value = '点击';
	inp.type = 'button';
	
	inp.addEventLisener('click', function(event){
		alert('input execute...');
		event.stopPropagation();//阻止冒泡事件的发生
	}, false);
	
	var div = document.createElement('div');
	div.addEventListener('click', function(){
		alert('div execute...');
	}, false);
	
	document.body.addEventListener('click', function(){
		alert('body execute...');
	}, false);
	
	div.appendChild(inp);
	document.body.appendChild(div);
	
};
var MyExt = {};

MyExt.EventManager = {
	
	// 添加监听
	addListener:function(element, eventName, fn, useCapture){
		if(element.addEventListener){
			element.addEventListener(eventName, fn, useCapture);
		} else if(element.attachEvent){
			element.attachEvent('on'+eventName, fn);
		}
	},
	
	// 移除监听
	removeListener:function(element, eventName, fn, useCapture){
		if (element.removeEventListener){
			element.removeEventListener(eventName, fn, useCapture);
		} else if (element.detachEvent) {
			element.detachEvent('on'+eventName, fn);
		}
	}
	
};


MyExt.EventManager.on = MyExt.EventManager.addListener;
MyExt.EventManager.un = MyExt.EventManager.removeListener;


window.onload = function(){
	var btn = document.getElementById('btn');
	MyExt.EventManager.on(btn, 'click', function(){
		alert('execute ...');
	}, false);
	
	MyExt.EventManager.on(btn, 'click', function(){
		alert('execute again ...');
	}, false);
};

Ext.onReady(function(){
	 // 利用观察者模式实现自定义事件
	 
	 // 1:由于浏览器自己也可以定义内置事件,如click/blur等,
	 //	我们自己也可以有一个类似的类,并可以在此类中定义一些事件
	 var observable = function(){
	 	// 存储自定义的事件类型
	 	this.events = ['start', 'stop'];
	 	
	 	// 设计一种数据结构,可以维护自定义的事件类型和事件之间的绑定关系,如下:
	 	// 			'start':[fn1, fn2, ...]
	 	// 			'stop':[fn1, fn2, ...]
	 	this.listeners = {};
	 };	
	 
	 
	// 2:添加新的自定义事件类型
	observable.prototype.addEvents = function(eventName){
		this.events.push(eventName);
	};
	 
	// 3:为自己的事件类型绑定响应的函数,添加事件监听
	observable.prototype.addListener = function(eventName, fn){
		// 先判断当前事件类型是否已经存在
		if(this.events.indexOf(eventName) == -1){
			this.addEvents(eventName);//当前不存在时,加入该事件
		}
		
		// 获取事件类型绑定的所有的函数
		var arr = this.listeners[eventName];
		// 如果当前这个函数数组不存在,则需要为此事件类型绑定新添加的函数
		if (!arr) {
			arr = [fn];// 直接绑定函数
		} else {
			// 如果当前事件类型已经存在绑定的函数,则校验所绑定的函数中是否已经包含了要绑定的fn函数
			if (arr.indexOf(fn) == -1){
				arr.push(fn);//如果不包含,则加入当前要绑定的函数
			}
		}
		
		// 重新维护一下当前事件类型所绑定的事件数组的关联关系
		this.listeners[eventName] = arr;
		
	};
	
	// 4:移除事件监听
	observable.prototype.removeListener = function(eventName, fn){
		// 先校验要移除的事件类型是否已经定义
		if (this.events.indexOf(eventName) == -1) {
			return;
		}
		
		// 存在要移除的事件类型时
		// 判断当前事件绑定的函数中是否包含要移除的函数
		var arr = this.listeners[eventName];
		if (!arr) {
			return;
		}
		
		// 判断要移除的函数fn存在与当前事件的函数数组中时
		if (arr.indexOf(fn) != -1) {
			// 要移除的函数存在与事件类型对应的函数
			arr.splice(arr.indexOf(fn), 1);
		}
		
	};
	
	 
	// 5、如何触发事件   即调用这个事件类型所对应的所有函数即可
	observable.prototype.fireEvent = function(eventName){
		// 如果没有传递事件类型,或者当前传递的事件类型不存在,则直接返回
		if (!eventName || this.events.indexOf(eventName) == -1) {
			return;
		}
		
		// 存在对应事件
		var arr = this.listeners[eventName];
		if (!arr) {
			return;
		}
		
		for(var i=0, len=arr.length; i<len; i++){
			var fn = arr[i];
			fn.call(fn, this);
		}
		
	};
	 
	// 6、javascript习惯  为原型对象方法起一个简单的名称,方便开发者使用
	observable.prototype.on = observable.prototype.addListener;
	observable.prototype.un = observable.prototype.removeListener;
	observable.prototype.fr = observable.prototype.fireEvent;
	
	
	//测试
	var ob = new observable();
	var fn1 = function(){
		alert('fn1...');
	};
	ob.on('start', fn1);
	
	var fn2 = function(){
		alert('fn2...');
	};
	ob.on('stop', fn2);
	
	// 移除监听
	//ob.un('start', fn1);
	
	ob.fr('start');
	ob.fr('stop');

	
	// 添加新事件
	ob.on('run', function(){
		alert('run');
	});
	
	ob.fr('run');
	
});
  1. Ext.EventManager.on(el, ename, fn);
  2. Ext.EventManager.on(el, {ename1:fn1, ename2:fn2});
  3. Ext.EventManager.on(el, {ename1:{fn:fun}, ename2:{fn:fun}});
Ext.onReady(function(){
	var inp = document.createElement('input');
	inp.type = 'button';
	inp.id = 'inp1';
	inp.value = '点击';
	document.body.appendChild(inp);
	
	var extInp = Ext.get('inp1');

	Ext.EventManager.on(extInp, 'click', function(){
		alert('execute  ...');
	});
	Ext.EventManager.on(extInp, 'click', function(){
		alert('execute again ...');
	});
	
	//	绑定多个事件:方式一
	Ext.EventManager.on(extInp, {
		'click':function(){
			alert('单击!');
		},
		'mouseout':function(){
			alert('移除!');
		}
	});

	//	绑定多个事件:方式二
	Ext.EventManager.on(extInp, {
		'click':{
			fn:function(){
				alert('点击1!');
			}
		},
		'mouseout':{
			fn:function(){
				alert('点击2!');
			}
		}
	});

}

标签:function,inp,alert,eventName,Ext,事件,机制,fn
来源: https://blog.csdn.net/SUNBOYmxbsH/article/details/112094657