Mar 30 2008

How to force jQuery.extend deep recursion

Tag: otherAndrea Ercolino @ 14:13:14

jQuery.extend extends a target object with properties from other objects and it’s widely used in every piece of jQuery code.

Really it’s very useful and simple to undestand and use for flat properties.

jQuery.extend( 
  { a:1, b:'2' }, 
  { a:'1', c:3 } 
) == 
  { a:'1', b:'2', c:3 }

On the contrary, if the involved objects have object properties, jQuery.extend is less intuitive and less useful too.

jQuery.extend( 
  { a:{ x:1 }, b:'2' }, 
  { a:{ y:'1' }, c:3 } 
) == 
  { a:{ y:'1' }, b:'2', c:3 }

Luckily, an undocumented feature (deep) makes jQuery.extend recurr object properties.

jQuery.extend( true, 
  { a:{ x:1 }, b:'2' }, 
  { a:{ y:'1' }, c:3 } 
) == 
  { a:{ x:1, y:'1' }, b:'2', c:3 }

Unluckily, deep only works for the first level. (not really a ‘bug’)

jQuery.extend( true, 
  { a:{ x:1, z:{ m: '' } }, b:'2' }, 
  { a:{ y:'1', z:{ n: 0 } }, c:3 } 
) == 
  { a:{ x:1, y:'1', z:{ n:0 } }, b:'2', c:3 }

If you need deep recursion use jQuery.extend_deep instead.

jQuery.extend_deep( true, 
  { a:{ x:1, z:{ m: '' } }, b:'2' }, 
  { a:{ y:'1', z:{ n: 0 } }, c:3 } 
) == 
  { a:{ x:1, y:'1', z:{ m:'', n:0 } }, b:'2', c:3 }

Here is the jQuery.extend_deep plugin:

/**
 * Implement deep object extension 
 * by replacing the line 599 of jQuery-1.2.3.js
 * (commented out in this function)
 */
jQuery.extend_deep = function() {
	var target = arguments[0] || {}, i = 1, length = arguments.length, deep = false, options;

	if ( target.constructor == Boolean ) {
		deep = target;
		target = arguments[1] || {};
		i = 2;
	}

	if ( typeof target != "object" && typeof target != "function" )
		target = {};

	if ( length == 1 ) {
		target = this;
		i = 0;
	}

	for ( ; i < length; i++ )
		if ( (options = arguments[ i ]) != null )
			for ( var name in options ) {
				if ( target === options[ name ] )
					continue;

				if ( deep && options[ name ] && typeof options[ name ] == "object" && target[ name ] && !options[ name ].nodeType )
//					target[ name ] = jQuery.extend( target[ name ], options[ name ] );
					target[ name ] = jQuery.extend_deep( true, target[ name ], options[ name ] );

				else if ( options[ name ] != undefined )
					target[ name ] = options[ name ];

			}

	return target;
};


Mar 18 2008

Metaobjects 1.5 Released

Tag: MetaobjectsAndrea Ercolino @ 23:10:23
Changes
  • Added support for easy namespacing
  • Added support for jQuery 1.2.3 cache
  • Rewritten the manual from scratch
Download

You can download metaobjects from Google Code


Sep 24 2007

Chili 1.9 Released Today

Tag: Chili, HotChiliAndrea Ercolino @ 20:50:40

UPDATE: Chili 2.0 has been released

Changes
  • Circumvented an evil bottleneck
  • Simplified the core clockwork
  • Removed the bundled jQuery library
  • Changed the plugin names to follow the naming convention of jQuery’s plugins
  • Added a new example showing that Chili 1.9 is much faster
Links

Next Page »