javascript - 工作笔记 (事件四)

时间:2022-09-14 09:03:09

  在javascript - 工作笔记 (事件绑定二)篇中,我将事件的方法做了简单的包装,

 JavaScript Code 
1
2
3
4
5
 
yx.bind(item, "click", function (e) {
        //console.log("Div Click 1 !");
        alert("Div Click 1 !");
        e.stopPropagation();
    });

  但是这样用起来有些不顺手,添加方法还要加个标签元素对象,能不能去掉第一个参数呢,答案是肯定的。

我们只需要将DOM元素对象转换成Yx对象,就可以了。但是要如何将dom变成Yx对象呢,如下:

 JavaScript Code 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
 
var Yx = function (ele) {//dom元素对象
    var self = this;
    if (
    (ele instanceof Array) ||
    (NodeList || (ele instanceof NodeList))) {
        ; i < ele.length; i++) {
            self[i] = ele[i];
        }
        self.length = ele.length;
    } else {
        self[] = ele;
        self.length = ;
    }
    return self;
}

  我们将dom元素对象挂在Yx对象的下面,像数组一样,使用下标获取,设置值,同时还保留了DOM节点自带的方法,属性。这时,我们使用的时候如下:

 JavaScript Code 
1
2
3
 
var item = document.getElementById("test");//获取dom对象
var yxItem = new Yx(item);//新建Yx对象
yxItem.bind( "click", function (e) { ... });//绑定事件

  但,这样写也有点不爽,每次还要new一下,能省掉new吗,当然可以。

 JavaScript Code 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
 
Yx.prototype.init = function(ele){
    var self = this;
    if(
    (ele instanceof Array) ||
    (NodeList || (ele instanceof NodeList))){
        ;i<ele.length;i++){
            self[i] = ele[i];
        }
        self.length = ele.length;
    }else{
        self[] = ele;
        self.length = ;
    }
    return self;
}

  我们新建一个方法为init用来新建Yx对象使用,同时,我们在构造方法中,这样写:

 JavaScript Code 
1
2
3
4
5
6
7
8
 
var Yx = function(ele){

Yx.fn = Yx.prototype;//将Yx原型链赋值给Yx.fn
    Yx.fn.init.prototype = Yx.fn;//实际是将Yx的原型链赋值给Yx.fn.init,这样Yx.fn.init就具有与Yx一样的原型链,
    
    return new Yx.fn.init(ele);//在这里实例化的是Yx.fn对象,但是它具有有Yx一样的原型链,
    //new 出来的对象与Yx对象是相同的
}

//这种方法因为在使用的时候去掉了new,被称为无new的构造方法,在源码中,我介绍了两种无new方法,写法不同,其实原理一样。

这时候我们使用方法如下:

 JavaScript Code 
1
2
3
4
5
6
7
8
9
 
var item = document.getElementById("test");  
var yxItem = yx(item);//直接调用yx方法,该方法中new Yx.fn对象
yxItem.bind("click",function(e){
    console.log("Div Click 1 !");
    e.stopPropagation();
});

window.$ = window.yx = Yx;//当然得有这么一句话才能直接使用yx(...)方法了,

完整代码如下:

 JavaScript Code 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
 
(function (window) {

var Yx = function (ele) {

//第一种无new实现方法
        var a = Yx.prototype; //将Yx.prototype存入a变量中,这样a变量中就含有了init这个方法,应该叫做对象
        //在javascript中任何事物都是对象,函数也是对象,xxx()是执行函数,new xxx()则是新建对象了,
        a.init.prototype = a; //将a(即:Yx.prototype原形链赋值给a.init对象的原形链,使这两个对象具有相同的方法,属性)
        return new a.init(ele); //新建一个a.init对象,该对象与new Yx(else)的对象具有相同的方法,属性

//第二种无new实现方法

//Yx.fn = Yx.prototype;
        //Yx.fn.init.prototype = Yx.fn;
        //return new Yx.fn.init(ele);
    }
    Yx.evGuid = ;
    window.NodeList = function () { } || window.NodeList;//IE下午NodeList对象
    //初始化
    Yx.prototype.init = function (ele) {
        var self = this;
        if (
    (ele instanceof Array) ||
    (NodeList && (ele instanceof NodeList))) {
            ; i < ele.length; i++) {
                self[i] = ele[i];
            }
            self.length = ele.length;
        } else {
            self[] = ele;
            self.length = ;
        }
        return self;
    }
    Yx.prototype.bind = function (evName, evFunc) {
        var self = this;
        ; i < self.length; i++) {
            self.bindEv(self[i], evName, evFunc);
        }
    }
    Yx.prototype.unbind = function (evName, evFunc) {
        var self = this;
        ; i < self.length; i++) {
            self.unbindEv(self[i], evName, evFunc);
        }
    }
    //绑定事件
    Yx.prototype.bindEv = function (ele, evName, evFunc) {
        if (!evFunc.$$guid) evFunc.$$guid = Yx.evGuid++; //为新添加的事件添加标识
        if (!ele.events) ele.events = {}; //为元素添加事件集合
        evName = evName;
        if (!ele.events[evName]) {
            ele.events[evName] = {};
        }
        if (ele.events[evName][evFunc.$$guid] == undefined)
            ele.events[evName][evFunc.$$guid] = {};
        ele.events[evName][evFunc.$$guid] = evFunc;
        ele["on" + evName] = eventManager; //事件统一处理
    }
    //解绑事件
    Yx.prototype.unbindEv = function (ele, evName, evFunc) {
        if (ele.events && ele.events[evName]) {
            delete ele.events[evName][evFunc.$$guid];
        }
    }
    //事件管理
    function eventManager(e) {
        var self = this; //当前对象
        var e = e || window.event; //event对象
        if (!e.stopPropagation) {//IE下的阻止默认行为,事件冒泡
            e.preventDefault = function () { this.returnValue = false; }
            e.stopPropagation = function () { this.cancelBubble = true; }
        }
        var evFuncs = self.events[e.type]; //获取当前对象,指定的事件名称事件数组
        for (var key in evFuncs) {
            evFuncs[key](e, self);
        }
    }
    window.$ = window.yx = Yx;//将Yx方法给两个别名
})(window);

var test = document.getElementById("test");
var testItem = yx(test);

testItem.bind("click", function (e) {
    //console.log("Div Click 1 !");
    alert("Div Click 1 !");
    e.stopPropagation();
});

var funcTest1 = function (e) {
    //console.log("Div Click 2 !");
    alert("Div Click 2 !");
};

testItem.bind("click", funcTest1);

var pArr = document.getElementsByTagName("p");
var pArrItem = $(pArr);

pArrItem.bind("click", function (e, item) {
    //console.log(item.innerHTML);
    alert(item.innerHTML);
    e.preventDefault();
});

var link = document.getElementById("a_link");
var linkItem = $(link);
linkItem.bind("click", function (e, item) {
    //console.log(item.innerHTML);
    alert(item.innerHTML);
    e.preventDefault();
});

  第一种无new方法与第二种无new方法原理一样,只是第一种方法看的明白些,第二种看起来NB一些,哈哈!

  Demo请点这里

javascript - 工作笔记 (事件四)的更多相关文章

  1. How Javascript works &lpar;Javascript工作原理&rpar; &lpar;十四&rpar; 解析,语法抽象树及最小化解析时间的 5 条小技巧

    个人总结:读完这篇文章需要15分钟,文章介绍了抽象语法树与js引擎解析这些语法树的过程,提到了懒解析——即转换为AST的过程中不直接进入函数体解析,当这个函数体需要执行的时候才进行相应转换.(因为有的 ...

  2. javascript - 工作笔记 (事件绑定)

    背景: 目前所做的项目,只能使用的是原生的javascript.对于javascript的事件绑定想必大家都懂得语法: 1,在标签中使用属性调用方法:<div onclick="AAA ...

  3. javascript - 工作笔记 (事件绑定二)

    在上篇中的事件绑定方法,相信大家都看到过了. 不过这里有点小小的问题,这些方法,变量都是全局的,难免会与其他的库或者方法发生冲突而被覆盖,因此,我在这里做了小小的封装,如下:  JavaScript ...

  4. javascript - 工作笔记 (事件三)

    有关定义就不多说了,事件分两种 一,冒泡型事件 这是IE浏览器中事件模型的实现,顾名思义,就像水中的泡一样,自底而上,其经过的父元素都会触发对应的事件. 即:触发元素的父元素先于触发元素触发,看dem ...

  5. JavaScript学习笔记——事件

    javascript事件基础和事件绑定 一.事件驱动 1.事件 javascript侦测到的用户的操作或是页面的一些行为(怎么发生的) 2.事件源 引发事件的元素.(发生在谁的身上)3.事件处理程序 ...

  6. javascript学习笔记(四):事件处理函数和动态创建html标记。

    1 HTML的事件属性  全局事件属性:HTML 4 增加了使事件在浏览器中触发动作的能力,比如当用户点击元素时启动 JavaScript. a. Window 事件属性,针对 window 对象触发 ...

  7. JavaScript基础笔记(四) JS式面向对象

    JS式面向对象 一.理解对象 一)属性类型 ECMA-262 第 5 版在定义只有内部才用的特性(attribute)时,描述了属性(property)的各种特征. ECMA-262 定义这些特性是为 ...

  8. 8&period; JavaScript学习笔记——事件

    8. 事件 8.1 事件基础 /// 事件就是用户或浏览器自身执行的某种动作.诸如 click.load 和 mouseover,都是事件的名字.而响应某个事件的函数就叫做事件处理程序(或事件侦听器) ...

  9. iOS工作笔记&lpar;十四&rpar;

    1.scrollview的frame指的是其可视范围,contentSize指的是其滚动范围,分别是在水平方向和竖直方向上的 所以要让scrollview在水平方向不能滚动,那么需要如下设置 _scr ...

随机推荐

  1. 《BI那点儿事》数据流转换——逆透视转换

    逆透视转换将来自单个记录中多个列的值扩展为单个列中具有同样值的多个记录,使得非规范的数据集成为较规范的版本.例如,每个客户在列出客户名的数据集中各占一行,在该行的各列中显示购买的产品和数量.逆透视转换 ...

  2. 【GoLang】GoLang GOPATH 工程管理 最佳实践

    参考资料: MAC下 Intellij IDEA GO语言插件安装及简单案例:http://blog.csdn.net/fenglailea/article/details/53054502 关于wi ...

  3. 推荐几个sql server牛人的博客

    Aaron Bertrand http://sqlblog.com/blogs/aaron_bertrand/ Brent Ozar www.brentozar.com/ Buck Woody htt ...

  4. 分享9款很有创意的HTML5动画

    1.HTML5 SVG Loading 动画加载特效 这是一款基于HTML5/CSS3和SVG的Loading加载动画特效,一共有4种不同的动画效果.每一组Loading动画都非常可爱,他们都非常欢快 ...

  5. C&num;--Session用完如何清除

    Session.Abandon();//清除全部Session//清除某个SessionSession["UserName"] = null;Session.Remove(&quo ...

  6. Delphi反汇编内部字符串处理函数不完全列表

    Delphi反汇编内部字符串处理函数/过程不完全列表 名称 参数 返回值 作用 等价形式 / 备注 _PStrCat EAX :目标字符串 EDX :源字符串 EAX 连接两个 Pascal 字符串 ...

  7. label 和 legend标签的用法

    label 和 legend标签的用法 label标准用法: 一般浏览器都支持 一般而言,label标签位于表单元素的前面或者后面,为控件提供说明文字 <label for="user ...

  8. 取URL得值

    有这样一个URL:http://item.taobao.com/item.htm?a=1&b=2&c=&d=xxx&e,请写一段JS程序提取URL中的各个GET参数(参 ...

  9. 关于background-size 的一点小坑

    目前在做一个网页,要求使用一个图片作为背景,必须要全屏目填充,于是我想,这不是很简单的事情么: 有两种实现方法:首先设置添加一个div(或者body),把div(或者body)元素的宽和高都设置成10 ...

  10. 最小化webpack项目

    先把代码贴出来,以后慢慢加说明 参考资料:入门 Webpack,看这篇就够了 / webpack 搭建自动打开,刷新浏览器 一.功能代码1.index.html <!DOCTYPE html&g ...