0

我制作了一个简单 HTML 页面的 JavaScript 选项卡视图。我已经通过节点使用 JavaScript 为标题标签添加了 onClick 函数。onClick 函数执行一个名为showTab的函数,将this作为参数传递。我知道[object window]

标题标签onClick函数设置如下图:

node.onclick = function() { showTab(this); };

showTab 函数如下:

function showTab(e) 
{ 
    var node = (e && e.target) || (window.event && window.event.srcElement); 
    alert(node.innerHTML); 
}

一切正常,当我单击其中一个标题时,会出现一条带有其 innerHTML 的警报。

但是,我确实使用了谷歌的一些帮助来实现这一点。我想要一些帮助来理解这条线的确切含义:

var node = (e && e.target) || (window.event && window.event.srcElement);

我做了自己的研究,发现它可以被认为是 C# 中的发送者。

但我想彻底了解它是如何工作的,它指的是什么,以及它如何知道哪个节点正在调用 showTab 函数,因为有 3 个标题标签执行相同的功能,都没有 id。

4

3 回答 3

2

啊,处理事件和浏览器的乐趣。

Trident 引擎(Internet explorer 和其他基于该引擎的引擎)处理事件的方式与大多数(全部?)其他浏览器不同。

<html>
<head>
    <title>Test</title>
</head>

<body>
    <button id="test_button">Click me</button>

<script>
// UGLY, UGLY, UGLY... don't really use this
var button = document.getElementById("test_button");
if (window.attachEvent) {
    button.attachEvent("onclick", showTab);
} else {
    button.addEventListener("click", showTab);
}

function showTab(e) 
{

    // Most browsers pass the event as 'e'
    // Microsoft puts the event in window.event
    // Either way, event will now point to the object we want.
    var event = e || window.event;


    // Once again, the different browsers handle the `target` property differently.
    // Target should now point to the right event.
    var target = event.target || event.srcElement;

    alert(target.innerHTML); 
}
</script>
</body>
于 2013-04-13T03:11:14.287 回答
1

这一行:

var node = (e && e.target) || (window.event && window.event.srcElement);

相当于这个逻辑:

var node;
if (e && e.target) {
    node = e.target;
} else if (window.event && window.event.srcElement) {
    node = window.event.srcElement;
} else {
    node = undefined;
}

这段代码的目的是处理旧版本的 IE 不将事件结构传递给事件处理程序的事实。相反,它存储在全局变量中window.event,并且事件目标也存储在事件的差异属性中。

做这样的事情更常见(我认为更具可读性):

function showTab(e) { 
    // get the event data structure into e
    e = e || window.event;

    // get the source of the event
    var node = e.target || e.srcElement;
    alert(node.innerHTML); 
}

实际上,任何体面的项目都应该使用库函数来抽象事件处理程序中的差异,这样特定于浏览器的代码只需要在项目中的一个位置,或者使用像 jQuery 这样的预构建库来处理这类事情。这是一个跨浏览器事件处理程序:

// refined add event cross browser
function addEvent(elem, event, fn) {
    if (typeof elem === "string") {
        elem = document.getElementById(elem);
    }

    function listenHandler(e) {
        var ret = fn.apply(this, arguments);
        if (ret === false) {
            e.stopPropagation();
            e.preventDefault();
        }
        return(ret);
    }

    function attachHandler() {
        // older versions of IE
        // set the this pointer same as addEventListener when fn is called
        // make sure the event is passed to the fn also so that works the same too
        // normalize the target of the event
        window.event.target = window.event.srcElement;
        var ret = fn.call(elem, window.event);   
        if (ret === false) {
            window.event.returnValue = false;
            window.event.cancelBubble = true;
        }
        return(ret);
    }

    if (elem.addEventListener) {
        elem.addEventListener(event, listenHandler, false);
    } else {
        elem.attachEvent("on" + event, attachHandler);
    }
}
于 2013-04-13T03:14:54.467 回答
-1

它正在获取被点击的 dom 元素,要么是 e.target 用于标准兼容的浏览器,要么是 window.event.srcElement(对于较新的 IE,可能是 e.srcElement 而不是)

见:http ://www.quirksmode.org/js/events_properties.html

于 2013-04-13T02:38:14.020 回答