动态事件绑定
来源:互联网 发布:最好企业网络投资理财 编辑:程序博客网 时间:2024/04/30 12:13
今天项目中有一个问题,就是关于动态生成的HTML标签的事件动态绑定,我原来是直接在动态生成的HTML标签后面,执行this.method();方法是可以绑定了,但原来符合的标签进行的多次方法绑定,所以后面会造成同一个事件的多次运行,所以在这里对这个问题进行总结,(总结是个很好的习惯)引用了一段别人的说明总结:
情况一: HTML代码存放在JS中,请看以下代码:
<body>
<p>第1行内容</p>
<p>第2行内容</p>
<p>第3行内容</p>
<script>
var appendhtml=document.createElement("p");
appendhtml.innerHTML="这是插入的内容";
document.body.appendChild(appendhtml);
var nodep=document.getElementsByTagName("p");
for (var i=0;i<nodep.length;i++){
nodep[i].onclick=function(){
console.log("Click Event!");
}
}
</script>
</body>
上面的代码是用原生的Javascript生成的,当此代码执行时,js会在页面中生成第四个P标签,且点击这四个标签的时候,都会触发相应的动作。那么是不是就是说,用js生成的HTML内容,都可以被绑定相应的事件呢?答案是否定的,在上面代码的script标签中,有两个代码段,代码段一是用来向HTML中插入内容的,代码段二是用来绑定事件的,如果把代码段一和代码段二互换位置,发现JS生成的第四个P标签没有绑定上click事件。用以下代码的jquery测试:
$(function(){
$("p").click(function(){
console.log("Click Event");
})
$("<p>这是生成的内容</p>").appendTo("body");
})
发现结果也一样,事件执行成功与否也代码段的顺序有直接的关系。其实原来很好分析,无论是利用getElementsByTagName还是jquery的选择器,当需要的内容还没有被插入时,选择器只会选择页面中已经存在的元素,所以事先没有存在元素是绑定不了事件的。
但是,实际情况是,工作中有可能需要把后来生成的元素绑定上事件,并注册上事件处理函数。例如本网站的留言系统,第一次加载只会显示固定条数的评论,如果评论超过一定数量,剩下的会用ajax的方式进行加载。所有的留言最后都有个回复功能,点击可以恢复相应的留言,也就是说,动态加载上来的留言,也许要绑定click事件,并注册上回复留言的函数。当然偷懒的方法是,为ajax加载上来的内容再注册一个click并再绑定一次相应的函数,但这加大了代码的冗余度,增加系统开销,还会使代码变得难以理解。那么更好的解决办法是什么呢?
可以这样理解,无论HTML内容是不是JS生成的,只要没有跨域,所有页面内的元素都属于这个页面,都能够绑定事件,JS中有个非常重要的概念叫事件冒泡,简单来讲,就是子元素产生的事件,会一直冒泡到最顶级父元素,并能够被父元素监测到。请看下图:
那么,我能不能在被插入元素的父元素上监测冒泡产生的事件,并回调相应的函数呢?答案是当然是肯定的。来看下面的例子,注意网页面里插入内容是在JS代码的最后。
<script>
$(function(){
$("body").delegate("p","click",function(){
console.log("Click Event");
})
$("<p>这是生成的内容</p>").appendTo("body");
})
</script>
这是,发现所有的P元素点击都产生了输出,说明代码运行成功。这里我们用到了jQuery的delegate函数,来看一下官方解释:
Attach a handler to one or more events for all elements that match the selector, now or in the future, based on a specific set of root elements.
根据特定的根元素,把一个或者多个事件注册到指定的元素上,不论这个元素现在是否存在。
在jQuery1.7.3以上的版本中,on方法也可以做这件事,官方有示例说明,这里不再赘述。
jQuery提供一个强大的API来解决这个问题,原生的JS怎么去做呢?下面给出一个简单方案,希望能对大家理解冒泡的原理有所帮助。
<script>
function gelegate(action,selector,callback){
document.addEventListener(action,function(e){
if(selector==e.target.tagName.toLowerCase()||selector==e.target.className){
console.log("Click Event");
callback();
}
})
}
gelegate('click','p',function(){});
var appendhtml=document.createElement("p");
appendhtml.innerHTML="这是插入的内容";
document.body.appendChild(appendhtml);
</script>
1,内联法:直接在HTML中调用,如:<input type="button" onclick="doEventThing(event)">
2,W3C:这个比较通用,因为是标准,如document.getElementById(
"div_1"
).addEventListener(
"click"
,
function
(){alert(
this
.id);},
false
);
3,上面说的一种方法,觉得也不错,通过事件冒泡,在被插入元素的父元素上监测冒泡产生的事件,并回调相应的函数。
总结如上,在此说明:<input type="button" onclick="doEventThing(event)"> ,在doEventThing(event)方法中,this表示window对象,表示当前作用域对象的话,应该直接传this,例如doEventThing(this)
- (Listitem)动态绑定事件
- javsciprt动态绑定事件
- js动态绑定事件
- Jquery动态绑定事件
- 动态绑定按钮事件
- 动态事件绑定
- Jquery动态绑定事件
- 5 动态事件绑定
- jQuery动态事件绑定
- jquery动态绑定事件
- jq 动态绑定事件
- jQuery动态绑定事件
- jquery动态绑定事件
- Button动态绑定事件
- JavaScript:按钮事件动态绑定
- JavaScript动态添加|绑定事件
- javascript动态绑定事件用法
- Jquery 动态绑定事件 live
- Gradle详解-Chapter 4. Using the Gradle Command-Line
- poj2785
- JAVA的IO操作(二)
- Linux 工具-------搜狗输入法for linux
- Spring环境搭建
- 动态事件绑定
- dm6446 初始化流程
- frontend http 前端名字定义问题
- Android service(四)Intent服务
- R语言实战:机器学习与数据分析源代码6(最终弹)
- c++学习心得
- MyBatis
- 快速中值滤波利用VC++和OpenCV调用其封装的动态链接库出现的错误和处理
- 移动渗透top 10