mass Framework data模块 v4
对v3进行改进,原来是用两个引用数组为元素节点提供UUID,另外两个数组提供缓存体。v4中删掉Data类,只有一个数组来为元素节点提供UUID,再用一个数组提供缓存体。缓存体之上有一个data对象属性,用于保存用户数据。相对于v3与jQuery2.0的新方案,它会在没有私有数据与用户数据时,会把这两个数组对应位置上的元素删掉,防止无限膨胀。
//==================================================
// 数据缓存模块
//==================================================
define("data", ["$lang"], function($) {
var owners = [],
caches = [];
/**
* 为目标对象指定一个缓存体
* @param {Any} owner
* @return {Object} 缓存体
* @api private
*/
function add(owner) {
var index = owners.push(owner);
return caches[index - 1] = {
data: {}
};
}
/**
* 为目标对象读写数据
* @param {Any} owner
* @param {Object|String} name ? 要处理的数据或数据包
* @param {Any} data ? 要写入的数据
* @param {Boolean} pvt ? 标识为内部数据
* @return {Any}
* @api private
*/
function innerData(owner, name, data, pvt) { //IE678不能为文本节点注释节点添加数据
var index = owners.indexOf(owner);
var table = index === -1 ? add(owner) : caches[index];
var getOne = typeof name === "string" //取得单个属性
var cache = table;
//私有数据都是直接放到table中,普通数据放到table.data中
if(!pvt) {
table = table.data;
}
if(name && typeof name == "object") {
$.mix(table, name); //写入一组属性
} else if(getOne && data !== void 0) {
table[name] = data; //写入单个属性
}
if(getOne) {
if(name in table) {
return table[name];
} else if(!pvt && owner && owner.nodeType == 1) {
//对于用HTML5 data-*属性保存的数据, 如<input id="test" data-full-name="Planet Earth"/>
//我们可以通过$("#test").data("full-name")或$("#test").data("fullName")访问到
return $.parseData(owner, name, cache);
}
} else {
return table;
}
}
/**
* 为目标对象移除数据
* @param {Any} owner
* @param {Any} name ? 要移除的数据
* @param {Boolean} pvt ? 标识为内部数据
* @return {Any}
* @api private
*/
function innerRemoveData(owner, name, pvt) {
var index = owners.indexOf(owner);
if(index > -1) {
var delOne = typeof name == "string",
table = caches[index],
cache = table,
clear = 1
if(delOne) {
if(!pvt) {
table = table.data;
}
if(table) {
delOne = table[name];
delete table[name];
}
for(var key in cache) {
if(key == "data") {
for(var i in cache.data) {
clear = 0;
break;
}
} else {
clear = 0;
break;
}
}
if(clear) {
owners.splice(index, 1);
caches.splice(index, 1);
}
}
return delOne; //返回被移除的数据
}
}
$.mix({
//判定是否关联了数据
hasData: function(owner) {
return owners.indexOf(owner) > -1;
},
// 读写用户数据
data: function(target, name, data) {
return innerData(target, name, data);
},
//读写内部数据
_data: function(target, name, data) {
return innerData(target, name, data, true);
},
//移除用户数据
removeData: function(target, name) {
return innerRemoveData(target, name);
},
//移除内部数据
_removeData: function(target, name) {
return innerRemoveData(target, name, true);
},
//将HTML5 data-*的属性转换为更丰富有用的数据类型,并保存起来
parseData: function(target, name, cache, value) {
var data, key = $.String.camelize(name),
_eval
if(cache && (key in cache)) return cache[key];
if(arguments.length != 4) {
var attr = "data-" + name.replace(/([A-Z])/g, "-$1").toLowerCase();
value = target.getAttribute(attr);
}
if(typeof value === "string") { //转换 /^(?:\{.*\}|null|false|true|NaN)$/
if(/^(?:\{.*\}|\[.*\]|null|false|true|NaN)$/.test(value) || +value + "" === value) {
_eval = true;
}
try {
data = _eval ? eval("0," + value) : value;
} catch(e) {
data = value;
}
if(cache) {
cache[key] = data;
}
}
return data;
},
//合并数据
mergeData: function(cur, src) {
if($.hasData(cur)) {
var oldData = $._data(src),
curData = $._data(cur),
events = oldData.events;
$.Object.merge(curData, oldData);
if(events) {
curData.events = [];
for(var i = 0, item; item = events[i++];) {
$.event.bind(cur, item);
}
}
}
}
});
return $
});
机器瞎学/数据掩埋/模式混淆/人工智障/深度遗忘/神经掉线/计算机幻觉/专注单身二十五年
浙公网安备 33010602011771号