首頁 > web前端 > js教程 > JavaScript事件使用指南的詳細介紹

JavaScript事件使用指南的詳細介紹

黄舟
發布: 2017-03-13 17:11:37
原創
1272 人瀏覽過

事件流

事件流描述的是從頁面中接收事件的順序,IE和Netscape提出來差不多完全相反的事件流的概念,IE事件流是事件冒泡流,Netscape事件流是事件捕獲流。

事件冒泡

IE的事件流叫做事件冒泡,即事件開始時由最具體的元素(文檔中嵌套最深的那個節點)接收,然後逐級向上(一直到文件);如下程式碼:

<p id = "p">
    <span id="span">
        <a id="aTag">事件测试</a>
    </span>
</p>
登入後複製

JS如下:

document.getElementById("aTag").addEventListener(&#39;click&#39;,aTag);
document.getElementById("span").addEventListener(&#39;click&#39;,span);
document.getElementById("p").addEventListener(&#39;click&#39;,p);
function aTag(e) {
    alert("点击的是a标签");
}
function span(e) {
    alert("点击的是span标签");
}
function p(e) {
    alert("点击的是p标签");
}
登入後複製

當點選「事件測試」文字後,那麼click事件會依照下列順序傳播;

# 1)先印出:點選的是a標籤

2) 再列印出:點選的是span標籤

3) 最後列印出:點選的是p標籤

4)  最後肯定是document文檔。

所有現代瀏覽器都支援事件冒泡。

事件擷取:

事件擷取與事件冒泡事件流正好相反的順序,事件擷取的事件流是最外層逐級向內傳播,也就是先document,然後逐級p標籤, span標籤, a標籤;

上面的JS程式碼改成如下:

document.getElementById("p").addEventListener(&#39;click&#39;,p,true);
document.getElementById("aTag").addEventListener(&#39;click&#39;,aTag,true);
document.getElementById("span").addEventListener(&#39;click&#39;,span,true);
登入後複製

第三個參數設定為true,即為捕獲事件,預設為false;否則的話,事件流還是和上面的一樣,因為不管是在IE還是標準瀏覽器下,事件冒泡瀏覽器都支援的。

DOM事件流

DOM2級事件規定的事件流包括三個階段,分別是:事件捕獲階段,處於目標階段和事件冒泡階段。示意圖就不畫了,具體的可以看看書。

DOM0級事件處理程式

如下程式碼是DOM0級事件處理程序:

var btn = document.getElementById("btn");
btn.onclick = function(){
     alert("Clicked");
};
登入後複製

使用DOM0級方法指定的事件處理程序被認為是元素的方法,處理程序是在元素的作用域進行的,程式中this是引用的是當前元素。

<p id="btn">btn</p>
var btn = document.getElementById("btn");
btn.onclick = function(){
    alert(this.id); // 弹出btn
}
登入後複製

點擊元素btn後,透過this.id取得元素的屬性id,也可以透過this存取元素的任何屬性和方法,以此方式新增的事情處理程序在事件流的冒泡階段處理。

也可以刪除透過DOM0級方法指定的事件處理程序,只要將事件處理程序的屬性值設為null即可。

btn.onclick = null; // 刪除事件處理程序;

如下JS程式碼改成如下:

var btn = document.getElementById("btn");
btn.onclick = function(){
    alert(this.id);
}
btn.onclick = null;
登入後複製

再點選btn後,沒有任何反應;

DOM2級事件處理程序

DOM2級事件定義了2個方法,用於處理指定和刪除事件處理程序的操作;

##addEventListener ()和removeEventListener()。所有DOM節點都包含這兩個方法,他們包含三個參數,第一個參數為事件類型;第二個參數為事件

函數,第三個參數為布林值,如果是true的話,說明是事件流是捕獲事件,如果是false的話,那麼事件流就是冒泡事件;

#比如如上的btn程式碼,我們改成如下:

var btn = document.getElementById("btn");
btn.addEventListener(&#39;click&#39;,function(e){
    alert(this.id);
},false);
登入後複製

上面的點擊事件是在冒泡階段被觸發,與DOM0級方法一樣,這裡添加的事件處理程序也是在其依副的元素作用域中運行,使用DOM2級添加事件處理程序的好處是可以添加多個事件處理程序,如下程式碼:

var btn = document.getElementById("btn");
btn.addEventListener(&#39;click&#39;,function(e){
    alert(this.id);
},false);
btn.addEventListener('click',function(e){
    alert("我是来测试的");
},false);
登入後複製

上面的程式碼被彈出2次對話框,而在DOM0級是不可以的;它永遠是執行最後一次的。

addEventListener新增的事件只能使用removeEventListener來刪除相對應的事件,那麼如上的JS不能按照上面的方式來寫哦!需要給定義一個函數;如下:

btn.addEventListener(&#39;click&#39;,handler,false);
function handler(e){
   alert(this.id);
}
登入後複製

可以使用以下方式對click事件刪除;如下程式碼:

btn.removeEventListener('click',handler);

上面的是標準瀏覽器下處理的事件,下面我們來看看在IE下處理的事件;

IE事件處理的程式

IE實作了與DOM類似的2個方法,分別是attachEvent()和detachEvent(),這兩個方法只接受2個參數,第一個參數是事件名稱,第二個參數是要處理的函數;由於IE8及更早版本只支援事件冒泡,所以透過attachEvent()加入的事件處理程序會被加入到冒泡階段;

下面是IE事件處理程序的程式碼如下:

btn.attachEvent(&#39;onclick&#39;,handler);
function handler(e){
    alert(this); // window
}
登入後複製

注意:attachEvent的事件名稱是onclick,而addEventListener的事件名稱是click,且IE中使用的attachEvent()與使用DOM0級方法的主要區別在於事件處理程序的作用域,在使用dom0級情況下,事件處理程序在其所屬元素的作用域內運行,在使用attachEvent()方法的情況下,事件處理程序在全域作用域下運行,其中的this等於window。

與addEventListener一樣,attachEvent也可以註冊多個點擊click事件,如下程式碼:

btn.attachEvent(&#39;onclick&#39;,function(e){
    alert("1");
});
btn.attachEvent(&#39;onclick&#39;,function(e){
    alert("2");
});
登入後複製

但是与Dom方法不同的是,这些事件处理程序不是以添加他们的顺序执行,而是以相反的顺序触发,比如如上代码,会先弹出2,然后弹出1对话框;

使用attachEvent注册的事件只能使用detachEvent()方法来移除;

下面我们可以来编写跨浏览器的事件处理程序;代码如下:

var EventUtil = {
    addHandler: function(element,type,handler) {
        if(element.addEventListener) {
                        element.addEventListener(type,handler,false);
        }else if(element.attachEvent) {
                    element.attachEvent("on"+type,handler);
        }else {
            element["on" +type] = handler;
        }
    },
    removeHandler: function(element,type,handler){
        if(element.removeEventListener) {
                    element.removeEventListener(type,handler,false);
        }else if(element.detachEvent) {
                    element.detachEvent("on"+type,handler);
        }else {
            element["on" +type] = null;
        }
    }
};
登入後複製

下面我们可以使用这个封装的函数代码来测试之前的代码了,代码改成如下所示:

function handler(){
    alert(1);
}
EventUtil.addHandler(btn,&#39;click&#39;,handler);
登入後複製

在IE或者标准浏览器下都会弹出1;如果我们需要移除click事件的话,我们可以使用如下代码:

EventUtil.removeHandler(btn,’click’,handler);

然后在标准浏览器下或者IE下点击btn元素都没有反应;

事件对象:

在触发DOM上的某个事件时,会产生一个事件对象event,这个对象中包含着所有与事件有关的信息;包括导致事件的元素,事件的类型以及其他与特定事件相关的信息。我们来看看dom0级和dom2级的事件对象Event;

比如如下代码:

var btn = document.getElementById("btn");
btn.onclick = function(e){
    console.log(e);
}
登入後複製

打印如下:

下面我们来看看最基本的成员的含义吧;如下:

属性/方法类型含义
bubblesBoolean事件是否冒泡
cancelableBoolean是否可以取消事件的默认行为
currentTargetBoolean事件处理程序当前正在处理事件的那个元素
defaultPreventedBoolean为true 表示已经调用了preventDefault()
detailInteger与事件相关的细节信息
eventPhaseInteger调用事件处理程序的阶段:1表示捕获阶段,2表示“处于目标”,3表示冒泡阶段
preventDefault()Function取消事件的默认行为。如果cancelable是true,则可以使用这个方法
stopImmediatePropagation()Function取消事件的进一步捕获或冒泡,同时阻止任何事件处理程序被调用
stopPropagation()Function取消事件的进一步捕获或冒泡。如果bubbles为true,则可以使用这个方法
targetElement事件的目标
typeString被触发的事件的类型
viewAbstractView与事件关联的抽象视图。等同于发生事件的window对象

理解currentTarget与target

在事件处理程序内部,this始终等于currentTarget值,即currentTarget是指当前被触发或者说正在处理事件的那个元素,而target是指当前的目标元素;比如如下代码,对btn按钮触发点击事件,那么e.currentTraget指向了this,e.target也指向了this;如下代码:

var btn = document.getElementById("btn");
btn.onclick = function(e){
    console.log(e.currentTarget == this); // true
    console.log(e.target == this);  // true
}
登入後複製

但是如果我对document.body触发点击的话,那么e.currentTarget就指向了document.body了,那么e.target 指向与 btn那个元素了,如下代码:

document.body.onclick = function(e){
    console.log(e.currentTarget === document.body); // true
    console.log(document.body === this);  // true
    console.log(e.target === document.getElementById("btn")); //true
};
登入後複製

现在应该能理解currentTarget与target的区别吧!currentTarget就是指被点击的那个元素,但是target是当前点击的目标元素,如上代码,由于btn上并没有注册事件,结果click事件就冒泡到了document.body,在那里事件才得到了处理。

理解标准浏览器下的事件对象与IE下的事件对象

标准浏览器下的事件对象是event,比如btn点击后;如下代码:

var btn = document.getElementById("btn");
btn.onclick = function(){
    console.log(event); //标准浏览器下打印事件对象
    console.log(event.type);//&#39;click&#39;
}
btn.onclick = function(){
    // IE下打印的事件对象window.event
    console.log(window.event);
    console.log(window.event.type); // &#39;click&#39;
 }
登入後複製

上面的写法是在DOM0级上注册事件,如果我们在Dom2级上注册事件的话,那么就会有一个事件对象event作为参数传入事件到函数中,如下:

var btn = document.getElementById("btn");
EventUtil.addHandler(btn,&#39;click&#39;,function(e){
    console.log(e);
});
登入後複製

理解特定事件的默认行为事件

在标准浏览器下,在阻止特定事件的默认行为,可以使用preventDefault()方法,比如如下,我点击一个连接,按道理是打开一个新连接窗口,但是我使用preventDefault()方法可以阻止默认行为,阻止打开新窗口;如下代码:

HTML:<a href="http://www.baidu.com" id="alink" target="_blank">打开新连接</a>
JS如下:
var alink = document.getElementById("alink");
alink.onclick = function(e){
    console.log(e)
    e.preventDefault();
}
登入後複製

就可以阻止页面进行跳转了~ 这是标准浏览器下处理方式,下面我们来看看IE是如何处理默认事件的;

IE下使用returnValue属性来取消给定事件的默认行为,只要将returnValue属性值设置为false即可,就可以阻止浏览器的默认行为,如下代码:

alink.onclick = function(){
    console.log(window.event)
    window.event.returnValue = false;
}
登入後複製

标准浏览器下与IE下的事件目标的区别

标准浏览器下使用e.target来指定当前被点击的目标元素,如下代码所示:

var btn = document.getElementById("btn");
btn.onclick = function(){
    console.log(event); 
    console.log(event.target); // 打印事件目标元素
}
登入後複製

IE下是使用event.srcElement来指定当前的目标元素,如下代码:

btn.onclick = function(){
    console.log(event); 
    console.log(window.event.srcElement);
}
登入後複製

理解标准浏览器与IE下阻止事件传播的区别

在标准浏览器下我们可以使用stopPropagation()方法来停止事件在DOM层次中的传播,即取消事件中的冒泡或者捕获。从而避免触发注册在document.body上面的事件处理程序,如下所示:

var btn = document.getElementById("btn");
btn.onclick = function(e){
    alert(1);
    e.stopPropagation();
}
document.body.onclick = function(){
    alert(2);
}
登入後複製

如上代码,如果我不使用stopPropagation()阻止冒泡事件的话,那么在页面中会先弹出1,然后弹出2,如果使用stopPropagation()方法的话,只会在页面上弹出1,就不会冒泡到body上面去;

IE下停止冒泡的话,我们可以使用cancelBubble属性,我们只要将此属性设置为true,即可阻止事件通过冒泡触发document.body中的注册事件。但是IE是不支持捕获事件的,但是stopPropagation()即支持捕获事件又支持冒泡事件的。如下代码:

btn.onclick = function(e){
    alert(1);
    window.event.cancelBubble = true;
}
document.body.onclick = function(){
    alert(2);
}
登入後複製

如果不设置window.event.cancelBubble 为true的话,就会先弹出1,然后弹出2,如果加上的话,就只会弹出1对话框。

理解了上面的区别后,我们现在可以往EventUtil对象里面添加跨浏览器的方法了;

跨浏览器的事件对象

var EventUtil = {
    addHandler: function(element,type,handler) {
        if(element.addEventListener) {
            element.addEventListener(type,handler,false);
        }else if(element.attachEvent) {
            element.attachEvent("on"+type,handler);
        }else {
            element["on" +type] = handler;
        }
    },
    removeHandler: function(element,type,handler){
        if(element.removeEventListener) {
            element.removeEventListener(type,handler,false);
        }else if(element.detachEvent) {
            element.detachEvent("on"+type,handler);
        }else {
            element["on" +type] = null;
        }
    },
    getEvent: function(event) {
        return event ? event : window.event;
    },
    getTarget: function(event) {
        return event.target || event.srcElement;
    },
    preventDefault: function(event){
        if(event.preventDefault) {
            event.preventDefault();
        }else {
            event.returnValue = false;
        }
    },
    stopPropagation: function(event) {
        if(event.stopPropagation) {
            event.stopPropagation();
        }else {
            event.cancelBubble = true;
        }
    }
};
登入後複製

事件类型:

DOM3级事件规定了以下几类事件;如下:

UI事件: 当用户与页面上的元素交互时触发;

load事件:当页面加载完后(包括所有图像,所有javascript文件,css文件等外部资源),就会触发window上面的load事件,如下代码是加载图片的:

HTML代码:

JS代码如下:

var img = document.getElementById("img");
EventUtil.addHandler(img,&#39;load&#39;,function(event){
      var event = EventUtil.getEvent(event);
      alert(EventUtil.getTarget(event).src);
});
登入後複製

当图片加载完后,就会弹出图片的url地址了;

如果在创建新的img元素时,可以为其指定一个事件处理程序,以便图像加载完成后给出提示,此时,最重要的是在指定src属性之前先指定事件;如下代码所示:

 EventUtil.addHandler(window,&#39;load&#39;,function(){
    var img = document.createElement("img");
    EventUtil.addHandler(img,&#39;load&#39;,function(e){
        e = EventUtil.getEvent(e);
        alert(EventUtil.getTarget(e).src);
    });
    document.body.appendChild(img);
    img.src = "event.png";
});
登入後複製

在图像加载完成后,会弹出图片地址了;

同样的功能,我们可以使用DOM0级的Image对象来实现,在DOM出现之前,开发人员经常使用Image对象在客户端预加载图像,如下代码:

EventUtil.addHandler(window,&#39;load&#39;,function(){
    var img = new Image();
    EventUtil.addHandler(img,&#39;load&#39;,function(e){
        alert(1);
    });
    img.src ="event.png";
});
登入後複製

Script元素也支持load事件,但是IE8及以下不支持,在IE9+,Firefox,Opera,chrome及Safari3+都支持,以便开发开发人员确定动态加载的javascript文件是否加载完毕;比如我们动态创建script标签后,通过load事件判断动态创建的script标签是否加载完毕,代码如下:

EventUtil.addHandler(window,&#39;load&#39;,function(){
    var script = document.createElement("script");
    EventUtil.addHandler(script,&#39;load&#39;,function(e){
        alert(1);
    });
    script.src = "a.js";
    document.body.appendChild(script);
});
登入後複製

焦点事件:当元素获得或失去焦点时触发;

有:blur:在元素失去焦点时触发,这个事件不会冒泡,所有浏览器都支持。

foucs:在元素获得焦点时触发,这个事件不会冒泡,所有浏览器都支持。

鼠标事件:当用户通过鼠标在页面操作时触发;

  1. click事件:在用户单击鼠标按钮或者按下回车键触发;

  2. dblclick事件:在用户双击鼠标按钮时被触发;

  3. mousedown事件:在用户按下了任意鼠标按钮时被触发,不能通过键盘触发这个事件。

  4. mouseenter事件:在鼠标光标从元素外部移动到元素范围之内被触发;这个事件不冒泡;

  5. mousemove事件:当鼠标指针在元素内部移动时重复地触发。

  6. mouseout事件:用户将其移入另一个元素内被触发。

  7. mouseover事件:鼠标指针在元素外部,用户将移入另一个元素的边界时触发,感觉和mouseenter事件类似;

  8. mouseup事件:用户释放鼠标按钮时触发;

页面上所有的元素都支持鼠标事件,除了mouseenter和mouseleave,所有鼠标事件都会冒泡,也可以被取消,而取消鼠标事件将会影响浏览器的默认行为。

理解客户区坐标位置

含义是:鼠标指针在可视区中的水平clientX和垂直clientY坐标;

如下图所示:

代码如下:

EventUtil.addHandler(btn,&#39;click&#39;,function(e){
    e = EventUtil.getEvent(e);
    console.log("可视区X轴坐标为:"+e.clientX + " "+ "可视区Y轴坐标为:"+e.clientY);
});
登入後複製

注意:客户区坐标位置不包含滚动条滚动的位置,因此这个位置不代表鼠标在页面上的位置;

理解页面坐标位置pageX和pageY:

pageX与pageY是指页面坐标的位置,与clientX和clientY的区别是:它包含页面滚动条的位置,如下图所示:

代码如下:

EventUtil.addHandler(btn,&#39;click&#39;,function(e){
    e = EventUtil.getEvent(e);
    console.log("页面X轴坐标为:"+e.pageX + " "+ "页面Y轴坐标为:"+e.pageY);
});
登入後複製

在页面没有滚动条的情况下,pageX与clientX相等,同理pageY与clientY相等。

但是IE8及更早的版本不支持pageX与pageY,不过我们可以使用客户区坐标(client,clientY)和滚动坐标计算出来;因此我们需要用到document.body(混杂模式下)或 document.documentElement(标准模式下)中的scrollLeft和scrollTop属性;

对此我们可以封装代码如下:

EventUtil.addHandler(btn,&#39;click&#39;,function(e){
    e = EventUtil.getEvent(e);
    var pageX = e.pageX,
          pageY = e.pageY;
    if(!pageX) {
    pageX = e.clientX + (document.body.scrollLeft || document.documentElement.scrollLeft);
    }
    if(!pageY) {
    pageY = e.clientY + (document.body.scrollTop || document.documentElement.scrollTop);
    }
    console.log("页面X轴坐标为:"+pageX + " "+ "页面Y轴坐标为:"+pageY);
});
登入後複製

理解屏幕坐标的位置

屏幕横坐标screenX和垂直坐标screenY属性是相对于整个屏幕的。如下图所示:

如下代码测试:

EventUtil.addHandler(btn,&#39;click&#39;,function(e){
    e = EventUtil.getEvent(e);
    console.log("屏幕X轴的坐标为:"+e.screenX + " "+"屏幕Y轴的坐标为:"+e.screenY);
});
登入後複製

理解鼠标滚轮事件:

IE6首先实现了mousewheel事件,此后opera,chrome和safari也都实现了这个事件,当用户通过鼠标滚轮与页面交互,在垂直方向上滚动页面时(无论向上还是向下),就会触发mousewheel事件,这个事件可以在任何元素上触发,最终会冒泡到document(IE8)或window(IE9,Opera,Chrome,Safari)对象,与mousewheel事件对应的event对象外,还有一个属性wheelDelta属性,当用户向前滚动鼠标滚轮时,wheelDelta是120的倍数,当用户向后滚动鼠标滚轮时,wheelDelta是-120的倍数。

将mousewheel事件给页面任何元素或document对象,即可处理鼠标滚轮操作;如下代码:

EventUtil.addHandler(btn,&#39;mousewheel&#39;,function(e){
    e = EventUtil.getEvent(e);
    alert(e.wheelDelta);
});
登入後複製

如上代码,我不是在document对象或者window对象上,而是在页面btn元素上触发的;但是我们要注意,在Opera9.5之前的版本中,wheelDelta值的正负号是颠倒的,如果我们要支持Opera9.5版本之前的话,那么我们需要浏览器检测技术来检测下;如下代码

EventUtil.addHandler(document, "mousewheel", function(event){
    event = EventUtil.getEvent(event);
    // var delta = (client.engine.opera && client.engine.opera < 9.5 ? -event.wheelDelta : event.wheelDelta);
       var delta = event.wheelDelta;
    alert(delta);
});
登入後複製

但是client.engine.opera 这句代码运行下会报错,因为目前还没有封装这个方法,所以等下一个博客我会研究代理检测封装下这个方法;所以先不考虑opera9.5,先注释掉这句代码;

但是FireFox支持一个为DOMMouseScroll的事件,也是在鼠标滚轮滚动时触发,与mousewheel事件一样,但是他的有关鼠标滚轮信息保存在detail属性中,当鼠标向前滚动时,这个属性值是-3的倍数,当鼠标滚轮向后滚动时,这个属性值是3的倍数;也可以给DOMMouseScroll事件使用在任何元素上,且这个事件会冒泡到window对象上,因此我们可以这样添加滚轮信息的代码如下:

EventUtil.addHandler(document, "DOMMouseScroll", function(event){
    event = EventUtil.getEvent(event);
    alert(event.detail);
});
登入後複製

我们现在可以给跨浏览器下的滚轮事件;代码如下:

function getWheelDelta (event) {
    if(event.wheelDelta) {
    // return (client.engine.opera && client.engine.opera < 9.5 ? -event.wheelDelta : event.wheelDelta);
         return  event.wheelDelta;
    }else {
        return -event.detail * 40
    }
}
登入後複製

getWheelDelta方法首先检测了事件对象是否包含了wheelDelta属性,如果包含则返回属性值,如果不包含,那么我们就当作是firefox浏览器,那么假设相应的值保存在detail属性中,有了上面的方法后,我们现在可以将相同的事件指定给mousewheel事件和DOMMouseScroll事件了;

EventUtil.addHandler(document, "DOMMouseScroll", handleMouseWheel);
EventUtil.addHandler(document, "mousewheel", handleMouseWheel);
function handleMouseWheel(event) {
    event = EventUtil.getEvent(event);
    var delta = EventUtil.getWheelDelta(event);
    alert(delta);
}
登入後複製

滚轮向上滚动是正数120,向下滚动是负数-120,所以根据是否大于0,可以判断是向下滚动还是向上滚动;

理解字符编码charCode

IE9+,firefox,chrome和safari的event对象都支持一个charCode属性,这个属性只有在发生keypress事件时才包含值,而且这个值是按下的那个键所代表字符的ASCLL编码,但是IE8及之前或者opera不支持这个属性,但是我们可以使用keyCode这个属性代替.在取得了字符编码之后,就可以使用String.fromCharCode()将其转换成实际的字符。

如下代码:

getCharCode: function(event) {
    if(typeof event.charCode == &#39;number&#39;) {
        return event.charCode;
    }else {
        return event.keyCode;
    }
}
登入後複製

我们现在可以给EventUtil添加事件了,如下代码:

var EventUtil = {
    addHandler: function(element,type,handler) {
        if(element.addEventListener) {
            element.addEventListener(type,handler,false);
        }else if(element.attachEvent) {
            element.attachEvent("on"+type,handler);
        }else {
            element["on" +type] = handler;
        }
    },
    removeHandler: function(element,type,handler){
        if(element.removeEventListener) {
            element.removeEventListener(type,handler,false);
        }else if(element.detachEvent) {
            element.detachEvent("on"+type,handler);
        }else {
            element["on" +type] = null;
        }
    },
    getEvent: function(event) {
        return event ? event : window.event;
    },
    getTarget: function(event) {
        return event.target || event.srcElement;
    },
    preventDefault: function(event){
        if(event.preventDefault) {
            event.preventDefault();
        }else {
            event.returnValue = false;
        }
    },
    stopPropagation: function(event) {
        if(event.stopPropagation) {
            event.stopPropagation();
        }else {
            event.cancelBubble = true;
        }
    },
    getRelatedTarget: function(event){
        if (event.relatedTarget){
            return event.relatedTarget;
        } else if (event.toElement){
            return event.toElement;
        } else if (event.fromElement){
            return event.fromElement;
        } else {
            return null;
        }
    },
    getWheelDelta: function(event) {
        if(event.wheelDelta) {
            return event.wheelDelta;
        }else {
            return -event.detail * 40
        }
    },
    getCharCode: function(event) {
        if(typeof event.charCode == &#39;number&#39;) {
            return event.charCode;
        }else {
            return event.keyCode;
        }
    }
};
登入後複製

我们现在可以做一个demo如下:

如下代码:
var inputp = document.getElementById("inputp");
EventUtil.addHandler(inputp,&#39;keypress&#39;,function(event){
    event = EventUtil.getEvent(event);
    var code = EventUtil.getCharCode(event);
    alert(EventUtil.getCharCode(event)); // 弹出字符编码
    alert(String.fromCharCode(code));  // 弹出字符
});
登入後複製

HTML5事件

1. contextmenu事件

contextmenu事件在windows操作系统下,我们是使用右键就可以自定义右键弹出菜单,但是我们使用右键的时候会有默认的菜单,因此我们需要使用阻止默认事件这个方法来阻止掉;此事件也是属于鼠标事件,因此此事件包含与光标位置中所有的属性,比如我们右键如下图所示:

HTML代码如下:
<p id="myp">Right click or Ctrl+click me to get a custom context menu.Click anywhere else to get the default context menu.
</p>
<ul id="myMenu" style="position:absolute;visibility:hidden;background-color:
    silver">
<li><a href="http://www.nczonline.net">Nicholas’ site</a></li>
<li><a href="http://www.wrox.com">Wrox site</a></li>
<li><a href="http://www.yahoo.com">Yahoo!</a></li>
</ul>
登入後複製
JS代码如下:
var p = document.getElementById("myp");
EventUtil.addHandler(p, "contextmenu", function(event){
    event = EventUtil.getEvent(event);
    EventUtil.preventDefault(event);
    var menu = document.getElementById("myMenu");
    menu.style.left = event.clientX + "px";
    menu.style.top = event.clientY + "px";
    menu.style.visibility = "visible";
});
EventUtil.addHandler(document, "click", function(event){
    document.getElementById("myMenu").style.visibility = "hidden";
});
登入後複製

如上,我们是通过右键的clientX和clientY来确定菜单的位置;当我点击文档document的时候 就隐藏该菜单;

浏览器支持有:IE,Firefox,Safari,chrome和Opera11+

beforeunload事件

此事件是给页面在卸载之前,给用户一个提示,是否需要卸载页面提示给用户,为了显示这个对话框,对IE和firefox而言,必须将event.returnValue的值设置为要显示给用户的字符串;但是对于safari和chrome而言,可以返回此字符串即可;

如下代码:

EventUtil.addHandler(window, "beforeunload",function(event){
    event = EventUtil.getEvent(event);
    var message = "I&#39;m really going to miss you if you go.";
    event.returnValue = message;
    return message;
});
登入後複製

当用户关闭游览器的时候,会弹出如下窗口给用户提示,如下:

点击离开此页按钮 即关闭窗口,点击留在此页按钮 即留在当前页面,但是当我按F5刷新页面的时候,同样会弹出窗口提示,如下:

浏览器支持:IE,firefox,chrome和safari都支持,但是Opera11及之前的版本不支持;

理解hashchange事件

HTML5中新增加了hashchange事件,以便在URL的参数列表(url中的#号后面的所有参数发生改变时通知开发人员),在Ajax应用中,开发人员经常使用url参数列表保存状态或导航信息;

我们必须把hashchange事件添加到window对象中,然后当url参数列表只要发生变化就会调用此事件,此事件对象event包含2个属性,oldURL和newURL,这两个属性分别保存着URL变化前后的完整URL;

支持的浏览器有:IE8+,firefox3.6+,safari5+,chrome和opera10.6+

在这些浏览器中,只有firefox3.6+,chrome和opera支持oldURL和newURL属性;

如下代码:

EventUtil.addHandler(window, "hashchange", function(event){
     alert("Old URL: " + event.oldURL + "\nNew URL: " + event.newURL);
});
登入後複製

当我第一次#号参数后面是aa,现在改成aaaa,就会触发此事件,如下所示:

有些浏览器并不支持oldURL和newURL,因此我们可以使用location.hash来保存当前的参数列表,如下代码:

EventUtil.addHandler(window, "hashchange", function(event){

      alert(location.hash);

});
登入後複製

当#号后面我改成bbb参数时候,会弹出如下所示:

可以使用如下代码来检测浏览器是否支持hashchange事件;

var isSupported = ("onhashchange" in window);
alert(isSupported);
登入後複製

如果IE8 是在IE7 文档模式下运行,即使功能无效它也会返回true。为解决这个问题,可以使用

以下这个更稳妥的检测方式:

var isSupported = ("onhashchange" in window) && (document.documentMode === undefined || document.documentMode > 7);
登入後複製

设备事件中的—orientationchange事件

苹果公司为移动safari添加的orientationchange事件是能让用户确定何时将设备由横向查看模式切换到纵向模式触发的事件;此属性中包含三个值,0表示肖像模式;90表示向左旋转的横向模式(主屏幕按钮在右侧),-90表示向右旋转的横向模式(主屏幕按钮在左侧),如下图所示:

只要用户改变了设备的查看模式,就会触发orientationchange事件,

使用IOS设备即可演示效果:代码如下:

EventUtil.addHandler(window, "load", function(event){
    var p = document.getElementById("myp");
    p.innerHTML = "Current orientation is " + window.orientation;
    EventUtil.addHandler(window, "orientationchange", function(event){
        p.innerHTML = "Current orientation is " + window.orientation;
    });
});
登入後複製

理解移动端的事件—触摸与手势事件

有以下几个触摸事件:

  1. touchstart: 當手指觸摸螢幕時觸發,即使是一個手指放在螢幕上也會觸發。

  2. touchmove:當手指在螢幕上滑動時連續觸發,這個事件發生期間,我們可以使用preventDefault()事件可以阻止滾動。

  3. touchend: 當手指從螢幕移開時觸發。

  4. touchcancel: 當系統停止追蹤觸控時觸發。

上面幾個事件都屬於冒泡事件,我們可以對此進行取消事件,每個觸碰的event物件都提供了滑鼠中常見的屬性;

bubbles, cancelable,view,clientX, clientY ,screenX, screenY,detail, altKey, shiftKey, ctrlKey, metaKey,

除了常見的DoM屬性外,觸控事件還包含下列三個用於追蹤觸控的屬性;

touches: 表示目前追蹤的觸控操作的Touch物件陣列;

targetTouches: 特定與事件目標的Touch物件陣列;

changeTouches: 表示自上次觸碰以來發生了什麼改變的Touch物件陣列;













### #######################################

以上是JavaScript事件使用指南的詳細介紹的詳細內容。更多資訊請關注PHP中文網其他相關文章!

相關標籤:
來源:php.cn
本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn
最新問題
熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板