Refactor jQuery.data a bit to reduce property lookups
[jquery.git] / src / data.js
1 var expando = "jQuery" + now(), uuid = 0, windowData = {};\r
2 \r
3 jQuery.extend({\r
4         cache: {},\r
5 \r
6         data: function( elem, name, data ) {\r
7                 elem = elem == window ?\r
8                         windowData :\r
9                         elem;\r
10 \r
11                 var id = elem[ expando ], cache = jQuery.cache;\r
12 \r
13                 // Compute a unique ID for the element\r
14                 if(!id) id = elem[ expando ] = ++uuid;\r
15 \r
16                 // Only generate the data cache if we're\r
17                 // trying to access or manipulate it\r
18                 if ( name && !cache[ id ] )\r
19                         cache[ id ] = {};\r
20 \r
21                 var thisCache = cache[ id ];\r
22 \r
23                 // Prevent overriding the named cache with undefined values\r
24                 if ( data !== undefined ) thisCache[ name ] = data;\r
25 \r
26                 if(name === true) return thisCache\r
27                 else if(name) return thisCache[name]\r
28                 else return id\r
29         },\r
30 \r
31         removeData: function( elem, name ) {\r
32                 elem = elem == window ?\r
33                         windowData :\r
34                         elem;\r
35 \r
36                 var id = elem[ expando ], cache = jQuery.cache, thisCache = cache[ id ];\r
37 \r
38                 // If we want to remove a specific section of the element's data\r
39                 if ( name ) {\r
40                         if ( thisCache ) {\r
41                                 // Remove the section of cache data\r
42                                 delete thisCache[ name ];\r
43 \r
44                                 // If we've removed all the data, remove the element's cache\r
45                                 if( jQuery.isEmptyObject(thisCache) )\r
46                                         jQuery.removeData( elem );\r
47                         }\r
48 \r
49                 // Otherwise, we want to remove all of the element's data\r
50                 } else {\r
51                         // Clean up the element expando\r
52                         try {\r
53                                 delete elem[ expando ];\r
54                         } catch(e){\r
55                                 // IE has trouble directly removing the expando\r
56                                 // but it's ok with using removeAttribute\r
57                                 if ( elem.removeAttribute )\r
58                                         elem.removeAttribute( expando );\r
59                         }\r
60 \r
61                         // Completely remove the data cache\r
62                         delete cache[ id ];\r
63                 }\r
64         },\r
65         queue: function( elem, type, data ) {\r
66                 if ( elem ){\r
67 \r
68                         type = (type || "fx") + "queue";\r
69 \r
70                         var q = jQuery.data( elem, type );\r
71 \r
72                         if ( !q || jQuery.isArray(data) )\r
73                                 q = jQuery.data( elem, type, jQuery.makeArray(data) );\r
74                         else if( data )\r
75                                 q.push( data );\r
76 \r
77                 }\r
78                 return q;\r
79         },\r
80 \r
81         dequeue: function( elem, type ){\r
82                 var queue = jQuery.queue( elem, type ),\r
83                         fn = queue.shift();\r
84 \r
85                 if( !type || type === "fx" )\r
86                         fn = queue[0];\r
87 \r
88                 if( fn !== undefined )\r
89                         fn.call(elem, function() { jQuery(elem).dequeue(type); });\r
90         }\r
91 });\r
92 \r
93 jQuery.fn.extend({\r
94         data: function( key, value ){\r
95                 if(typeof key === "undefined" && this.length) return jQuery.data(this[0], true);\r
96 \r
97                 var parts = key.split(".");\r
98                 parts[1] = parts[1] ? "." + parts[1] : "";\r
99 \r
100                 if ( value === undefined ) {\r
101                         var data = this.triggerHandler("getData" + parts[1] + "!", [parts[0]]);\r
102 \r
103                         if ( data === undefined && this.length )\r
104                                 data = jQuery.data( this[0], key );\r
105 \r
106                         return data === undefined && parts[1] ?\r
107                                 this.data( parts[0] ) :\r
108                                 data;\r
109                 } else\r
110                         return this.trigger("setData" + parts[1] + "!", [parts[0], value]).each(function(){\r
111                                 jQuery.data( this, key, value );\r
112                         });\r
113         },\r
114 \r
115         removeData: function( key ){\r
116                 return this.each(function(){\r
117                         jQuery.removeData( this, key );\r
118                 });\r
119         },\r
120         queue: function(type, data){\r
121                 if ( typeof type !== "string" ) {\r
122                         data = type;\r
123                         type = "fx";\r
124                 }\r
125 \r
126                 if ( data === undefined )\r
127                         return jQuery.queue( this[0], type );\r
128 \r
129                 return this.each(function(i, elem){\r
130                         var queue = jQuery.queue( this, type, data );\r
131 \r
132                         if( type == "fx" && queue.length == 1 )\r
133                                 queue[0].call(this, function() { jQuery(elem).dequeue(type); });\r
134                 });\r
135         },\r
136         dequeue: function(type){\r
137                 return this.each(function(){\r
138                         jQuery.dequeue( this, type );\r
139                 });\r
140         },\r
141         clearQueue: function(type){\r
142                 return this.queue( type || "fx", [] );\r
143         }\r
144 });