最近精简了JQuery,精简到33KB,一些功能肯定被K掉了。保留了常用的:
ready, attr, data, css, html, text, val, empty, append, siblings, wrap, trigger, bind, unbind, delegate, mouseenter, mouseleave, anim, stop, ajax, jsonp等等。
除了attr,data,css用了JQ的,并做了些改动,其他的基本都没在JQ的源码上精简,算个山寨货?。。。
功能肯定没JQ强大,但是文件大小从JQ1.6的80K到30K,用在一些不是特别复杂的应用上还是不错的。
语法也是用了链式操作,因为一些方法没参考JQ源码,所以有些语法和JQ不一样了。JQ的一些插件也不能直接用了,不过改改插件,基本上还是可以用的。
因为选择器没采用用sizzle,所以没法用一些高级的选择符,比如odd,even,nth-child,这些就需要另外写方法实现了。
odd,even的实现比较省事,取奇偶就可以了,i % 2的余数是0还是1就OK。
nth-child的实现费了一些力,不仅要匹配允许的选择符,还要返回符合规范的结果。
如果不知道CSS的nth-child选择符可以自己Search一下,偶就不介绍了。
一些例子:nth-child(2n+1), nth-child(2), nth-child(3n), nth-child(n+2),nth-child(-n+2)
代码如下:
function nthChild(nodeList, selector ) {
var ret = [],
reg = /(-?\d*)[n]*([+-]\d+)*/,
m = selector.match(reg);
if (selector === m[1]) { // nth-child:(2) - 纯数字,直接返回
return [nodeList[(parseInt(m[1])-1)]];
}
var filter = function(i){
++i; //nth从1开始, elem从0开始,elem的index要+1
if (m[2]) { // 类似:nth-child:(-2n-1) / nth-child(n+2)
if ('' === m[1]){ // nth-child(n+2)
m[1] = 1;
}else if ('-' === m[1]) { // nth-child(-n+2)
m[1] = -1;
}// else nth-child(-2n-1) / nth-child(2n+10)
}else { // nth-child:(2n)
m[2] = 0;
}
var n = (i-parseInt(m[2])) / parseInt(m[1]);
// 正整数返回true
return ( n === parseInt(n) && n >= 0) ? true : false;
}
each(nodeList, function(i){ //each 方法需要单独写
if (filter(i)) {
ret.push(this)
}
});
return ret;
}
实现nth-child的思路:
nth-child的公式为:nth-child(x*n+y);
n从0开始++,(x*n+y)要>0
x *n + y = i; // n,为自然数,从0开始; i为要取的第几个元素(正整数)
上面得到:n = (i-y) / x ; 整除,余0
那么,当i满足:(i-y) % x === 0 && (i-y) / x >= 0,就是符合条件的了
使用:
function each( obj, fn ) {
var i = 0, len = obj.length, val;
for (; i < len; i++) {
val = fn.call(obj[i], i, obj[i]);
if ( val === false ) break;
}
}
var list = nthChild(document.getElementsByTagName("li"), '2n+1'); //奇数行
//使用FF/CM/OP/IE9等支持nth-child选择符的浏览器,得到NodeList的结果,可以用来与nthChild的结果比较
//比如:document.querySelectorAll('li:nth-child(2n+1)')
each(list, function(){ this.className = 'selected'; }); //给奇数行设置class=selected