dataUser存储用户的数据
dataPriv 存储JQ自己的数据
0 JQuery.fn.extend.data
data: function( key, value ) {
var i, name, data,
elem = this[ 0 ],
//返回NamedNodeMap对象,属性节点的集和,例如[class,data-name]
attrs = elem && elem.attributes;
// Gets all values
//不传key意味得到全部
if ( key === undefined ) {
if ( this.length ) {
//得到全部的数据
data = dataUser.get( elem );
if ( elem.nodeType === 1 && !dataPriv.get( elem, "hasDataAttrs" ) ) {
i = attrs.length;
while ( i-- ) {
// Support: IE 11 only
// The attrs elements can be null (#14894)
if ( attrs[ i ] ) {
name = attrs[ i ].name;
if ( name.indexOf( "data-" ) === 0 ) {
//将已-分隔的写法转换为驼峰写法,并去除私有前缀(ms-)
name = camelCase( name.slice( 5 ) );
//当data[ name ]为undefined且elem.getAttribute("data-"+name)有值时 会执行dataUser.set方法。
这时data值也会改变,因为data指向的内存地址没有改变,但内存里存储的数据发生了变化
dataAttr( elem, name, data[ name ] );
}
}
}
dataPriv.set( elem, "hasDataAttrs", true );
}
}
return data;
}
// Sets multiple values
//设置多个值{name:"123",age:12}
if ( typeof key === "object" ) {
//this是Jquery对象
return this.each( function() {
//this 是DOM对象
dataUser.set( this, key );
} );
}
return access( this, function( value ) {
var data;
// The calling jQuery object (element matches) is not empty
// (and therefore has an element appears at this[ 0 ]) and the
// `value` parameter was not undefined. An empty jQuery object
// will result in `undefined` for elem = this[ 0 ] which will
// throw an exception if an attempt to read a data cache is made.
if ( elem && value === undefined ) {
// Attempt to get data from the cache
// The key will always be camelCased in Data
data = dataUser.get( elem, key );
if ( data !== undefined ) {
return data;
}
// Attempt to "discover" the data in
// HTML5 custom data-* attrs
data = dataAttr( elem, key );
if ( data !== undefined ) {
return data;
}
// We tried really hard, but the data doesn't exist.
return;
}
// Set the data...
this.each( function() {
// We always store the camelCased key
dataUser.set( this, key, value );
} );
}, null, value, arguments.length > 1, null, true );
},
0.1 dataAttr
function dataAttr( elem, key, data ) {
var name;
// If nothing was found internally, try to fetch any
// data from the HTML5 data-* attribute
if ( data === undefined && elem.nodeType === 1 ) {
// rmultiDash = [A-Z]/g $&等同于是RegExp对象的静态属性lastMatch,是指匹配的片段,把驼峰写法转换为-分隔
name = "data-" + key.replace( rmultiDash, "-$&" ).toLowerCase();
data = elem.getAttribute( name );
if ( typeof data === "string" ) {
try {
//进行类型转换 比如"true"=>true
data = getData( data );
} catch ( e ) {}
// Make sure we set the data so it isn't changed later
//放入elem的dataUser中
dataUser.set( elem, key, data );
} else {
data = undefined;
}
}
return data;
}
0.2 getData
function getData( data ) {
if ( data === "true" ) {
return true;
}
if ( data === "false" ) {
return false;
}
if ( data === "null" ) {
return null;
}
// Only convert to a number if it doesn't change the string
//+data 将字符串数字("123")转换数字
if ( data === +data + "" ) {
return +data;
}
///^(?:\{[\w\W]*\}|\[[\w\W]*\])$/ ,简单的json验证 列入<p class="shadow" data-name="{"klo":123}"></p>
if ( rbrace.test( data ) ) {
return JSON.parse( data );
}
return data;
}
1 JQuery.fn.extend.removeData
removeData: function( key ) {
return this.each( function() {
dataUser.remove( this, key );
} );
}
网友评论