• Javascript公共脚本库系列(三): 格式化事件对象/事件对象详解


    本文转自:http://www.cnblogs.com/zhangziqiu/archive/2009/02/13/javascriptLibrary-3.html

    一.摘要

    本系列文章是为了抽象通用的,跨浏览器的脚本方法.

    本篇文章为脚本库添加跨浏览器的获取事件对象的方法, 重点是讲解javascript中的事件对象的原理.希望通过分享微薄的知识告诉大家如何进行"加法运算"而不是死记硬背"1+1=2".

    二.实现效果

    本次添加的两个函数用于获取事件对象, 事件对象中包含很多的信息,比如鼠标的坐标, 从而实现自己想要的功能.

    实例一可以在屏幕上捕获鼠标按键代码和键盘按键代码:

    image  image

    实例二实现重写鼠标右键菜单:

    image

    三.事件对象简介

    事件源和事件对象就相当于C#中事件函数的sender和EventArgs参数.

    事件源是产生事件的元素本身, 而事件对象则带有事件相关的信息.事件对象只有在发生事件时才被创建, 并且只能在事件中访问.当事件关联的处理函数执行完毕后, 事件对象就被销毁.

    事件对象带有很多有用的信息,比如屏幕坐标,按键代码,是否冒泡等.但是可惜的是FireFox支持的DOM事件模型和IE的事件模型并不完全一致,获取事件对象的方式也不相同.在IE中通过window.event使用当前的事件对象,而DOM则规定事件对象要作为唯一参数传递给事件处理函数.

    四.实现代码

    我们的ScriptHelper类又要添加两个新方法了:

    /*  获取事件对象
        使用举例: <div onclick=" var oEvent=ScriptHelper.getEvent();"></div>
        注意事项: 只能在事件中使用. 比如onclick中. 不能在自定义方法中使用.   
    */
    scriptHelper.prototype.getEvent = function()
    {
        if( window.event )
        {
            return window.event;
        }
        else
        {        
            return this.getEvent.caller.arguments[0];
        }
    } 
    
    /*  取消冒泡事件
        使用举例: <div onclick=" var oEvent=ScriptHelper.cancelBubble();"></div>
        注意事项: 只能在事件中使用. 比如onclick中.  不能在自定义方法中使用.
    */
    scriptHelper.prototype.cancelBubble = function()
    {
        if( window.event )
        {
            window.event.cancelBubble = true;
        }
        else
        {        
            return this.cancelBubble.caller.arguments[0].cancelBubble = true;
        }
    } 

    这两个方法十分简单.getEvent 用于获取事件对象. cancelBubble和getEvent类似,但不是返回事件对象, 而是取消事件对象的冒泡事件.

    也许有人会觉得getEvent 和cancelBubble中有重复代码,认为可以在cancelBubble中调用getEvent 获取事件对象,然后再取消冒泡事件. 然而不能这么做, 这两个事件都只能用在事件处理函数中, cancelBubble已经是一个自定义方法, 不能在自定义方法中使用getEvent .原因是在DOM事件中,事件对象是事件的唯一参数.对于FireFox我们是通过caller.arguments[0]来捕获事件对象,caller表示此方法的调用者, 必须为事件. 下文中还有对于事件参数的讲解.

    五.应用实例

    实例一 在屏幕上捕获鼠标按键代码和键盘按键代码

    实例代码:

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <html xmlns="http://www.w3.org/1999/xhtml" >
    <head>
        <title>ScriptHelper 类测试 -- 事件对象实例 -- 获取键盘鼠标按键代码</title>
        <script src="https://files.cnblogs.com/zhangziqiu/ScriptHelper.js" type="text/javascript"></script>
        <style type="text/css">
            .cursorHand { cursor:pointer;}        
        </style>
    </head>
    <body >
        <script type="text/javascript">
            function getKeyCode()
            {
                var oEvent = ScriptHelper.getEvent();
                alert( "KeyCode:" + oEvent.keyCode);
            }
            
            function getMouseButtonCode()
            {
                var oEvent = ScriptHelper.getEvent();
                alert( "Mouse Button Code:" + oEvent.button);
            }
            
            ScriptHelper.addEventListener( document, "keydown", getKeyCode );
            ScriptHelper.addEventListener( document, "mousedown", getMouseButtonCode );  
        </script>   
    
    </body>
    </html>

    实例说明:

    本实例中使用了ScriptHelper.getEvent方法获取事件对象,并且获取了事件对象中的键盘代码和鼠标按键代码.注意实例中是使用ScriptHelper.addEventListener将getKeyCode和getMouseButtonCode添加到事件上.此时getKeyCode函数等同于onkeydown事件, 所以在getKeyCode函数中调用ScriptHelper.getEvent就等同于在onkeydown事件中调用.

    但是注意不能这么写:

    <body onkeydown="getKeyCode();">

    因为上面的代码等同于:

    body.onkeydown = function()
    {
         getKeyCode();
    }
     

    实例二  重写鼠标右键菜单

    实例代码:

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <html xmlns="http://www.w3.org/1999/xhtml" >
    <head>
        <title>ScriptHelper 类测试 -- 事件对象实例 -- 重写鼠标右键菜单</title>
        <script src="https://files.cnblogs.com/zhangziqiu/ScriptHelper.js" type="text/javascript"></script>
        <style type="text/css">
            .cursorHand { cursor:pointer;}   
            .menu 
            {
                background:#FFFFFF none repeat scroll 0 0;
                border:1px solid #ACA899;
                color:#000000;
                font-size:12px;
                position:absolute;
                display:none;
            }
            .menu ul 
            {
                list-style-image:none;
                list-style-position:outside;
                list-style-type:none;
                margin:3px;
                padding:3px;
            }
            .menu ul li
            {
                cursor:pointer;
                margin-bottom:5px;
            }         
        </style>
    </head>
    <body style="position:relative;">
        <script type="text/javascript">   
        </script>   
        
        <div>测试文字: 欢迎访问 http://zhangziqiu.cnblogs.com 一起学习,一起进步.</div>
    
    
        <div id="mouseRightButtonMenu" class="menu" onclick="ScriptHelper.cancelBubble();">
            <ul>
                <li id="divMouseMenu1">查看选中内容</li>
                <li><a href="http://zhangziqiu.cnblogs.com" target="_blank">返回博客首页</a></li>
            </ul>
        </div>
        <script type="text/javascript">
        //显示鼠标右键菜单
        function showMouseRightButtonMenu()
        {
            ScriptHelper.cancelBubble();
            var oEvent = ScriptHelper.getEvent();
            var menu = document.getElementById('mouseRightButtonMenu');
            if( oEvent.button == 2)
            {
                menu.style.display="block";
                menu.style.left = oEvent.clientX + "px";
                menu.style.top = oEvent.clientY + "px";                
            }
        }
        
        //关闭鼠标右键菜单
        function closeMouseRightButtonMenu()
        {
            var oEvent = ScriptHelper.getEvent();
            if( oEvent.button == 0 || oEvent.button == 1)
            {
                ScriptHelper.closeDivCommon('mouseRightButtonMenu');
            }
        }
        
        //空函数,用于取消FireFox默认的鼠标右键菜单
        function blankMethod()
        {  
            return false;
        } 
        
        //添加鼠标右键菜单的相关事件
        document.onclick= blankMethod;
        document.ondblclick= blankMethod;
        ScriptHelper.addEventListener( document, "mousedown", showMouseRightButtonMenu );
        ScriptHelper.addEventListener( document, "click", closeMouseRightButtonMenu );
        ScriptHelper.addEventListener( document, "contextmenu", blankMethod );  
            
        /* 菜单项相关函数 */        
        function mouseMenu1()
        {
            ScriptHelper.closeDivCommon("mouseRightButtonMenu");
            
            var selectText = "未选中任何内容";
            if( window.getSelection ) 
            {
                selectText = window.getSelection().toString();
            } 
            else if(document.selection && document.selection.createRange) 
            {
                selectText = document.selection.createRange().text;
            }
            if( selectText!=null && selectText!="" )
            {
                alert(selectText);
            } 
        }        
        var divMouseMenu1 = document.getElementById("divMouseMenu1");
        if( divMouseMenu1!=null)
        {
            ScriptHelper.addEventListener( divMouseMenu1, "mousedown", mouseMenu1 );
        }
        </script>
    </body>
    </html>

    实例说明:

    此实例的代码很多. 原理就是通过事件对象判断是否单击了右键, 如果是则弹出我们自己的鼠标右键菜单.

    六.使用技巧

    • IE中鼠标左键代码是1,FF是0. IE和FF鼠标右键代码都是2(oEvent.button)
    • 取消默认的鼠标菜单, ie中重写document.oncontentmenu方法, ff中要重写document.click方法.
    • 鼠标事件对象中的clientX和clientY可以获取鼠标的坐标
    • ie中可以直接设置div的style.top和style.left属性为数字(比如100).ff中必须在数字后加"px"(比如100px)
    • 不同的事件类型有顺序: (1)mousedown (2)mouseup (3)click

    七.事件对象详解

    获取

    IE中,事件对象是window对象的一个属性.事件处理函数必须这样访问事件对象:

            obj.onclick=function()
            {
                var oEvent = window.event;
            }

    在DOM标准中,事件对象必须作为唯一参数传给事件处理函数:

            obj.onclick=function()
            {
                var oEvent = arguments[0];
            }

    除了使用argument[0]访问此参数, 我们也可以指定参数名称,上面的代码等同于:

            obj.onclick=function(oEvent)
            {
                
            }

    目前兼容DOM的浏览器有Firefox,Safari,Opera,IE7等.

    通用的事件对象数据

    在IE和DOM中,事件对象带有的数据并不完全相同.但是我认为只有完全的那些数据才是值得我们使用的.下面是一些可以在IE和DOM中使用的事件对象数据.其中假设oEvent是事件对象.

    1.获取时间类型

    var eventType = oEvent.type

    2.获取键盘按键代码:

    需要在keydown和keyup事件中使用.

    var eventKeyCode = oEvent.keyCode

    3.检测Shift,Alt,Ctrl键是否被按下:

            var isShift = oEvent.shiftKey;
            var isAlt = oEvent.altKey;
            var isCtrl = oEvent.ctrlKey;

    返回的是boolean值.

    4.获取鼠标指针坐标

            var x = oEvent.clientX;
            var y = oEvent.clientY;

    八.总结

    网上复杂绚丽的脚本特效很多, 但是再复杂的特效也离不开基础的事件和事件对象.一旦明白了原理, 相信大家的创造力可以做出来很多通用的优秀的脚本控件.比如下面这个网址中就有很多的特效:http://www.scriptlover.com/controls/context/ ,感谢"痴情客"在本系列的第二篇文章中提供了上面的网址.

    作者:张子秋
    出处:http://www.cnblogs.com/zhangziqiu/
    本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
  • 相关阅读:
    Graph 学习
    忘记 mysql 8.0 root 密码 怎么修改
    HTML字符实体(关于&nbsp;&gt;&lt;等)
    Sqlserver 中系统表sysobjects、syscolumns以及函数object_id
    SQL Server创建索引(转)
    改善SQL语句(转)
    (转)SqlServer索引及优化详解(1)
    标签点击不返回顶部和不刷新页面方法
    c#模拟js escape方法
    获取枚举描述信息
  • 原文地址:https://www.cnblogs.com/weekend001/p/1564760.html
Copyright © 2020-2023  润新知