- 浏览: 520975 次
- 性别:
- 来自: 北京
博客专栏
-
jQuery技术内幕
浏览量:200705
最新评论
-
青春依旧:
学习html5哪里好?当然华清远见是首选!
[原创] jQuery源码分析-01总体架构 -
追梦1819:
[size=x-small][color=red][/colo ...
[原创] jQuery源码分析-04 选择器-Sizzle-设计思路 -
niuqiang2008:
学习学习
[原创] jQuery源码分析-04 选择器-Sizzle-工作原理 -
liuweihug:
jquery 解析正则表达式及常见的Regex规则和表达式 - ...
[原创] jQuery源码分析-02正则表达式-RegExp-常用正则表达式 -
liang8768:
mark!!!
[原创] jQuery源码分析-00前言开光
属性操作主要介绍prop、attr、val三个接口的实现,相对于其他的接口,这三个的源码实现复杂,更容易让人混淆,一不小心就回使用错误的接口或返回错误的值,因此重点分析。
9.1 .prop() vs .attr()
9.1.1 概述
1.6.1相对1.5.x最大的改进,莫过于对属性.attr()的重写了。在1.6.1中,将.attr()一分为二: .attr()、.prop(),这是一个令人困惑的变更,也是一个破坏性的升级,会直接影响到无数的网站和项目升级到1.6。
简单的说,.attr()是通过setAttribute、getAttribute实现,.prop()则通过Element[ name ]实现:
jQuery.attr |
setAttribute, getAttribute |
jQuery.removeAttr |
removeAttribute, removeAttributeNode(getAttributeNode ) |
jQuery.prop |
Element[ name ] |
jQuery.removeProp |
delete Element[ name ] |
事实上.attr()和.prop()的不同,是HTML属性(HTML attributes)和DOM属性(DOM properties)的不同。HTML属性解析的是HTML代码中的存在的属性,返回的总是字符串,而DOM属性解析的是DOM对象的属性,可能是字符串,也可能是一个对象,可能与HTML属性相同,也可能不同。
9.1.2 测试
看个例子,让我们对HTML属性和DOM属性的区别有个直观的概念:
HTML代码:
<a href="abc.html" class="csstest" style="font-size: 30px;">link</a> <input type="text" value="123"> <input type="checkbox" checked="checked"> |
JavaScript代码:
console.info( $('#a').attr('href') ); // abc.html console.info( $('#a').prop('href') ); // file:///H:/open/ws-nuysoft/com.jquery/jquery/abc.html
console.info( $('#a').attr('class') ); // csstest console.info( $('#a').prop('class') ); // csstest
console.info( document.getElementById('a').getAttribute('class') ); // csstest console.info( document.getElementById('a').className ); // csstest
console.info( $('#a').attr('style') ); // font-size: 30px; console.info( $('#a').prop('style') ); // CSSStyleDeclaration { 0="font-size", fontSize="30px", ...} console.info( document.getElementById('a').getAttribute('style') ); // font-size: 30px; console.info( document.getElementById('a').style ); // CSSStyleDeclaration { 0="font-size", fontSize="30px", ...}
console.info( $('#text').attr('value') ); // 123 console.info( $('#text').prop('value') ); // 123
console.info( $('#checkbox').attr('checked') ); // checked console.info( $('#checkbox').prop('checked') ); // true |
可以看到HTML属性和DOM属性在属性名、属性值上都诸多不同。
9.1.3 区别
不同之处总结如下:
属性名可能不同,尽管大部分的属性名还是相似或一致的
HTML属性值总是返回字符串,DOM属性值则可能是整型、字符串、对象,可以获取更多的内容
DOM属性总是返回当前的状态(值),而HTML属性(在大多数浏览)返回的初始化时的状态(值)
DOM属性只能返回固定属性名的值,而HTML属性则可以返回在HTML代码中自定义的属性名的值
相对于HTML属性的浏览器兼容问题,DOM属性名和属性值在浏览器之间的差异更小,并且DOM属性也有标准可依
9.1.4 建议
下边让我们回到.attr()和.prop(),经过以上测试和分析,可以得出对.attr()和.prop()的使用建议如下
优先使用.prop(),因为.prop()总是返回最新的状态(值)
只有涉及到自定义HTML属性时使用.attr(),或者可以说,忘掉.attr()吧
9.1.5 源码
jQuery.attr
// 设置或获取HTML属性 // http://stackoverflow.com/questions/5874652/prop-vs-attr attr: function( elem, name, value, pass ) { var nType = elem.nodeType;
// don't get/set attributes on text, comment and attribute nodes // 忽略文本、注释、属性节点 if ( !elem || nType === 3 || nType === 8 || nType === 2 ) { return undefined; } // 遇到与方法同名的属性,则执行方法 // 如果遇到的是扩展或需要修正的属性,则执行相应的方法 if ( pass && name in jQuery.attrFn ) { return jQuery( elem )[ name ]( value ); }
// Fallback to prop when attributes are not supported // 如果不支持getAttribute,则调用jQuery.prop // 求助于prop?prop是从attr中分化出来的,居然要求助于prop,看来attr要被放弃了 if ( !("getAttribute" in elem) ) { return jQuery.prop( elem, name, value ); }
var ret, hooks, notxml = nType !== 1 || !jQuery.isXMLDoc( elem );
// Normalize the name if needed // 格式化name(修正tabindex > tabIndex) name = notxml && jQuery.attrFix[ name ] || name; // 属性钩子:type tabIndex hooks = jQuery.attrHooks[ name ];
// 如果没有name对应的钩子 if ( !hooks ) { // Use boolHook for boolean attributes // 使用boolean钩子处理boolean属性 if ( rboolean.test( name ) && (typeof value === "boolean" || value === undefined || value.toLowerCase() === name.toLowerCase()) ) { // 使用 布尔钩子(静态方法对象):set get hooks = boolHook;
// Use formHook for forms and if the name contains certain characters // 使用表单钩子 } else if ( formHook && (jQuery.nodeName( elem, "form" ) || rinvalidChar.test( name )) ) { // 使用 表单钩子(静态方法对象):set get hooks = formHook; } }
// 如果value已定义,则设置或移除 // 设置 if ( value !== undefined ) { // typeof null === 'object' // true // typeof undefined === 'undefined' // true // null == undefined true // null === undefined false // value为null,则移除name属性 // 注意这里用的都是恒等号 if ( value === null ) { jQuery.removeAttr( elem, name ); return undefined;
} // 属性钩子、布尔钩子、表单钩子,如果有对应的钩子,则调用钩子的set方法 else if ( hooks && "set" in hooks && notxml && (ret = hooks.set( elem, value, name )) !== undefined ) { return ret;
} else { // 最后的最后,还是调用setAttribute,前边的各种钩子,都是修正属性 // 强制将value转换为字符串 elem.setAttribute( name, "" + value ); return value; } // 如果value是undefined,说明是取属性值,如果对应的钩子的有get方法,则调用钩子的get方法 } else if ( hooks && "get" in hooks && notxml ) { return hooks.get( elem, name );
} else { // 最后的最后:getAttribute ret = elem.getAttribute( name );
// Non-existent attributes return null, we normalize to undefined // 不存在的属性返回null,格式化为undefined return ret === null ? undefined : ret; } } |
jQuery.prop
// 设置或获取DOM属性 prop: function( elem, name, value ) { var nType = elem.nodeType;
// don't get/set properties on text, comment and attribute nodes // 忽略文本、注释、属性节点 if ( !elem || nType === 3 || nType === 8 || nType === 2 ) { return undefined; }
var ret, hooks, notxml = nType !== 1 || !jQuery.isXMLDoc( elem );
// Try to normalize/fix the name // 属性名name修正 name = notxml && jQuery.propFix[ name ] || name;
hooks = jQuery.propHooks[ name ]; // 设置 // 看着prop的实现是不是很眼熟?嗯,和attr的思路类似! if ( value !== undefined ) { // 如果钩子存在set方法,则调用钩子的set方法 if ( hooks && "set" in hooks && (ret = hooks.set( elem, value, name )) !== undefined ) { return ret;
} else { return (elem[ name ] = value); } // 读取 } else { if ( hooks && "get" in hooks && (ret = hooks.get( elem, name )) !== undefined ) { return ret;
} else { return elem[ name ]; } } } |
jQuery.fn.attr、jQuery.fn.prop
内部通过jQuery.access调用jQuery.attr、jQuery.prop实现
attr: function( name, value ) { return jQuery.access( this, name, value, true, jQuery.attr ); },
prop: function( name, value ) { return jQuery.access( this, name, value, true, jQuery.prop ); } |
jQuery.access
// Mutifunctional method to get and set values to a collection // The value/s can be optionally by executed if its a function // 多功能函数,读取或设置集合的属性值;值为函数时会被执行 // fn:jQuery.fn.css, jQuery.fn.attr, jQuery.fn.prop access: function( elems, key, value, exec, fn, pass ) { var length = elems.length;
// Setting many attributes // 如果有多个属性,则迭代 if ( typeof key === "object" ) { for ( var k in key ) { jQuery.access( elems, k, key[k], exec, fn, value ); } return elems; }
// Setting one attribute // 只设置一个属性 if ( value !== undefined ) { // Optionally, function values get executed if exec is true exec = !pass && exec && jQuery.isFunction(value); // 调用fn for ( var i = 0; i < length; i++ ) { fn( elems[i], key, exec ? value.call( elems[i], i, fn( elems[i], key ) ) : value, pass ); }
return elems; }
// Getting an attribute // 读取属性 return length ? fn( elems[0], key ) : undefined; } |
评论
有时间补吧,写了这么多,多看几遍有基础了,剩下的看起来就容易了
发表评论
-
[原创] jQuery源码分析-04 选择器-Sizzle-设计思路
2011-11-14 20:59 6848作者:nuysoft/高云 QQ:47214707 Em ... -
[原创] jQuery源码分析-04 选择器-Sizzle-工作原理
2011-11-13 23:45 7881作者:nuysoft/高云 QQ:47214707 EM ... -
[原创] jQuery源码分析-02正则表达式-RegExp-常用正则表达式
2011-10-27 01:29 46633作者:nuysoft/JS攻城师/ ... -
[原创] jQuery源码分析-jQuery中的循环技巧
2011-10-27 00:36 14546作者:nuysoft/JS攻城师/高云 QQ:47214707 ... -
[原创] jQuery源码分析-10事件处理-Event-DOM-ready
2011-10-20 01:20 10598作者:nuysoft/JS攻城师/ ... -
[原创] jQuery源码分析-Java工程师应该向jQuery学习的8点建议
2011-10-18 23:56 12245作者:nuysoft/高云 QQ:47214707 EM ... -
[原创] jQuery源码分析-10事件处理-Event-事件绑定与删除-bind/unbind+live/die+delegat/undelegate
2011-10-18 22:31 15664作者:nuysoft/高云 QQ:47214707 EM ... -
[原创] jQuery源码分析-10事件处理-Event-源码结构
2011-10-17 01:01 12118作者:nuysoft/高云 QQ:47214707 EMail ... -
[原创] jQuery源码分析-07数据缓存-Cache
2011-10-13 19:55 12129作者:nuysoft/高云 QQ:47214707 EMail ... -
[原创] jQuery源码分析-06浏览器测试-Support
2011-10-13 19:19 9898作者:nuysoft/高云 QQ:47214707 EMail ... -
[原创] jQuery源码分析系列目录(持续更新)
2011-10-12 12:30 29350作者:nuysoft/高云 QQ:47214707 E ... -
[原创] jQuery源码分析-10事件处理-Event-概述和基础知识
2011-10-12 00:16 12007作者:nuysoft/高云 Q ... -
[原创] jQuery源码分析-08队列 Queue
2011-10-10 23:48 10788作者:nuysoft/高云 Q ... -
[原创] jQuery源码分析-03构造jQuery对象-工具函数
2011-09-29 23:21 29778作者:nuysoft/高云 QQ:47214707 E ... -
[原创] jQuery源码分析-15AJAX-类型转换器
2011-09-29 02:25 7404作者:nuysoft/高云 QQ:47214707 EM ... -
[原创] jQuery源码分析-03构造jQuery对象-源码结构和核心函数
2011-09-28 02:20 52961作者:nuysoft/高云 QQ:47214707 EMail ... -
[原创] jQuery源码分析-如何做jQuery源码分析
2011-09-27 00:22 14995近期在ITEYE陆续写了几篇jQuery源码分析,乐在其 ... -
[原创] jQuery源码分析-17尺寸和大小 Dimensions & Offset
2011-09-25 22:05 7047边读边写,不正确的地方,还请各位告诉我,多多交流共同学习, ... -
[原创] jQuery源码分析-15AJAX-前置过滤器和请求分发器
2011-09-23 00:09 13275边读边写,不正确的 ... -
[原创] jQuery源码分析-00前言开光
2011-09-21 23:42 46999jQuery源码分析 - 前言 jQuery凭借简洁的语法和 ...
相关推荐
本文将对jQuery中用于处理元素尺寸和偏移的接口进行深入分析,帮助开发者理解各种接口的应用场景和具体用法。 ### Offset接口 Offset接口主要包括`.offset()`和`.offsetParent()`两个方法。 #### .offset() `....
源码分析可以帮助我们理解具体的实现细节,如如何定义书页的结构,如何编写CSS样式来实现翻页动画,以及如何使用JavaScript控制翻页逻辑。 解压密码为“www.0html.com”,这提示我们源码可能受版权保护,仅用于学习...
七、源码分析 6-妙味课堂原创JavaScript视频教程——运动课程(9课)课程资料中,你可能会看到不同类型的运动示例,如淡入淡出、滑动、旋转等。每种运动都包含了一个或多个关键帧,通过改变时间和空间坐标来实现。通过...
这篇博客"透明圆角化使用模板(半原创)"可能探讨了如何在特定环境中创建具有透明圆角的元素,可能涉及到CSS、JavaScript或者某种特定的开发工具。 首先,我们来了解一下CSS中的透明圆角化。CSS3引入了`border-radius...
Expression Language(EL)则是用于在JSP页面中获取和操作JavaBean属性的简洁语法。 4. **数据库连接管理**:项目会涉及数据库操作,如MySQL或Oracle,使用JDBC(Java Database Connectivity)进行连接。数据库连接...
描述中提到这不是原创,意味着这是一种已有的设计实践或代码实现,作者可能是分享了他找到的解决方案或者是基于某个现有实现进行了修改。通过博文链接(由于这是一个文本环境,我们无法直接访问链接,但通常博主会...
8. jQuery或类似的库:为了简化DOM操作,很多开发者会选择使用jQuery或其他类似的库,它们提供了丰富的功能和简洁的API。 9. ES6+新特性:现代JavaScript(ES6及以上版本)引入了许多新特性,如箭头函数、模板字符...
jQuery是一个JavaScript库,它简化了JavaScript的使用,提供了丰富的API,如DOM操作、事件处理、动画效果等,使得开发者能更高效地编写代码。 Bootstrap是由Twitter开发的前端框架,它包含了一系列预设的CSS样式和...