论坛首页 Web前端技术论坛

js模拟点击那点事

浏览 16915 次
精华帖 (1) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (2)
作者 正文
   发表时间:2011-07-28  

在实际的应用开发中,我们会常常用到JS的模事件,但有时会遇到一些问题,比如说点击事件,举个简单的例子,点击表单外的“提交”按钮来提交表单。上代码吧。

Html:

<h3>请单击“提交”,测试提交按钮的单击事件也被触发了。</h3>
<button id="btn">提交</button>
<form action="#" method="get" id="form">
  <input type="text" name="site" value="www.woiweb.net" readonly/>
  <input id="subbtn" type="submit" value="先别点击此按钮提交" onclick="alert('我已经提交了');"/>
</form>

 

Javscript:

<script type="text/javascript">
  var sub = document.getElementById("subbtn");
  var btn = document.getElementById("btn");
//通用方法
btn.onclick = function() {
sub.click();
}
</script>

 

经过测试,IE,FF,Chrome,Opera,Safari都没有问题,均可正常提交表单。

但在实际的设计中,为了让提交按钮更好看,buildder经常把它们用a标签来处理,加个背景图片来模拟按钮,我们仍然用上面的思路来尝试,增加一个a标签,让它来提交表单,我们仅修改html

Html:

<h3>请单击“提交”,测试提交按钮的单击事件也被触发了。</h3>
<button id="btn">提交</button>
<form action="#" method="get" id="form">
  <input type="text" name="site" value="www.woiweb.net" readonly/>
  <!--<input id="subbtn" type="submit" value="先别点击此按钮提交" onclick="alert('我已经提交了');"/> -->
  <a id="subbtn" href="javascript:;" onclick="alert('在此调用提交表单的方法')">模拟提交按钮</a>
</form>

 

Javascript:

<script type="text/javascript">
  var sub = document.getElementById("subbtn");
  var btn = document.getElementById("btn");
//通用方法
btn.onclick = function() {
sub.click();
}
</script>

 

运行后,问题出现了,IE、FF、Opera均OK,但Chrome和Safari不能正常运行,后来网上搜索了下,发现a标签并不是和按钮一样有onclick()事件的,解决办法是针对 IE 和 FF编写不同的逻辑,JS代码如下:
javascript:

<script type="text/javascript">
  var sub = document.getElementById("subbtn");
  var btn = document.getElementById("btn");
//通用方法
btn.onclick = function() {
   //sub.click();
   if (/msie/i.test(navigator.userAgent)) //IE
   {
      sub.fireEvent("onclick");
   } else {
      var e = document.createEvent('MouseEvent');
      e.initEvent('click', false, false);
      sub.dispatchEvent(e);
   }
}
</script>

 

至此,问题解决,虽然这个问题很简单,但很容易被大家忽略,贴出来和大家一起分享。

 

语法:
createEvent(eventType)

参数 描述
eventType 想获取的 Event 对象的事件模块名。关于有效的事件类型列表,请参阅”说明”部分。

返回值

返回新创建的 Event 对象,具有指定的类型。

抛出

如果实现支持需要的事件类型,该方法将抛出代码为 NOT_SUPPORTED_ERR 的 DOMException 异常。

说明

该方法将创建一种新的事件类型,该类型由参数 eventType 指定。注意,该参数的值不是要创建的事件接口的名称,而是定义那个接口的 DOM 模块的名称。

下表列出了 eventType 的合法值和每个值创建的事件接口:

参数 事件接口 初始化方法
HTMLEvents HTMLEvent iniEvent()
MouseEvents MouseEvent iniMouseEvent()
UIEvents UIEvent iniUIEvent()

用该方法创建了 Event 对象以后,必须用上表中所示的初始化方法初始化对象。关于初始化方法的详细信息,请参阅 Event 对象参考。

该方法实际上不是由 Document 接口定义的,而是由 DocumentEvent 接口定义的。如果一个实现支持 Event 模块,那么 Document 对象就会实现 DocumentEvent 接口并支持该方法。

 

参考资料:http://www.w3school.com.cn/xmldom/met_document_createevent.asp
本文链接:http://www.woiweb.net/js-simulate-click-event.html

   发表时间:2011-07-28  
我向来都是对form进行submit的,不过倒没有注意过兼容性的问题。
0 请登录后投票
   发表时间:2011-07-29  
我也来一个,Ext下扩展Ext.Element,使它支持fireEvent模拟事件。(用于开发测试代码)
开发的时候参考了w3c dom相关文档,实测鼠标点击事件是一切OK的

(function(){
	var eventTypes = ["HTMLEvents", "MouseEvents", "UIEvents", "MutationEvents", "Events"];
	var eventMap = {
		HTMLEvents : {
			abort : true,
			blur : true,
			change : true,
			error : true,
			focus : true,
			load : true,
			reset : true,
			resize : true,
			scroll : true,
			select : true,
			submit : true,
			unload : true
		},
		UIEvents : { // 包含MouseEvents
			DOMActivate : true,
			DOMFocusIn : true,
			DOMFocusOut : true,
			keydown : true,
			keypress : true,
			keyup : true
		},
		MouseEvents : {
			click : true,
			mousedown : true,
			mousemove : true,
			mouseout : true,
			mouseover : true,
			mouseup : true
		},
		MutationEvents : {
			DOMAttrModified : true,
			DOMNodeInserted : true,
			DOMNodeRemoved : true,
			DOMCharacterDataModified : true,
			DOMNodeInsertedIntoDocument : true,
			DOMNodeRemovedFromDocument : true,
			DOMSubtreeModified : true
		},
		Events : {
			// 所有事件
		}
	};
	
	var getType = function(ename){
		var foundType = "Events";
		Ext.each(eventTypes, function(type){
			var map = eventMap[type];
			if(map.hasOwnProperty(ename) && map[ename] === true){
				foundType = type;
				return false;
			}
		});
		return foundType;
	};
	
	var defaultCfg = {
		canBubble : true,
		cancelable : true,
		view : window,
		detail : 0,
		screenX : 0,
		screenY : 0,
		clientX : 0,
		clientY : 0,
		ctrlKey : false,
		altKey : false,
		shiftKey : false,
		metaKey : false,
		button : 0,
		prevValue : null,
		newValue : null,
		attrName : null,
		attrChange : 1
	};
	var getDefalutCfg = function(dom, cfg){
		cfg = cfg || {};
		Ext.applyIf(cfg, defaultCfg);
		
		cfg.relatedTarget = cfg.relatedTarget || dom;
		return cfg;
	};
	Ext.override(Ext.Element, {
		/*
		 * 模拟html dom事件
		 */
		fireEvent : function(ename, cfg){
			var e, type, dom = this.dom;
			ename = ename || "";
			if(Ext.isIE){
				e = document.createEventObject();
				Ext.apply(e, cfg);
				dom.fireEvent("on" + ename, e);
			}else{
				type = getType(ename);
				cfg = getDefalutCfg(dom, cfg);
				e = document.createEvent(type);
				switch(type){
					case "UIEvents":
						e.initUIEvent(ename, cfg.canBubble, cfg.cancelable, cfg.view, cfg.detail);
						break;
					case "MouseEvents":
						e.initMouseEvent(ename, cfg.canBubble, cfg.cancelable, cfg.view, cfg.detail,
									cfg.screenX, cfg.screenY, cfg.clientX, cfg.clientY,
									cfg.ctrlKey, cfg.altKey, cfg.shiftKey, cfg.metaKey,
									cfg.button, cfg.relatedTarget);
						break;
					case "MutationEvent":
						e.initMutationEvent(ename, cfg.canBubble, cfg.cancelable, cfg.relatedNode,
									cfg.prevValue, cfg.newValue, cfg.attrName, cfg.attrChange);
						break;
					default: // Events
						e.initEvent(ename, cfg.canBubble, cfg.cancelable);
						break;
				}
				dom.dispatchEvent(e);
			}
		}
	});

})();


使用方法:
// 模拟左键点击按钮(mousedown和mouseup并不是必须,只是为了更真实模拟)
el.fireEvent("mousedown", {button:0});
el.fireEvent("mouseup", {button:0});
el.fireEvent("click", {button:0});
0 请登录后投票
   发表时间:2011-07-29  
为什么搞这么复杂,直接在div上加onclick事件,再调用form的submit()不行吗
0 请登录后投票
   发表时间:2011-07-30  
hh161151 写道
为什么搞这么复杂,直接在div上加onclick事件,再调用form的submit()不行吗

人家要触发原始提交链接上的动作,其实我感觉用form的onSubmit比较好。。。

但有些时候确实需要模拟事件,比如写自动测试代码
0 请登录后投票
   发表时间:2011-07-30  
学习啦。其实javascript这块,我觉得就是操作属性,这些简单觉得没必要大做文章
0 请登录后投票
   发表时间:2011-07-30  
jack1210 写道
学习啦。其实javascript这块,我觉得就是操作属性,这些简单觉得没必要大做文章

等某天你需要的时候就觉得很有必要了
0 请登录后投票
   发表时间:2011-07-30  
关键还是鼠标的动作

AddEventListener  和 AttachEvent没用啊

咕~~(╯﹏╰)b
0 请登录后投票
   发表时间:2011-07-30  
去研究一下jq的trigger怎么实现,应该有所收获
0 请登录后投票
   发表时间:2011-07-30  
勘误下:FF中A是没有click方法的。仅IE和Opera有。
0 请登录后投票
论坛首页 Web前端技术版

跳转论坛:
Global site tag (gtag.js) - Google Analytics