diff --git a/src/attributes/attr.js b/src/attributes/attr.js index 4c43eb1fc..9822f3e61 100644 --- a/src/attributes/attr.js +++ b/src/attributes/attr.js @@ -106,12 +106,19 @@ jQuery.extend( { // Hooks for boolean attributes boolHook = { set: function( elem, value, name ) { + var strValue = String( value ); + if ( value === false ) { // Remove boolean attributes when set to false jQuery.removeAttr( elem, name ); } else { - elem.setAttribute( name, name ); + elem.setAttribute( name, + name.toLowerCase() === "hidden" && + strValue.toLowerCase() === "until-found" ? + strValue : + name + ); } return name; } @@ -129,9 +136,13 @@ jQuery.each( jQuery.expr.match.bool.source.match( /\w+/g ), function( _i, name ) // Avoid an infinite loop by temporarily removing this function from the getter handle = attrHandle[ lowercaseName ]; attrHandle[ lowercaseName ] = ret; - ret = getter( elem, name, isXML ) != null ? - lowercaseName : - null; + + ret = getter( elem, name, isXML ); + ret = ret == null || + ( lowercaseName === "hidden" && ret.toLowerCase() === "until-found" ) ? + ret : + lowercaseName; + attrHandle[ lowercaseName ] = handle; } return ret; diff --git a/test/unit/attributes.js b/test/unit/attributes.js index 34bf579b8..b2360dfc9 100644 --- a/test/unit/attributes.js +++ b/test/unit/attributes.js @@ -479,6 +479,24 @@ QUnit.test( "attr(String, Object)", function( assert ) { assert.equal( jQuery( "#name" ).attr( "nonexisting", undefined ).attr( "nonexisting" ), undefined, ".attr('attribute', undefined) does not create attribute (trac-5571)" ); } ); +QUnit.test( "attr( previously-boolean-attr, non-boolean-value)", function( assert ) { + assert.expect( 3 ); + + var div = jQuery( "
" ).appendTo( "#qunit-fixture" ); + + div.attr( "hidden", "foo" ); + assert.strictEqual( div.attr( "hidden" ), "hidden", + "Values normalized for previously-boolean hidden attribute" ); + + div.attr( "hidden", "until-found" ); + assert.strictEqual( div.attr( "hidden" ), "until-found", + "`until-found` value preserved for hidden attribute" ); + + div.attr( "hiDdeN", "uNtil-fOund" ); + assert.strictEqual( div.attr( "hidden" ), "uNtil-fOund", + "`uNtil-fOund` different casing preserved" ); +} ); + QUnit.test( "attr(non-ASCII)", function( assert ) { assert.expect( 2 );