jQuery 源码:属性

对元素属性的操作的实例方法。

jQuery.fn.extend({
	attr 			//调用工具的方法 attr
	removeAttr		//调用工具的方法 removeAttr
	prop 			//调用工具的方法 prop
	removeProp 		//调用工具的方法

	addClass
	removeClass
	toggleClass
	hasClass
	val

});

工具方法。
jQuery.extend({
	valHooks
	attr
	removeAttr
	attrHooks
	propFix
	prop
	propHooks
});


例子 : 

添加属性
	$('#div1').attr('title', 'dongdong');
	alert($('#div1').attr('title'));

设定属性
	$('#div1').prop('title', 'dangdang');
	alert($('#div1').prop('title'));


原生的js设定,
	var oDiv = document.getElementById('#div1');
	oDiv.setAttribute*('title', 'hello');
或者使用
	oDiv.title = 'hg';
	oDiv['title'] = 'hg';	传参可以用这个。


这里	attr-->setAttribute
	poro-->[''] 或者 . 

prop 和 attr 还是有很多不一样的地方。一般用attr用的多一些。

//	删除
	removeProp(attr);	//	无法删除id属性,其他可以
	removeAttr(attr);	//	可以干掉id这种,

jQuery 支持 $('input').attr('checked', true);	//选中当选框。
通过hooks处理的。解决了兼容,但是个人觉得还是不要这么写
还是用 $('input').attr('checked', 'checked');		//好一些,保持了语音话,和原生的习惯,
写js多了,看了很多框架,最大的感觉,就是原生,框架都是衍生品。都是美丽的房子,但是在美丽,也需要原生的砖头去盖。
能用原生,就用原生。只要有可能,就不用框架完成。

removeAttr(string);		//可以传入参数。比日 aa bb cc。那么就字符串分割,然后依次干掉。





源码:
	attr: function( elem, name, value ) {
		var hooks, ret,
			nType = elem.nodeType;

		// don't get/set attributes on text, comment and attribute nodes
		// 不存在,就返回, 节点类型 文本,注视,属性。这几个类型无法设定属性。只有元素节点可以。
		if ( !elem || nType === 3 || nType === 8 || nType === 2 ) {
			return;
		}

		// Fallback to prop when attributes are not supported
		//	有些元素不支持属性操作的时候,
		//  core_strundefined 是undefiend。
// 	$(document).attr();	document 和 window 是无法设定这种的。
//	但是,支持 obj['attr'] 这种类型的绑定。

		if ( typeof elem.getAttribute === core_strundefined ) {
			return jQuery.prop( elem, name, value );	//转换成prop代替attr
		}


		// All attributes are lowercase
		// Grab necessary hook if one is defined
		//	isXMLDoc 第一次见。是sizzle的方法,sizzle.isXML,判断当前节点是不是xml下的节点,是酒返回真
		if ( nType !== 1 || !jQuery.isXMLDoc( elem ) ) {
			name = name.toLowerCase();
			// attrHooks set 和 get 两种,兼容。返回值存在就兼容,不存在就兼容。
			hooks = jQuery.attrHooks[ name ] ||
				// jQuery.expr 是sizzle.selectors 
	//	"checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",
	// 就对上面这一串进行处理
				( jQuery.expr.match.bool.test( name ) ? boolHook : nodeHook );
		}

		if ( value !== undefined ) {

			if ( value === null ) {
				jQuery.removeAttr( elem, name );

			// hooks 存在, "set" 存在,并且不是undefined,就是做好了操作。
			} else if ( hooks && "set" in hooks && (ret = hooks.set( elem, value, name )) !== undefined ) {
				return ret;

			// 如果是undefined, 应该就执行这种设定。
			} else {
				elem.setAttribute( name, value + "" );
				return value;
			}

		} else if ( hooks && "get" in hooks && (ret = hooks.get( elem, name )) !== null ) {
			return ret;

		} else {
			//  jQuery.find 就是 sizzle的对象。
			// sizzle.attr()--->> getattr的方法。 在里面已经实现了,就直接复用就好了。
			ret = jQuery.find.attr( elem, name );

			// Non-existent attributes return null, we normalize to undefined
			return ret == null ?
				undefined :
				ret;
		}
	},


attrHooks: 钩子机制,让我想想到了windows,向总当时写了一个很牛的钩子。看的我很心动啊。哈哈
这里一看,就一个set,那么兼容就是就是指针对设定。
针对功能检测中的radio问题。 呃,具体细节不看了。。反正就是这个了。修复IE下面的bug

	attrHooks: {
		type: {
			set: function( elem, value ) {
				if ( !jQuery.support.radioValue && value === "radio" && jQuery.nodeName(elem, "input") ) {
					// Setting the type on a radio button after the value resets the value in IE6-9
					// Reset value to default in case type is set after value during creation
					var val = elem.value;
					elem.setAttribute( "type", value );
					if ( val ) {
						elem.value = val;
					}
					return value;
				}
			}
		}
	},


干掉属性。

	removeAttr: function( elem, value ) {
		var name, propName,
			i = 0,
			attrNames = value && value.match( core_rnotwhite );

		if ( attrNames && elem.nodeType === 1 ) {
			while ( (name = attrNames[i++]) ) {
				propName = jQuery.propFix[ name ] || name;

				// Boolean attributes get special treatment (#10870)
				//	jQuery.expr.match 这里有调用了sizzle中的方法。去判断是否有哪些属性。就进入,然后干掉[]的属性。
				if ( jQuery.expr.match.bool.test( name ) ) {
					// Set corresponding property to false
					elem[ propName ] = false;
				}

				elem.removeAttribute( name );	//原生的js
			}
		}
	},

先存入nodetype,
然后判断是不是xml。不是开始兼容模式,是的话,进用xml的模式,不考虑兼容性。
我都没用过xml在js里面,写其他语言用xml做个配置文件,做解析用。
其实xml理解为语义话的标签就好了。实际上我感觉是解析用的。用个txt文件也一样可以做,

	prop: function( elem, name, value ) {
		var ret, hooks, notxml,
			nType = elem.nodeType;

		// don't get/set properties on text, comment and attribute nodes
		if ( !elem || nType === 3 || nType === 8 || nType === 2 ) {
			return;
		}

		notxml = nType !== 1 || !jQuery.isXMLDoc( elem );

		if ( notxml ) {
			// Fix name and attach hooks
			name = jQuery.propFix[ name ] || name;
			hooks = jQuery.propHooks[ name ];
		}

		if ( value !== undefined ) {
			return hooks && "set" in hooks && (ret = hooks.set( elem, value, name )) !== undefined ?
				ret :
				( elem[ name ] = value );

		} else {
			return hooks && "get" in hooks && (ret = hooks.get( elem, name )) !== null ?
				ret :
				elem[ name ];
		}
	},


//	设定光标的切换。table建。
//	html有个属性,tabindex = 'number';	可以改变国标的切换的顺序。
//	rfocusable = /^(?:input|select|textarea|button)$/i;		
//  正则表示。看看事什么框。都是可以获取光标的节奏的节点。

	propHooks: {
		tabIndex: {
			get: function( elem ) {
				return elem.hasAttribute( "tabindex" ) || rfocusable.test( elem.nodeName ) || elem.href ?
					elem.tabIndex :
					-1;
			}
		}
	}
原文地址:https://www.cnblogs.com/hgonlywj/p/4870426.html