Build: Take core-js-bundle from the external directory as well
[jquery.git] / src / core.js
blob31d749dd1f150fec6c726ce791dc48d1993bf7bf
1 import arr from "./var/arr.js";
2 import getProto from "./var/getProto.js";
3 import slice from "./var/slice.js";
4 import flat from "./var/flat.js";
5 import push from "./var/push.js";
6 import indexOf from "./var/indexOf.js";
7 import class2type from "./var/class2type.js";
8 import toString from "./var/toString.js";
9 import hasOwn from "./var/hasOwn.js";
10 import fnToString from "./var/fnToString.js";
11 import ObjectFunctionString from "./var/ObjectFunctionString.js";
12 import support from "./var/support.js";
13 import isWindow from "./var/isWindow.js";
14 import DOMEval from "./core/DOMEval.js";
15 import toType from "./core/toType.js";
17 var version = "@VERSION",
19         rhtmlSuffix = /HTML$/i,
21         // Define a local copy of jQuery
22         jQuery = function( selector, context ) {
24                 // The jQuery object is actually just the init constructor 'enhanced'
25                 // Need init if jQuery is called (just allow error to be thrown if not included)
26                 return new jQuery.fn.init( selector, context );
27         };
29 jQuery.fn = jQuery.prototype = {
31         // The current version of jQuery being used
32         jquery: version,
34         constructor: jQuery,
36         // The default length of a jQuery object is 0
37         length: 0,
39         toArray: function() {
40                 return slice.call( this );
41         },
43         // Get the Nth element in the matched element set OR
44         // Get the whole matched element set as a clean array
45         get: function( num ) {
47                 // Return all the elements in a clean array
48                 if ( num == null ) {
49                         return slice.call( this );
50                 }
52                 // Return just the one element from the set
53                 return num < 0 ? this[ num + this.length ] : this[ num ];
54         },
56         // Take an array of elements and push it onto the stack
57         // (returning the new matched element set)
58         pushStack: function( elems ) {
60                 // Build a new jQuery matched element set
61                 var ret = jQuery.merge( this.constructor(), elems );
63                 // Add the old object onto the stack (as a reference)
64                 ret.prevObject = this;
66                 // Return the newly-formed element set
67                 return ret;
68         },
70         // Execute a callback for every element in the matched set.
71         each: function( callback ) {
72                 return jQuery.each( this, callback );
73         },
75         map: function( callback ) {
76                 return this.pushStack( jQuery.map( this, function( elem, i ) {
77                         return callback.call( elem, i, elem );
78                 } ) );
79         },
81         slice: function() {
82                 return this.pushStack( slice.apply( this, arguments ) );
83         },
85         first: function() {
86                 return this.eq( 0 );
87         },
89         last: function() {
90                 return this.eq( -1 );
91         },
93         even: function() {
94                 return this.pushStack( jQuery.grep( this, function( _elem, i ) {
95                         return ( i + 1 ) % 2;
96                 } ) );
97         },
99         odd: function() {
100                 return this.pushStack( jQuery.grep( this, function( _elem, i ) {
101                         return i % 2;
102                 } ) );
103         },
105         eq: function( i ) {
106                 var len = this.length,
107                         j = +i + ( i < 0 ? len : 0 );
108                 return this.pushStack( j >= 0 && j < len ? [ this[ j ] ] : [] );
109         },
111         end: function() {
112                 return this.prevObject || this.constructor();
113         }
116 jQuery.extend = jQuery.fn.extend = function() {
117         var options, name, src, copy, copyIsArray, clone,
118                 target = arguments[ 0 ] || {},
119                 i = 1,
120                 length = arguments.length,
121                 deep = false;
123         // Handle a deep copy situation
124         if ( typeof target === "boolean" ) {
125                 deep = target;
127                 // Skip the boolean and the target
128                 target = arguments[ i ] || {};
129                 i++;
130         }
132         // Handle case when target is a string or something (possible in deep copy)
133         if ( typeof target !== "object" && typeof target !== "function" ) {
134                 target = {};
135         }
137         // Extend jQuery itself if only one argument is passed
138         if ( i === length ) {
139                 target = this;
140                 i--;
141         }
143         for ( ; i < length; i++ ) {
145                 // Only deal with non-null/undefined values
146                 if ( ( options = arguments[ i ] ) != null ) {
148                         // Extend the base object
149                         for ( name in options ) {
150                                 copy = options[ name ];
152                                 // Prevent Object.prototype pollution
153                                 // Prevent never-ending loop
154                                 if ( name === "__proto__" || target === copy ) {
155                                         continue;
156                                 }
158                                 // Recurse if we're merging plain objects or arrays
159                                 if ( deep && copy && ( jQuery.isPlainObject( copy ) ||
160                                         ( copyIsArray = Array.isArray( copy ) ) ) ) {
161                                         src = target[ name ];
163                                         // Ensure proper type for the source value
164                                         if ( copyIsArray && !Array.isArray( src ) ) {
165                                                 clone = [];
166                                         } else if ( !copyIsArray && !jQuery.isPlainObject( src ) ) {
167                                                 clone = {};
168                                         } else {
169                                                 clone = src;
170                                         }
171                                         copyIsArray = false;
173                                         // Never move original objects, clone them
174                                         target[ name ] = jQuery.extend( deep, clone, copy );
176                                 // Don't bring in undefined values
177                                 } else if ( copy !== undefined ) {
178                                         target[ name ] = copy;
179                                 }
180                         }
181                 }
182         }
184         // Return the modified object
185         return target;
188 jQuery.extend( {
190         // Unique for each copy of jQuery on the page
191         expando: "jQuery" + ( version + Math.random() ).replace( /\D/g, "" ),
193         // Assume jQuery is ready without the ready module
194         isReady: true,
196         error: function( msg ) {
197                 throw new Error( msg );
198         },
200         noop: function() {},
202         isPlainObject: function( obj ) {
203                 var proto, Ctor;
205                 // Detect obvious negatives
206                 // Use toString instead of jQuery.type to catch host objects
207                 if ( !obj || toString.call( obj ) !== "[object Object]" ) {
208                         return false;
209                 }
211                 proto = getProto( obj );
213                 // Objects with no prototype (e.g., `Object.create( null )`) are plain
214                 if ( !proto ) {
215                         return true;
216                 }
218                 // Objects with prototype are plain iff they were constructed by a global Object function
219                 Ctor = hasOwn.call( proto, "constructor" ) && proto.constructor;
220                 return typeof Ctor === "function" && fnToString.call( Ctor ) === ObjectFunctionString;
221         },
223         isEmptyObject: function( obj ) {
224                 var name;
226                 for ( name in obj ) {
227                         return false;
228                 }
229                 return true;
230         },
232         // Evaluates a script in a provided context; falls back to the global one
233         // if not specified.
234         globalEval: function( code, options, doc ) {
235                 DOMEval( code, { nonce: options && options.nonce }, doc );
236         },
238         each: function( obj, callback ) {
239                 var length, i = 0;
241                 if ( isArrayLike( obj ) ) {
242                         length = obj.length;
243                         for ( ; i < length; i++ ) {
244                                 if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
245                                         break;
246                                 }
247                         }
248                 } else {
249                         for ( i in obj ) {
250                                 if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
251                                         break;
252                                 }
253                         }
254                 }
256                 return obj;
257         },
260         // Retrieve the text value of an array of DOM nodes
261         text: function( elem ) {
262                 var node,
263                         ret = "",
264                         i = 0,
265                         nodeType = elem.nodeType;
267                 if ( !nodeType ) {
269                         // If no nodeType, this is expected to be an array
270                         while ( ( node = elem[ i++ ] ) ) {
272                                 // Do not traverse comment nodes
273                                 ret += jQuery.text( node );
274                         }
275                 } else if ( nodeType === 1 || nodeType === 9 || nodeType === 11 ) {
276                         return elem.textContent;
277                 } else if ( nodeType === 3 || nodeType === 4 ) {
278                         return elem.nodeValue;
279                 }
281                 // Do not include comment or processing instruction nodes
283                 return ret;
284         },
287         // results is for internal usage only
288         makeArray: function( arr, results ) {
289                 var ret = results || [];
291                 if ( arr != null ) {
292                         if ( isArrayLike( Object( arr ) ) ) {
293                                 jQuery.merge( ret,
294                                         typeof arr === "string" ?
295                                                 [ arr ] : arr
296                                 );
297                         } else {
298                                 push.call( ret, arr );
299                         }
300                 }
302                 return ret;
303         },
305         inArray: function( elem, arr, i ) {
306                 return arr == null ? -1 : indexOf.call( arr, elem, i );
307         },
309         isXMLDoc: function( elem ) {
310                 var namespace = elem && elem.namespaceURI,
311                         docElem = elem && ( elem.ownerDocument || elem ).documentElement;
313                 // Assume HTML when documentElement doesn't yet exist, such as inside
314                 // document fragments.
315                 return !rhtmlSuffix.test( namespace || docElem && docElem.nodeName || "HTML" );
316         },
318         merge: function( first, second ) {
319                 var len = +second.length,
320                         j = 0,
321                         i = first.length;
323                 for ( ; j < len; j++ ) {
324                         first[ i++ ] = second[ j ];
325                 }
327                 first.length = i;
329                 return first;
330         },
332         grep: function( elems, callback, invert ) {
333                 var callbackInverse,
334                         matches = [],
335                         i = 0,
336                         length = elems.length,
337                         callbackExpect = !invert;
339                 // Go through the array, only saving the items
340                 // that pass the validator function
341                 for ( ; i < length; i++ ) {
342                         callbackInverse = !callback( elems[ i ], i );
343                         if ( callbackInverse !== callbackExpect ) {
344                                 matches.push( elems[ i ] );
345                         }
346                 }
348                 return matches;
349         },
351         // arg is for internal usage only
352         map: function( elems, callback, arg ) {
353                 var length, value,
354                         i = 0,
355                         ret = [];
357                 // Go through the array, translating each of the items to their new values
358                 if ( isArrayLike( elems ) ) {
359                         length = elems.length;
360                         for ( ; i < length; i++ ) {
361                                 value = callback( elems[ i ], i, arg );
363                                 if ( value != null ) {
364                                         ret.push( value );
365                                 }
366                         }
368                 // Go through every key on the object,
369                 } else {
370                         for ( i in elems ) {
371                                 value = callback( elems[ i ], i, arg );
373                                 if ( value != null ) {
374                                         ret.push( value );
375                                 }
376                         }
377                 }
379                 // Flatten any nested arrays
380                 return flat( ret );
381         },
383         // A global GUID counter for objects
384         guid: 1,
386         // jQuery.support is not used in Core but other projects attach their
387         // properties to it so it needs to exist.
388         support: support
389 } );
391 if ( typeof Symbol === "function" ) {
392         jQuery.fn[ Symbol.iterator ] = arr[ Symbol.iterator ];
395 // Populate the class2type map
396 jQuery.each( "Boolean Number String Function Array Date RegExp Object Error Symbol".split( " " ),
397         function( _i, name ) {
398                 class2type[ "[object " + name + "]" ] = name.toLowerCase();
399         } );
401 function isArrayLike( obj ) {
403         var length = !!obj && obj.length,
404                 type = toType( obj );
406         if ( typeof obj === "function" || isWindow( obj ) ) {
407                 return false;
408         }
410         return type === "array" || length === 0 ||
411                 typeof length === "number" && length > 0 && ( length - 1 ) in obj;
414 export default jQuery;