From 4c9d62be82508f34e5e400d88b943dedf1419ac4 Mon Sep 17 00:00:00 2001 From: Steve Clay Date: Thu, 4 Sep 2008 01:08:38 +0000 Subject: [PATCH] ab_tests/ : + test for /min (and reran) examples : cleanup - examples/3 - jquery-1.2.3.js (unneeded duplicate) --- min_extras/ab_tests/results_summary.txt | 38 +- min_extras/ab_tests/test_all.bat | 28 +- min_extras/config.php | 2 +- min_extras/examples/1/_groupsSources.php | 2 +- min_extras/examples/1/index.php | 9 +- min_extras/examples/2/_groupsSources.php | 2 +- min_extras/examples/2/index.php | 20 +- min_extras/examples/3/index.php | 37 - min_extras/examples/3/m.php | 44 - min_extras/examples/index.php | 3 + min_extras/examples/jquery-1.2.3.js | 3408 ------------------- min_extras/examples/lib.js | 6 + min_extras/examples/test space.js | 6 +- min_extras/unit_tests/test_HTTP_Encoder.php | 2 +- 14 files changed, 78 insertions(+), 3529 deletions(-) delete mode 100644 min_extras/examples/3/index.php delete mode 100644 min_extras/examples/3/m.php create mode 100644 min_extras/examples/index.php delete mode 100644 min_extras/examples/jquery-1.2.3.js create mode 100644 min_extras/examples/lib.js diff --git a/min_extras/ab_tests/results_summary.txt b/min_extras/ab_tests/results_summary.txt index e54cc51..5437a92 100644 --- a/min_extras/ab_tests/results_summary.txt +++ b/min_extras/ab_tests/results_summary.txt @@ -1,28 +1,38 @@ -Document Path: /_3rd_party/minify/web/ab_tests/ideal_php/before.php +Document Path: /min_extras/ab_tests/ideal_php/before.php Document Length: 15993 bytes -Requests per second: 429.53 [#/sec] (mean) +Requests per second: 415.58 [#/sec] (mean) -------------------------------------------------------------------------------- -Document Path: /_3rd_party/minify/web/ab_tests/v1.0/minify.php?files=before.js +Document Path: /min_extras/ab_tests/v1.0/minify.php?files=before.js Document Length: 54159 bytes -Requests per second: 299.07 [#/sec] (mean) +Requests per second: 275.86 [#/sec] (mean) -------------------------------------------------------------------------------- -Document Path: /_3rd_party/minify/web/ab_tests/minify/test_Files.php +Document Path: /min_extras/ab_tests/minify/test_Files.php Document Length: 15993 bytes -Requests per second: 243.81 [#/sec] (mean) + (Connect: 0, Length: 4, Exceptions: 0) +Requests per second: 239.70 [#/sec] (mean) -------------------------------------------------------------------------------- -Document Path: /_3rd_party/minify/web/ab_tests/minify/test_Groups.php/test +Document Path: /min_extras/ab_tests/minify/test_Groups.php/test Document Length: 15993 bytes -Requests per second: 225.35 [#/sec] (mean) + (Connect: 0, Length: 2, Exceptions: 0) +Requests per second: 204.15 [#/sec] (mean) -------------------------------------------------------------------------------- -Document Path: /_3rd_party/minify/web/ab_tests/minify/test_Version1.php?files=before.js +Document Path: /min_extras/ab_tests/minify/test_Version1.php?files=before.js Document Length: 15993 bytes -Requests per second: 234.43 [#/sec] (mean) + (Connect: 0, Length: 2, Exceptions: 0) +Requests per second: 233.58 [#/sec] (mean) -------------------------------------------------------------------------------- -Document Path: /_3rd_party/minify/web/ab_tests/mod_deflate/before.js +Document Path: /min/?f=min_extras/ab_tests/minify/before.js +Document Length: 15993 bytes + (Connect: 0, Length: 1, Exceptions: 0) +Requests per second: 246.63 [#/sec] (mean) +-------------------------------------------------------------------------------- +Document Path: /min_extras/ab_tests/mod_deflate/before.js Document Length: 16053 bytes -Requests per second: 189.07 [#/sec] (mean) + (Connect: 0, Length: 1, Exceptions: 0) +Requests per second: 191.04 [#/sec] (mean) -------------------------------------------------------------------------------- -Document Path: /_3rd_party/minify/web/ab_tests/type-map/before.js.var +Document Path: /min_extras/ab_tests/type-map/before.js.var Document Length: 15993 bytes -Requests per second: 503.94 [#/sec] (mean) + (Connect: 0, Length: 1, Exceptions: 0) +Requests per second: 518.22 [#/sec] (mean) -------------------------------------------------------------------------------- diff --git a/min_extras/ab_tests/test_all.bat b/min_extras/ab_tests/test_all.bat index cc31561..45b9962 100644 --- a/min_extras/ab_tests/test_all.bat +++ b/min_extras/ab_tests/test_all.bat @@ -1,9 +1,13 @@ @SET PATH=%PATH%;C:\xampp\apache\bin -::SET ABCALL=ab -d -S -c 100 -n 2000 -H "Accept-Encoding: deflate, gzip" http://localhost -@SET ABCALL=ab -d -S -c 100 -n 2000 -H "Accept-Encoding: deflate, gzip" http://mc.dev/_3rd_party +@SET DOMAIN=http://mc.dev -::SET TXTVIEWER=notepad.exe +::@SET ABCALL=ab -d -S -c 100 -n 2000 -H "Accept-Encoding: deflate, gzip" http://localhost +@SET ABCALL=ab -d -S -c 100 -n 2000 -H "Accept-Encoding: deflate, gzip" + +@SET ABTESTS=%DOMAIN%/min_extras/ab_tests + +::@SET TXTVIEWER=notepad.exe @SET TXTVIEWER="C:\Program Files\Notepad++\notepad++.exe" @SET DELIM=TYPE _delimiter @@ -11,31 +15,35 @@ DEL results.txt :: baseline PHP -%ABCALL%/minify/web/ab_tests/ideal_php/before.php >> results.txt +%ABCALL% %ABTESTS%/ideal_php/before.php >> results.txt @%DELIM% >> results.txt :: 1.0 release -%ABCALL%/minify/web/ab_tests/v1.0/minify.php?files=before.js >> results.txt +%ABCALL% %ABTESTS%/v1.0/minify.php?files=before.js >> results.txt @%DELIM% >> results.txt :: Files controller -%ABCALL%/minify/web/ab_tests/minify/test_Files.php >> results.txt +%ABCALL% %ABTESTS%/minify/test_Files.php >> results.txt @%DELIM% >> results.txt :: Groups controller -%ABCALL%/minify/web/ab_tests/minify/test_Groups.php/test >> results.txt +%ABCALL% %ABTESTS%/minify/test_Groups.php/test >> results.txt @%DELIM% >> results.txt :: Version1 controller -%ABCALL%/minify/web/ab_tests/minify/test_Version1.php?files=before.js >> results.txt +%ABCALL% %ABTESTS%/minify/test_Version1.php?files=before.js >> results.txt +@%DELIM% >> results.txt + +::/min application +%ABCALL% %DOMAIN%/min/?f=min_extras/ab_tests/minify/before.js >> results.txt @%DELIM% >> results.txt :: mod_deflate -%ABCALL%/minify/web/ab_tests/mod_deflate/before.js >> results.txt +%ABCALL% %ABTESTS%/mod_deflate/before.js >> results.txt @%DELIM% >> results.txt :: type-map -%ABCALL%/minify/web/ab_tests/type-map/before.js.var >> results.txt +%ABCALL% %ABTESTS%/type-map/before.js.var >> results.txt @%DELIM% >> results.txt FINDSTR "Path: Length: Requests --" results.txt > results_summary.txt diff --git a/min_extras/config.php b/min_extras/config.php index e9ed391..3ad3d55 100644 --- a/min_extras/config.php +++ b/min_extras/config.php @@ -13,5 +13,5 @@ ini_set('include_path', * Set $minifyCachePath to a PHP-writeable path to enable server-side caching * in all examples and tests. */ -$minifyCachePath = 'C:/xampp/tmp'; // ''; +$minifyCachePath = ''; diff --git a/min_extras/examples/1/_groupsSources.php b/min_extras/examples/1/_groupsSources.php index ae33a03..efb9085 100644 --- a/min_extras/examples/1/_groupsSources.php +++ b/min_extras/examples/1/_groupsSources.php @@ -3,7 +3,7 @@ $base = realpath(dirname(__FILE__) . '/..'); $groupsSources = array( 'js' => array( - "{$base}/jquery-1.2.3.js" + "{$base}/lib.js" ,"{$base}/test space.js" ) ,'css' => array("{$base}/test.css") diff --git a/min_extras/examples/1/index.php b/min_extras/examples/1/index.php index e3ba2fe..27ae19c 100644 --- a/min_extras/examples/1/index.php +++ b/min_extras/examples/1/index.php @@ -18,8 +18,8 @@ $cssBuild = new Minify_Build($groupsSources['css']);

Note: You should always enable caching using -Minify::useServerCache(). For the examples this can be set in -config.php. Notice that minifying jQuery takes several seconds!.

+Minify::setCache(). For the examples this can be set in +config.php.

Minify Example 1 : Groups controller + Far-off Expires header

@@ -40,7 +40,10 @@ changed in the HTML document, causing the browser to request a new version.

Test client cache

-

Reload page (F5 can trigger no-cache headers)

+

When you click here to reload the page, your browser should +not have to re-download the minified files.

+ +

example 2 »

diff --git a/min_extras/examples/2/_groupsSources.php b/min_extras/examples/2/_groupsSources.php index ae33a03..efb9085 100644 --- a/min_extras/examples/2/_groupsSources.php +++ b/min_extras/examples/2/_groupsSources.php @@ -3,7 +3,7 @@ $base = realpath(dirname(__FILE__) . '/..'); $groupsSources = array( 'js' => array( - "{$base}/jquery-1.2.3.js" + "{$base}/lib.js" ,"{$base}/test space.js" ) ,'css' => array("{$base}/test.css") diff --git a/min_extras/examples/2/index.php b/min_extras/examples/2/index.php index f4f4f3b..5fdcda5 100644 --- a/min_extras/examples/2/index.php +++ b/min_extras/examples/2/index.php @@ -26,8 +26,8 @@ ob_start();

Note: You should always enable caching using -Minify::useServerCache(). For the examples this can be set in -config.php. Notice that minifying jQuery takes several seconds!.

+Minify::setCache(). For the examples this can be set in +config.php.

Minify Example 2: Minifying Everything

@@ -40,6 +40,9 @@ elements.

As the document is XHTML, Minify_HTML places the 2nd <script> element in a CDATA section because it contains "<". The output is valid XHTML.

+

Validate XHTML

+

Minify tests

Test client cache

-

Reload page (F5 can trigger no-cache headers)

+

When you click here to reload the page, your browser should +not have to re-download any files.

+ +

extras index »

diff --git a/min_extras/examples/3/index.php b/min_extras/examples/3/index.php deleted file mode 100644 index 3c047e2..0000000 --- a/min_extras/examples/3/index.php +++ /dev/null @@ -1,37 +0,0 @@ - - - - - Minify Example 3 - - - - - - -

Note: You should always enable caching using -Minify::useServerCache(). For the examples this can be set in -config.php. Notice that minifying jQuery takes several seconds!.

- - -

Minify Example 3: Files controller

- -

This is an example of Minify serving a directory of single css/js files. -Each file is minified and sent with HTTP encoding (browser-permitting).

- -

Minify tests

- - -

Test client cache

-

Reload page (F5 can trigger no-cache headers)

- - - - - \ No newline at end of file diff --git a/min_extras/examples/3/m.php b/min_extras/examples/3/m.php deleted file mode 100644 index 8918a4a..0000000 --- a/min_extras/examples/3/m.php +++ /dev/null @@ -1,44 +0,0 @@ - dirname(__FILE__) . '/../' . $filename - )); - exit(); - } -} - -header("HTTP/1.0 404 Not Found"); -echo "HTTP/1.0 404 Not Found"; \ No newline at end of file diff --git a/min_extras/examples/index.php b/min_extras/examples/index.php new file mode 100644 index 0000000..e5762fe --- /dev/null +++ b/min_extras/examples/index.php @@ -0,0 +1,3 @@ +)[^>]*$|^#(\w+)$/; - -// Is it a simple selector -var isSimple = /^.[^:#\[\.]*$/; - -jQuery.fn = jQuery.prototype = { - init: function( selector, context ) { - // Make sure that a selection was provided - selector = selector || document; - - // Handle $(DOMElement) - if ( selector.nodeType ) { - this[0] = selector; - this.length = 1; - return this; - - // Handle HTML strings - } else if ( typeof selector == "string" ) { - // Are we dealing with HTML string or an ID? - var match = quickExpr.exec( selector ); - - // Verify a match, and that no context was specified for #id - if ( match && (match[1] || !context) ) { - - // HANDLE: $(html) -> $(array) - if ( match[1] ) - selector = jQuery.clean( [ match[1] ], context ); - - // HANDLE: $("#id") - else { - var elem = document.getElementById( match[3] ); - - // Make sure an element was located - if ( elem ) - // Handle the case where IE and Opera return items - // by name instead of ID - if ( elem.id != match[3] ) - return jQuery().find( selector ); - - // Otherwise, we inject the element directly into the jQuery object - else { - this[0] = elem; - this.length = 1; - return this; - } - - else - selector = []; - } - - // HANDLE: $(expr, [context]) - // (which is just equivalent to: $(content).find(expr) - } else - return new jQuery( context ).find( selector ); - - // HANDLE: $(function) - // Shortcut for document ready - } else if ( jQuery.isFunction( selector ) ) - return new jQuery( document )[ jQuery.fn.ready ? "ready" : "load" ]( selector ); - - return this.setArray( - // HANDLE: $(array) - selector.constructor == Array && selector || - - // HANDLE: $(arraylike) - // Watch for when an array-like object, contains DOM nodes, is passed in as the selector - (selector.jquery || selector.length && selector != window && !selector.nodeType && selector[0] != undefined && selector[0].nodeType) && jQuery.makeArray( selector ) || - - // HANDLE: $(*) - [ selector ] ); - }, - - // The current version of jQuery being used - jquery: "1.2.3", - - // The number of elements contained in the matched element set - size: function() { - return this.length; - }, - - // The number of elements contained in the matched element set - length: 0, - - // Get the Nth element in the matched element set OR - // Get the whole matched element set as a clean array - get: function( num ) { - return num == undefined ? - - // Return a 'clean' array - jQuery.makeArray( this ) : - - // Return just the object - this[ num ]; - }, - - // Take an array of elements and push it onto the stack - // (returning the new matched element set) - pushStack: function( elems ) { - // Build a new jQuery matched element set - var ret = jQuery( elems ); - - // Add the old object onto the stack (as a reference) - ret.prevObject = this; - - // Return the newly-formed element set - return ret; - }, - - // Force the current matched set of elements to become - // the specified array of elements (destroying the stack in the process) - // You should use pushStack() in order to do this, but maintain the stack - setArray: function( elems ) { - // Resetting the length to 0, then using the native Array push - // is a super-fast way to populate an object with array-like properties - this.length = 0; - Array.prototype.push.apply( this, elems ); - - return this; - }, - - // Execute a callback for every element in the matched set. - // (You can seed the arguments with an array of args, but this is - // only used internally.) - each: function( callback, args ) { - return jQuery.each( this, callback, args ); - }, - - // Determine the position of an element within - // the matched set of elements - index: function( elem ) { - var ret = -1; - - // Locate the position of the desired element - this.each(function(i){ - if ( this == elem ) - ret = i; - }); - - return ret; - }, - - attr: function( name, value, type ) { - var options = name; - - // Look for the case where we're accessing a style value - if ( name.constructor == String ) - if ( value == undefined ) - return this.length && jQuery[ type || "attr" ]( this[0], name ) || undefined; - - else { - options = {}; - options[ name ] = value; - } - - // Check to see if we're setting style values - return this.each(function(i){ - // Set all the styles - for ( name in options ) - jQuery.attr( - type ? - this.style : - this, - name, jQuery.prop( this, options[ name ], type, i, name ) - ); - }); - }, - - css: function( key, value ) { - // ignore negative width and height values - if ( (key == 'width' || key == 'height') && parseFloat(value) < 0 ) - value = undefined; - return this.attr( key, value, "curCSS" ); - }, - - text: function( text ) { - if ( typeof text != "object" && text != null ) - return this.empty().append( (this[0] && this[0].ownerDocument || document).createTextNode( text ) ); - - var ret = ""; - - jQuery.each( text || this, function(){ - jQuery.each( this.childNodes, function(){ - if ( this.nodeType != 8 ) - ret += this.nodeType != 1 ? - this.nodeValue : - jQuery.fn.text( [ this ] ); - }); - }); - - return ret; - }, - - wrapAll: function( html ) { - if ( this[0] ) - // The elements to wrap the target around - jQuery( html, this[0].ownerDocument ) - .clone() - .insertBefore( this[0] ) - .map(function(){ - var elem = this; - - while ( elem.firstChild ) - elem = elem.firstChild; - - return elem; - }) - .append(this); - - return this; - }, - - wrapInner: function( html ) { - return this.each(function(){ - jQuery( this ).contents().wrapAll( html ); - }); - }, - - wrap: function( html ) { - return this.each(function(){ - jQuery( this ).wrapAll( html ); - }); - }, - - append: function() { - return this.domManip(arguments, true, false, function(elem){ - if (this.nodeType == 1) - this.appendChild( elem ); - }); - }, - - prepend: function() { - return this.domManip(arguments, true, true, function(elem){ - if (this.nodeType == 1) - this.insertBefore( elem, this.firstChild ); - }); - }, - - before: function() { - return this.domManip(arguments, false, false, function(elem){ - this.parentNode.insertBefore( elem, this ); - }); - }, - - after: function() { - return this.domManip(arguments, false, true, function(elem){ - this.parentNode.insertBefore( elem, this.nextSibling ); - }); - }, - - end: function() { - return this.prevObject || jQuery( [] ); - }, - - find: function( selector ) { - var elems = jQuery.map(this, function(elem){ - return jQuery.find( selector, elem ); - }); - - return this.pushStack( /[^+>] [^+>]/.test( selector ) || selector.indexOf("..") > -1 ? - jQuery.unique( elems ) : - elems ); - }, - - clone: function( events ) { - // Do the clone - var ret = this.map(function(){ - if ( jQuery.browser.msie && !jQuery.isXMLDoc(this) ) { - // IE copies events bound via attachEvent when - // using cloneNode. Calling detachEvent on the - // clone will also remove the events from the orignal - // In order to get around this, we use innerHTML. - // Unfortunately, this means some modifications to - // attributes in IE that are actually only stored - // as properties will not be copied (such as the - // the name attribute on an input). - var clone = this.cloneNode(true), - container = document.createElement("div"); - container.appendChild(clone); - return jQuery.clean([container.innerHTML])[0]; - } else - return this.cloneNode(true); - }); - - // Need to set the expando to null on the cloned set if it exists - // removeData doesn't work here, IE removes it from the original as well - // this is primarily for IE but the data expando shouldn't be copied over in any browser - var clone = ret.find("*").andSelf().each(function(){ - if ( this[ expando ] != undefined ) - this[ expando ] = null; - }); - - // Copy the events from the original to the clone - if ( events === true ) - this.find("*").andSelf().each(function(i){ - if (this.nodeType == 3) - return; - var events = jQuery.data( this, "events" ); - - for ( var type in events ) - for ( var handler in events[ type ] ) - jQuery.event.add( clone[ i ], type, events[ type ][ handler ], events[ type ][ handler ].data ); - }); - - // Return the cloned set - return ret; - }, - - filter: function( selector ) { - return this.pushStack( - jQuery.isFunction( selector ) && - jQuery.grep(this, function(elem, i){ - return selector.call( elem, i ); - }) || - - jQuery.multiFilter( selector, this ) ); - }, - - not: function( selector ) { - if ( selector.constructor == String ) - // test special case where just one selector is passed in - if ( isSimple.test( selector ) ) - return this.pushStack( jQuery.multiFilter( selector, this, true ) ); - else - selector = jQuery.multiFilter( selector, this ); - - var isArrayLike = selector.length && selector[selector.length - 1] !== undefined && !selector.nodeType; - return this.filter(function() { - return isArrayLike ? jQuery.inArray( this, selector ) < 0 : this != selector; - }); - }, - - add: function( selector ) { - return !selector ? this : this.pushStack( jQuery.merge( - this.get(), - selector.constructor == String ? - jQuery( selector ).get() : - selector.length != undefined && (!selector.nodeName || jQuery.nodeName(selector, "form")) ? - selector : [selector] ) ); - }, - - is: function( selector ) { - return selector ? - jQuery.multiFilter( selector, this ).length > 0 : - false; - }, - - hasClass: function( selector ) { - return this.is( "." + selector ); - }, - - val: function( value ) { - if ( value == undefined ) { - - if ( this.length ) { - var elem = this[0]; - - // We need to handle select boxes special - if ( jQuery.nodeName( elem, "select" ) ) { - var index = elem.selectedIndex, - values = [], - options = elem.options, - one = elem.type == "select-one"; - - // Nothing was selected - if ( index < 0 ) - return null; - - // Loop through all the selected options - for ( var i = one ? index : 0, max = one ? index + 1 : options.length; i < max; i++ ) { - var option = options[ i ]; - - if ( option.selected ) { - // Get the specifc value for the option - value = jQuery.browser.msie && !option.attributes.value.specified ? option.text : option.value; - - // We don't need an array for one selects - if ( one ) - return value; - - // Multi-Selects return an array - values.push( value ); - } - } - - return values; - - // Everything else, we just grab the value - } else - return (this[0].value || "").replace(/\r/g, ""); - - } - - return undefined; - } - - return this.each(function(){ - if ( this.nodeType != 1 ) - return; - - if ( value.constructor == Array && /radio|checkbox/.test( this.type ) ) - this.checked = (jQuery.inArray(this.value, value) >= 0 || - jQuery.inArray(this.name, value) >= 0); - - else if ( jQuery.nodeName( this, "select" ) ) { - var values = value.constructor == Array ? - value : - [ value ]; - - jQuery( "option", this ).each(function(){ - this.selected = (jQuery.inArray( this.value, values ) >= 0 || - jQuery.inArray( this.text, values ) >= 0); - }); - - if ( !values.length ) - this.selectedIndex = -1; - - } else - this.value = value; - }); - }, - - html: function( value ) { - return value == undefined ? - (this.length ? - this[0].innerHTML : - null) : - this.empty().append( value ); - }, - - replaceWith: function( value ) { - return this.after( value ).remove(); - }, - - eq: function( i ) { - return this.slice( i, i + 1 ); - }, - - slice: function() { - return this.pushStack( Array.prototype.slice.apply( this, arguments ) ); - }, - - map: function( callback ) { - return this.pushStack( jQuery.map(this, function(elem, i){ - return callback.call( elem, i, elem ); - })); - }, - - andSelf: function() { - return this.add( this.prevObject ); - }, - - data: function( key, value ){ - var parts = key.split("."); - parts[1] = parts[1] ? "." + parts[1] : ""; - - if ( value == null ) { - var data = this.triggerHandler("getData" + parts[1] + "!", [parts[0]]); - - if ( data == undefined && this.length ) - data = jQuery.data( this[0], key ); - - return data == null && parts[1] ? - this.data( parts[0] ) : - data; - } else - return this.trigger("setData" + parts[1] + "!", [parts[0], value]).each(function(){ - jQuery.data( this, key, value ); - }); - }, - - removeData: function( key ){ - return this.each(function(){ - jQuery.removeData( this, key ); - }); - }, - - domManip: function( args, table, reverse, callback ) { - var clone = this.length > 1, elems; - - return this.each(function(){ - if ( !elems ) { - elems = jQuery.clean( args, this.ownerDocument ); - - if ( reverse ) - elems.reverse(); - } - - var obj = this; - - if ( table && jQuery.nodeName( this, "table" ) && jQuery.nodeName( elems[0], "tr" ) ) - obj = this.getElementsByTagName("tbody")[0] || this.appendChild( this.ownerDocument.createElement("tbody") ); - - var scripts = jQuery( [] ); - - jQuery.each(elems, function(){ - var elem = clone ? - jQuery( this ).clone( true )[0] : - this; - - // execute all scripts after the elements have been injected - if ( jQuery.nodeName( elem, "script" ) ) { - scripts = scripts.add( elem ); - } else { - // Remove any inner scripts for later evaluation - if ( elem.nodeType == 1 ) - scripts = scripts.add( jQuery( "script", elem ).remove() ); - - // Inject the elements into the document - callback.call( obj, elem ); - } - }); - - scripts.each( evalScript ); - }); - } -}; - -// Give the init function the jQuery prototype for later instantiation -jQuery.prototype.init.prototype = jQuery.prototype; - -function evalScript( i, elem ) { - if ( elem.src ) - jQuery.ajax({ - url: elem.src, - async: false, - dataType: "script" - }); - - else - jQuery.globalEval( elem.text || elem.textContent || elem.innerHTML || "" ); - - if ( elem.parentNode ) - elem.parentNode.removeChild( elem ); -} - -jQuery.extend = jQuery.fn.extend = function() { - // copy reference to target object - var target = arguments[0] || {}, i = 1, length = arguments.length, deep = false, options; - - // Handle a deep copy situation - if ( target.constructor == Boolean ) { - deep = target; - target = arguments[1] || {}; - // skip the boolean and the target - i = 2; - } - - // Handle case when target is a string or something (possible in deep copy) - if ( typeof target != "object" && typeof target != "function" ) - target = {}; - - // extend jQuery itself if only one argument is passed - if ( length == 1 ) { - target = this; - i = 0; - } - - for ( ; i < length; i++ ) - // Only deal with non-null/undefined values - if ( (options = arguments[ i ]) != null ) - // Extend the base object - for ( var name in options ) { - // Prevent never-ending loop - if ( target === options[ name ] ) - continue; - - // Recurse if we're merging object values - if ( deep && options[ name ] && typeof options[ name ] == "object" && target[ name ] && !options[ name ].nodeType ) - target[ name ] = jQuery.extend( target[ name ], options[ name ] ); - - // Don't bring in undefined values - else if ( options[ name ] != undefined ) - target[ name ] = options[ name ]; - - } - - // Return the modified object - return target; -}; - -var expando = "jQuery" + (new Date()).getTime(), uuid = 0, windowData = {}; - -// exclude the following css properties to add px -var exclude = /z-?index|font-?weight|opacity|zoom|line-?height/i; - -jQuery.extend({ - noConflict: function( deep ) { - window.$ = _$; - - if ( deep ) - window.jQuery = _jQuery; - - return jQuery; - }, - - // See test/unit/core.js for details concerning this function. - isFunction: function( fn ) { - return !!fn && typeof fn != "string" && !fn.nodeName && - fn.constructor != Array && /function/i.test( fn + "" ); - }, - - // check if an element is in a (or is an) XML document - isXMLDoc: function( elem ) { - return elem.documentElement && !elem.body || - elem.tagName && elem.ownerDocument && !elem.ownerDocument.body; - }, - - // Evalulates a script in a global context - globalEval: function( data ) { - data = jQuery.trim( data ); - - if ( data ) { - // Inspired by code by Andrea Giammarchi - // http://webreflection.blogspot.com/2007/08/global-scope-evaluation-and-dom.html - var head = document.getElementsByTagName("head")[0] || document.documentElement, - script = document.createElement("script"); - - script.type = "text/javascript"; - if ( jQuery.browser.msie ) - script.text = data; - else - script.appendChild( document.createTextNode( data ) ); - - head.appendChild( script ); - head.removeChild( script ); - } - }, - - nodeName: function( elem, name ) { - return elem.nodeName && elem.nodeName.toUpperCase() == name.toUpperCase(); - }, - - cache: {}, - - data: function( elem, name, data ) { - elem = elem == window ? - windowData : - elem; - - var id = elem[ expando ]; - - // Compute a unique ID for the element - if ( !id ) - id = elem[ expando ] = ++uuid; - - // Only generate the data cache if we're - // trying to access or manipulate it - if ( name && !jQuery.cache[ id ] ) - jQuery.cache[ id ] = {}; - - // Prevent overriding the named cache with undefined values - if ( data != undefined ) - jQuery.cache[ id ][ name ] = data; - - // Return the named cache data, or the ID for the element - return name ? - jQuery.cache[ id ][ name ] : - id; - }, - - removeData: function( elem, name ) { - elem = elem == window ? - windowData : - elem; - - var id = elem[ expando ]; - - // If we want to remove a specific section of the element's data - if ( name ) { - if ( jQuery.cache[ id ] ) { - // Remove the section of cache data - delete jQuery.cache[ id ][ name ]; - - // If we've removed all the data, remove the element's cache - name = ""; - - for ( name in jQuery.cache[ id ] ) - break; - - if ( !name ) - jQuery.removeData( elem ); - } - - // Otherwise, we want to remove all of the element's data - } else { - // Clean up the element expando - try { - delete elem[ expando ]; - } catch(e){ - // IE has trouble directly removing the expando - // but it's ok with using removeAttribute - if ( elem.removeAttribute ) - elem.removeAttribute( expando ); - } - - // Completely remove the data cache - delete jQuery.cache[ id ]; - } - }, - - // args is for internal usage only - each: function( object, callback, args ) { - if ( args ) { - if ( object.length == undefined ) { - for ( var name in object ) - if ( callback.apply( object[ name ], args ) === false ) - break; - } else - for ( var i = 0, length = object.length; i < length; i++ ) - if ( callback.apply( object[ i ], args ) === false ) - break; - - // A special, fast, case for the most common use of each - } else { - if ( object.length == undefined ) { - for ( var name in object ) - if ( callback.call( object[ name ], name, object[ name ] ) === false ) - break; - } else - for ( var i = 0, length = object.length, value = object[0]; - i < length && callback.call( value, i, value ) !== false; value = object[++i] ){} - } - - return object; - }, - - prop: function( elem, value, type, i, name ) { - // Handle executable functions - if ( jQuery.isFunction( value ) ) - value = value.call( elem, i ); - - // Handle passing in a number to a CSS property - return value && value.constructor == Number && type == "curCSS" && !exclude.test( name ) ? - value + "px" : - value; - }, - - className: { - // internal only, use addClass("class") - add: function( elem, classNames ) { - jQuery.each((classNames || "").split(/\s+/), function(i, className){ - if ( elem.nodeType == 1 && !jQuery.className.has( elem.className, className ) ) - elem.className += (elem.className ? " " : "") + className; - }); - }, - - // internal only, use removeClass("class") - remove: function( elem, classNames ) { - if (elem.nodeType == 1) - elem.className = classNames != undefined ? - jQuery.grep(elem.className.split(/\s+/), function(className){ - return !jQuery.className.has( classNames, className ); - }).join(" ") : - ""; - }, - - // internal only, use is(".class") - has: function( elem, className ) { - return jQuery.inArray( className, (elem.className || elem).toString().split(/\s+/) ) > -1; - } - }, - - // A method for quickly swapping in/out CSS properties to get correct calculations - swap: function( elem, options, callback ) { - var old = {}; - // Remember the old values, and insert the new ones - for ( var name in options ) { - old[ name ] = elem.style[ name ]; - elem.style[ name ] = options[ name ]; - } - - callback.call( elem ); - - // Revert the old values - for ( var name in options ) - elem.style[ name ] = old[ name ]; - }, - - css: function( elem, name, force ) { - if ( name == "width" || name == "height" ) { - var val, props = { position: "absolute", visibility: "hidden", display:"block" }, which = name == "width" ? [ "Left", "Right" ] : [ "Top", "Bottom" ]; - - function getWH() { - val = name == "width" ? elem.offsetWidth : elem.offsetHeight; - var padding = 0, border = 0; - jQuery.each( which, function() { - padding += parseFloat(jQuery.curCSS( elem, "padding" + this, true)) || 0; - border += parseFloat(jQuery.curCSS( elem, "border" + this + "Width", true)) || 0; - }); - val -= Math.round(padding + border); - } - - if ( jQuery(elem).is(":visible") ) - getWH(); - else - jQuery.swap( elem, props, getWH ); - - return Math.max(0, val); - } - - return jQuery.curCSS( elem, name, force ); - }, - - curCSS: function( elem, name, force ) { - var ret; - - // A helper method for determining if an element's values are broken - function color( elem ) { - if ( !jQuery.browser.safari ) - return false; - - var ret = document.defaultView.getComputedStyle( elem, null ); - return !ret || ret.getPropertyValue("color") == ""; - } - - // We need to handle opacity special in IE - if ( name == "opacity" && jQuery.browser.msie ) { - ret = jQuery.attr( elem.style, "opacity" ); - - return ret == "" ? - "1" : - ret; - } - // Opera sometimes will give the wrong display answer, this fixes it, see #2037 - if ( jQuery.browser.opera && name == "display" ) { - var save = elem.style.outline; - elem.style.outline = "0 solid black"; - elem.style.outline = save; - } - - // Make sure we're using the right name for getting the float value - if ( name.match( /float/i ) ) - name = styleFloat; - - if ( !force && elem.style && elem.style[ name ] ) - ret = elem.style[ name ]; - - else if ( document.defaultView && document.defaultView.getComputedStyle ) { - - // Only "float" is needed here - if ( name.match( /float/i ) ) - name = "float"; - - name = name.replace( /([A-Z])/g, "-$1" ).toLowerCase(); - - var getComputedStyle = document.defaultView.getComputedStyle( elem, null ); - - if ( getComputedStyle && !color( elem ) ) - ret = getComputedStyle.getPropertyValue( name ); - - // If the element isn't reporting its values properly in Safari - // then some display: none elements are involved - else { - var swap = [], stack = []; - - // Locate all of the parent display: none elements - for ( var a = elem; a && color(a); a = a.parentNode ) - stack.unshift(a); - - // Go through and make them visible, but in reverse - // (It would be better if we knew the exact display type that they had) - for ( var i = 0; i < stack.length; i++ ) - if ( color( stack[ i ] ) ) { - swap[ i ] = stack[ i ].style.display; - stack[ i ].style.display = "block"; - } - - // Since we flip the display style, we have to handle that - // one special, otherwise get the value - ret = name == "display" && swap[ stack.length - 1 ] != null ? - "none" : - ( getComputedStyle && getComputedStyle.getPropertyValue( name ) ) || ""; - - // Finally, revert the display styles back - for ( var i = 0; i < swap.length; i++ ) - if ( swap[ i ] != null ) - stack[ i ].style.display = swap[ i ]; - } - - // We should always get a number back from opacity - if ( name == "opacity" && ret == "" ) - ret = "1"; - - } else if ( elem.currentStyle ) { - var camelCase = name.replace(/\-(\w)/g, function(all, letter){ - return letter.toUpperCase(); - }); - - ret = elem.currentStyle[ name ] || elem.currentStyle[ camelCase ]; - - // From the awesome hack by Dean Edwards - // http://erik.eae.net/archives/2007/07/27/18.54.15/#comment-102291 - - // If we're not dealing with a regular pixel number - // but a number that has a weird ending, we need to convert it to pixels - if ( !/^\d+(px)?$/i.test( ret ) && /^\d/.test( ret ) ) { - // Remember the original values - var style = elem.style.left, runtimeStyle = elem.runtimeStyle.left; - - // Put in the new values to get a computed value out - elem.runtimeStyle.left = elem.currentStyle.left; - elem.style.left = ret || 0; - ret = elem.style.pixelLeft + "px"; - - // Revert the changed values - elem.style.left = style; - elem.runtimeStyle.left = runtimeStyle; - } - } - - return ret; - }, - - clean: function( elems, context ) { - var ret = []; - context = context || document; - // !context.createElement fails in IE with an error but returns typeof 'object' - if (typeof context.createElement == 'undefined') - context = context.ownerDocument || context[0] && context[0].ownerDocument || document; - - jQuery.each(elems, function(i, elem){ - if ( !elem ) - return; - - if ( elem.constructor == Number ) - elem = elem.toString(); - - // Convert html string into DOM nodes - if ( typeof elem == "string" ) { - // Fix "XHTML"-style tags in all browsers - elem = elem.replace(/(<(\w+)[^>]*?)\/>/g, function(all, front, tag){ - return tag.match(/^(abbr|br|col|img|input|link|meta|param|hr|area|embed)$/i) ? - all : - front + ">"; - }); - - // Trim whitespace, otherwise indexOf won't work as expected - var tags = jQuery.trim( elem ).toLowerCase(), div = context.createElement("div"); - - var wrap = - // option or optgroup - !tags.indexOf("", "" ] || - - !tags.indexOf("", "" ] || - - tags.match(/^<(thead|tbody|tfoot|colg|cap)/) && - [ 1, "", "
" ] || - - !tags.indexOf("", "" ] || - - // matched above - (!tags.indexOf("", "" ] || - - !tags.indexOf("", "" ] || - - // IE can't serialize and