Merge branch 'master' of github.com:jquery/jquery
authorjeresig <jeresig@gmail.com>
Thu, 23 Sep 2010 16:09:49 +0000 (12:09 -0400)
committerjeresig <jeresig@gmail.com>
Thu, 23 Sep 2010 16:09:49 +0000 (12:09 -0400)
src/core.js
src/event.js
test/unit/core.js
test/unit/event.js

index f6a07eb..2c2b746 100644 (file)
@@ -69,7 +69,10 @@ var jQuery = function( selector, context ) {
        push = Array.prototype.push,
        slice = Array.prototype.slice,
        trim = String.prototype.trim,
-       indexOf = Array.prototype.indexOf;
+       indexOf = Array.prototype.indexOf,
+       
+       // [[Class]] -> type pairs
+       class2type = {};
 
 jQuery.fn = jQuery.prototype = {
        init: function( selector, context ) {
@@ -306,7 +309,7 @@ jQuery.fn.init.prototype = jQuery.fn;
 
 jQuery.extend = jQuery.fn.extend = function() {
        // copy reference to target object
-       var target = arguments[0] || {}, i = 1, length = arguments.length, deep = false, options, name, src, copy;
+       var target = arguments[0] || {}, i = 1, length = arguments.length, deep = false, options, name, src, copy, copyIsArray;
 
        // Handle a deep copy situation
        if ( typeof target === "boolean" ) {
@@ -340,10 +343,15 @@ jQuery.extend = jQuery.fn.extend = function() {
                                        continue;
                                }
 
-                               // Recurse if we're merging object literal values or arrays
-                               if ( deep && copy && ( jQuery.isPlainObject(copy) || jQuery.isArray(copy) ) ) {
-                                       var clone = src && ( jQuery.isPlainObject(src) || jQuery.isArray(src) ) ? src
-                                               : jQuery.isArray(copy) ? [] : {};
+                               // Recurse if we're merging plain objects or arrays
+                               if ( deep && copy && ( jQuery.isPlainObject(copy) || (copyIsArray = jQuery.isArray(copy)) ) ) {
+                                       if ( copyIsArray ) {
+                                               copyIsArray = false;
+                                               clone = src && jQuery.isArray(src) ? src : [];
+
+                                       } else {
+                                               clone = src && jQuery.isPlainObject(src) ? src : {};
+                                       }
 
                                        // Never move original objects, clone them
                                        target[ name ] = jQuery.extend( deep, clone, copy );
@@ -483,7 +491,7 @@ jQuery.extend({
        type: function( obj ) {
                return obj == null ?
                        String( obj ) :
-                       toString.call(obj).slice(8, -1).toLowerCase();
+                       class2type[ toString.call(obj) ] || "object";
        },
 
        isPlainObject: function( obj ) {
@@ -795,6 +803,11 @@ jQuery.extend({
        browser: {}
 });
 
+// Populate the class2type map
+jQuery.each("Boolean Number String Function Array Date RegExp Object".split(" "), function(i, name) {
+       class2type[ "[object " + name + "]" ] = name.toLowerCase();
+});
+
 browserMatch = jQuery.uaMatch( userAgent );
 if ( browserMatch.browser ) {
        jQuery.browser[ browserMatch.browser ] = true;
index 264ac5b..e667ddb 100644 (file)
@@ -944,6 +944,14 @@ jQuery.each(["live", "die"], function( i, name ) {
                var type, i = 0, match, namespaces, preType,
                        selector = origSelector || this.selector,
                        context = origSelector ? this : jQuery( this.context );
+               
+               if ( typeof types === "object" && !types.preventDefault ) {
+                       for ( var key in types ) {
+                               context[ name ]( key, data, types[key], selector );
+                       }
+                       
+                       return this;
+               }
 
                if ( jQuery.isFunction( data ) ) {
                        fn = data;
index eec3d7c..7ef2ad7 100644 (file)
@@ -219,7 +219,7 @@ test("trim", function() {
 });
 
 test("type", function() {
-       expect(18);
+       expect(23);
 
        equals( jQuery.type(null), "null", "null" );
        equals( jQuery.type(undefined), "undefined", "undefined" );
@@ -239,6 +239,11 @@ test("type", function() {
        equals( jQuery.type(new Date()), "date", "Date" );
        equals( jQuery.type(new Function("return;")), "function", "Function" );
        equals( jQuery.type(function(){}), "function", "Function" );
+       equals( jQuery.type(window), "object", "Window" );
+       equals( jQuery.type(document), "object", "Document" );
+       equals( jQuery.type(document.body), "object", "Element" );
+       equals( jQuery.type(document.createTextNode("foo")), "object", "TextNode" );
+       equals( jQuery.type(document.getElementsByTagName("*")), "object", "NodeList" );
 });
 
 test("isPlainObject", function() {
@@ -661,7 +666,7 @@ test("jQuery.merge()", function() {
 });
 
 test("jQuery.extend(Object, Object)", function() {
-       expect(27);
+       expect(28);
 
        var settings = { xnumber1: 5, xnumber2: 7, xstring1: "peter", xstring2: "pan" },
                options = { xnumber2: 1, xstring2: "x", xxx: "newstring" },
@@ -688,8 +693,11 @@ test("jQuery.extend(Object, Object)", function() {
        same( deep2.foo, deep2copy.foo, "Check if not deep2: options must not be modified" );
        equals( deep1.foo2, document, "Make sure that a deep clone was not attempted on the document" );
 
-       ok( jQuery.extend(true, [], arr) !== arr, "Deep extend of array must clone array" );
        ok( jQuery.extend(true, {}, nestedarray).arr !== arr, "Deep extend of object must clone child array" );
+       
+       // #5991
+       ok( jQuery.isArray( jQuery.extend(true, { arr: {} }, nestedarray).arr ), "Cloned array heve to be an Array" );
+       ok( jQuery.isPlainObject( jQuery.extend(true, { arr: arr }, { arr: {} }).arr ), "Cloned object heve to be an plain object" );
 
        var empty = {};
        var optionsWithLength = { foo: { length: -1 } };
index 9e1ac89..3032497 100644 (file)
@@ -206,6 +206,45 @@ test("bind/one/unbind(Object)", function(){
        equals( mouseoverCounter, 4, "bind(Object)" );
 });
 
+test("live/die(Object), delegate/undelegate(String, Object)", function() {
+       expect(6);
+       
+       var clickCounter = 0, mouseoverCounter = 0,
+               $p = jQuery("#firstp"), $a = $p.find("a:first");
+       
+       var events = {
+               click: function( event ) {
+                       clickCounter += ( event.data || 1 );
+               },
+               mouseover: function( event ) {
+                       mouseoverCounter += ( event.data || 1 );
+               }
+       };
+       
+       function trigger() {
+               $a.trigger("click").trigger("mouseover");
+       }
+       
+       $a.live( events );
+       $p.delegate( "a", events, 2 );
+       
+       trigger();
+       equals( clickCounter, 3, "live/delegate" );
+       equals( mouseoverCounter, 3, "live/delegate" );
+       
+       $p.undelegate( "a", events );
+       
+       trigger();
+       equals( clickCounter, 4, "undelegate" );
+       equals( mouseoverCounter, 4, "undelegate" );
+       
+       $a.die( events );
+       
+       trigger();
+       equals( clickCounter, 4, "die" );
+       equals( mouseoverCounter, 4, "die" );
+});
+
 test("bind(), iframes", function() {
        // events don't work with iframes, see #939 - this test fails in IE because of contentDocument
        var doc = jQuery("#loadediframe").contents();