JavaScript中DOM树的事件流

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/black_hole2009/article/details/52690276

图片展示了DOM树是如何使用事件流进行事件分发:


Dom树中从最外层的Window至内层具体的html标签都可以通过addEventListener(type, listener, useCapture)方法添加监听事件。

捕获阶段(Capture Phase):

事件分发顺序是从最外层的Window开始,按照顺序:Window-Document-html-body-table-tbody-tr-td由外至内分发。

目标阶段(Target Phase):

事件分发至真正被点击的元素。

冒泡阶段(Bubbling Phase):

事件分发顺序是从最内层的td开始,按照顺序:td-tr-tbody-table-body-html-Document-Window由内往外分发,与事件捕获顺序相反。就像将一个石头扔进水里,气泡由水底向水面上浮一样。


例子:


<style>
	    #testDiv, #testP, #testSpan{
	        margin: 5px;
	        padding: 5px;
	        box-sizing: border-box;
	        cursor: default;
	    }
	    #testDiv{
	        width: 300px;
	        height: 300px;
	        border: indianred 3px solid;
	    }
	    #testP{
	        width: 200px;
	        height: 200px;
	        border: hotpink 3px solid;
	    }
	    #testSpan{
	        display: block;
	        width: 100px;
	        height: 100px;
	        border: orange 3px solid;
	    }
</style>
<body>
    <div id="testDiv">testDiv
        <p id="testP">testP
            <span id="testSpan">testSpan</span>
        </p>
    </div>
</body>

<script>
    var testDiv = document.getElementById("testDiv");
    var testP = document.getElementById("testP");
    var testSpan = document.getElementById("testSpan");

    // 捕获,阶段绑定事件
    window.addEventListener("click", function(e){
        console.log("window 捕获,", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, true);

    document.addEventListener("click", function(e){
        console.log("document 捕获,", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, true);

    document.documentElement.addEventListener("click", function(e){
        console.log("html 捕获,", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, true);

    document.body.addEventListener("click", function(e){
        console.log("body 捕获,", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, true);

    testDiv.addEventListener("click", function(e){
        console.log("testDiv 捕获,", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, true);

    testP.addEventListener("click", function(e){
        console.log("testP 捕获,,", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, true);

    testSpan.addEventListener("click", function(e){
        console.log("testSpan 捕获,", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, true);

    // 冒泡阶段绑定的事件
    window.addEventListener("click", function(e){
        console.log("window 冒泡", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, false);

    document.addEventListener("click", function(e){
        console.log("document 冒泡", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, false);

    document.documentElement.addEventListener("click", function(e){
        console.log("html 冒泡", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, false);

    document.body.addEventListener("click", function(e){
        console.log("body 冒泡", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, false);

    testDiv.addEventListener("click", function(e){
        console.log("testDiv 冒泡", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, false);

    testP.addEventListener("click", function(e){
        console.log("testP 冒泡", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, false);

    testSpan.addEventListener("click", function(e){
        console.log("testSpan 冒泡", "目标节点:" + e.target.nodeName, ", 当前节点:" + e.currentTarget.nodeName);
    }, false);
</script>
点击testSpan标签布局的橙色方框内部,控制台的打印结果如下:



猜你喜欢

转载自blog.csdn.net/black_hole2009/article/details/52690276
今日推荐