diff options
-rw-r--r-- | src/selector.js | 11 | ||||
-rw-r--r-- | src/selector/rbuggyQSA.js | 5 | ||||
-rw-r--r-- | src/selector/support.js | 3 | ||||
-rw-r--r-- | test/unit/selector.js | 22 |
4 files changed, 34 insertions, 7 deletions
diff --git a/src/selector.js b/src/selector.js index e6ec6a326..117ee3051 100644 --- a/src/selector.js +++ b/src/selector.js @@ -255,15 +255,20 @@ function find( selector, context, results, seed ) { // `qSA` may not throw for unrecognized parts using forgiving parsing: // https://drafts.csswg.org/selectors/#forgiving-selector - // like the `:has()` pseudo-class: - // https://drafts.csswg.org/selectors/#relational + // like the `:is()` pseudo-class: + // https://drafts.csswg.org/selectors/#matches // `CSS.supports` is still expected to return `false` then: // https://drafts.csswg.org/css-conditional-4/#typedef-supports-selector-fn // https://drafts.csswg.org/css-conditional-4/#dfn-support-selector if ( support.cssSupportsSelector && + // `CSS.supports( "selector(...)" )` requires the argument to the + // `selector` function to be a `<complex-selector>`, not + // a `<complex-selector-list>` which our selector may be. Wrapping with + // `:is` works around the issue and is supported by all browsers + // we support except for IE which will fail the support test anyway. // eslint-disable-next-line no-undef - !CSS.supports( "selector(" + newSelector + ")" ) ) { + !CSS.supports( "selector(:is(" + newSelector + "))" ) ) { // Support: IE 11+ // Throw to get to the same code path as an error directly in qSA. diff --git a/src/selector/rbuggyQSA.js b/src/selector/rbuggyQSA.js index e8bfd0bf7..709fb0f63 100644 --- a/src/selector/rbuggyQSA.js +++ b/src/selector/rbuggyQSA.js @@ -27,9 +27,8 @@ if ( !support.cssSupportsSelector ) { // `:has()` uses a forgiving selector list as an argument so our regular // `try-catch` mechanism fails to catch `:has()` with arguments not supported // natively like `:has(:contains("Foo"))`. Where supported & spec-compliant, - // we now use `CSS.supports("selector(SELECTOR_TO_BE_TESTED)")` but outside - // that, let's mark `:has` as buggy to always use jQuery traversal for - // `:has()`. + // we now use `CSS.supports("selector(:is(SELECTOR_TO_BE_TESTED))")`, but + // outside that we mark `:has` as buggy. rbuggyQSA.push( ":has" ); } diff --git a/src/selector/support.js b/src/selector/support.js index ea9f24050..387c41bfe 100644 --- a/src/selector/support.js +++ b/src/selector/support.js @@ -1,5 +1,8 @@ import support from "../var/support.js"; +// Support: IE 11+ +// IE doesn't support `CSS.supports( "selector(...)" )`; it will throw +// in this support test. try { /* eslint-disable no-undef */ diff --git a/test/unit/selector.js b/test/unit/selector.js index 0057fe57a..d177ab997 100644 --- a/test/unit/selector.js +++ b/test/unit/selector.js @@ -400,7 +400,7 @@ QUnit.test( "name", function( assert ) { } ); QUnit.test( "comma-separated", function( assert ) { - assert.expect( 4 ); + assert.expect( 10 ); var fixture = jQuery( "<div><h2><span></span></h2><div><p><span></span></p><p></p></div></div>" ); @@ -408,6 +408,26 @@ QUnit.test( "comma-separated", function( assert ) { assert.equal( fixture.find( "h2, div p" ).filter( "h2" ).length, 1, "has to find one <h2>" ); assert.equal( fixture.find( "h2 , div p" ).filter( "p" ).length, 2, "has to find two <p>" ); assert.equal( fixture.find( "h2 , div p" ).filter( "h2" ).length, 1, "has to find one <h2>" ); + assert.equal( fixture.find( "h2 ,div p" ).filter( "p" ).length, 2, "has to find two <p>" ); + assert.equal( fixture.find( "h2 ,div p" ).filter( "h2" ).length, 1, "has to find one <h2>" ); + assert.equal( fixture.find( "h2,div p" ).filter( "p" ).length, 2, "has to find two <p>" ); + assert.equal( fixture.find( "h2,div p" ).filter( "h2" ).length, 1, "has to find one <h2>" ); + assert.equal( fixture.find( "h2\t,\rdiv p" ).filter( "p" ).length, 2, "has to find two <p>" ); + assert.equal( fixture.find( "h2\t,\rdiv p" ).filter( "h2" ).length, 1, "has to find one <h2>" ); +} ); + +QUnit.test( "comma-separated, only supported natively (gh-5177)", function( assert ) { + assert.expect( 5 ); + + var fixture = jQuery( "<div><input/><span></span></div>" ); + + fixture.appendTo( "#qunit-fixture" ); + + assert.equal( fixture.find( "input:valid, span" ).length, 2, "has to find two elements" ); + assert.equal( fixture.find( "input:valid , span" ).length, 2, "has to find two elements" ); + assert.equal( fixture.find( "input:valid ,span" ).length, 2, "has to find two elements" ); + assert.equal( fixture.find( "input:valid,span" ).length, 2, "has to find two elements" ); + assert.equal( fixture.find( "input:valid\t,\rspan" ).length, 2, "has to find two elements" ); } ); QUnit.test( "child and adjacent", function( assert ) { |