@@ -2448,3 +2448,232 @@ QUnit[ QUnit.jQuerySelectors ? "test" : "skip" ]( "Ensure no 'undefined' handler
24482448 assert . ok ( ! jQuery . expr . attrHandle . hasOwnProperty ( "undefined" ) ,
24492449 "Extra attr handlers are not added to Expr.attrHandle (https://github.com/jquery/sizzle/issues/353)" ) ;
24502450} ) ;
2451+
2452+ QUnit . test ( "jQuery.find.matchesSelector" , function ( assert ) {
2453+ assert . expect ( 15 ) ;
2454+
2455+ var link = document . getElementById ( "simon1" ) ,
2456+ input = document . getElementById ( "text1" ) ,
2457+ option = document . getElementById ( "option1a" ) ,
2458+ disconnected = document . createElement ( "div" ) ;
2459+
2460+ link . title = "Don't click me" ;
2461+ assert . ok ( jQuery . find . matchesSelector ( link , "[rel='bookmark']" ) , "attribute-equals string" ) ;
2462+ assert . ok ( jQuery . find . matchesSelector ( link , "[rel=bookmark]" ) , "attribute-equals identifier" ) ;
2463+ assert . ok ( jQuery . find . matchesSelector ( link , "[\nrel = bookmark\t]" ) ,
2464+ "attribute-equals identifier (whitespace ignored)" ) ;
2465+ assert . ok ( jQuery . find . matchesSelector ( link , "a[title=\"Don't click me\"]" ) ,
2466+ "attribute-equals string containing single quote" ) ;
2467+
2468+ // trac-12303
2469+ input . setAttribute ( "data-pos" , ":first" ) ;
2470+ assert . ok ( jQuery . find . matchesSelector ( input , "input[data-pos=\\:first]" ) ,
2471+ "attribute-equals POS in identifier" ) ;
2472+ assert . ok ( jQuery . find . matchesSelector ( input , "input[data-pos=':first']" ) ,
2473+ "attribute-equals POS in string" ) ;
2474+ if ( QUnit . jQuerySelectors ) {
2475+ assert . ok ( jQuery . find . matchesSelector ( input , ":input[data-pos=':first']" ) ,
2476+ "attribute-equals POS in string after pseudo" ) ;
2477+ } else {
2478+ assert . ok ( "skip" , ":input not supported in selector-native" ) ;
2479+ }
2480+
2481+ option . setAttribute ( "test" , "" ) ;
2482+ assert . ok ( jQuery . find . matchesSelector ( option , "[id=option1a]" ) ,
2483+ "id attribute-equals identifier" ) ;
2484+ if ( QUnit . jQuerySelectors ) {
2485+ assert . ok ( jQuery . find . matchesSelector ( option , "[id*=option1][type!=checkbox]" ) ,
2486+ "attribute-not-equals identifier" ) ;
2487+ } else {
2488+ assert . ok ( "skip" , "[key!=value] not supported in selector-native" ) ;
2489+ }
2490+ assert . ok ( jQuery . find . matchesSelector ( option , "[id*=option1]" ) , "attribute-contains identifier" ) ;
2491+ assert . ok ( ! jQuery . find . matchesSelector ( option , "[test^='']" ) ,
2492+ "attribute-starts-with empty string (negative)" ) ;
2493+
2494+ option . className = "=]" ;
2495+ assert . ok ( jQuery . find . matchesSelector ( option , ".\\=\\]" ) ,
2496+ "class selector with attribute-equals confusable" ) ;
2497+
2498+ assert . ok ( jQuery . find . matchesSelector ( disconnected , "div" ) , "disconnected element" ) ;
2499+ assert . ok ( jQuery . find . matchesSelector ( link , "* > *" ) , "child combinator matches in document" ) ;
2500+ assert . ok ( ! jQuery . find . matchesSelector ( disconnected , "* > *" ) , "child combinator fails in fragment" ) ;
2501+ } ) ;
2502+
2503+ QUnit . test ( "jQuery.find.matches" , function ( assert ) {
2504+ assert . expect ( 4 ) ;
2505+
2506+ var iframeChild ,
2507+ input = document . getElementById ( "text1" ) ,
2508+ div = document . createElement ( "div" ) ,
2509+ iframe = document . getElementById ( "iframe" ) ,
2510+ iframeDoc = iframe . contentDocument || iframe . contentWindow . document ;
2511+
2512+ assert . deepEqual ( jQuery . find . matches ( "input" , [ input ] ) , [ input ] ,
2513+ "jQuery.find.matches with seed of input element" ) ;
2514+ assert . deepEqual ( jQuery . find . matches ( "div" , [ div ] ) , [ div ] ,
2515+ "jQuery.find.matches with disconnected element" ) ;
2516+
2517+ iframeDoc . open ( ) ;
2518+ iframeDoc . write ( "<body><div id='foo'><div id='bar'></div></div></body>" ) ;
2519+ iframeDoc . close ( ) ;
2520+
2521+ iframeChild = iframeDoc . getElementById ( "bar" ) ;
2522+
2523+ assert . deepEqual (
2524+ jQuery . find . matches ( ":root > body > #foo > #bar" , [ iframeChild ] ) ,
2525+ [ iframeChild ] ,
2526+ "jQuery.find.matches infers context from element"
2527+ ) ;
2528+
2529+ assert . deepEqual (
2530+ jQuery . find . matches ( ":root *" , [ div , iframeChild , input ] ) ,
2531+ [ iframeChild , input ] ,
2532+ "jQuery.find.matches infers context from each seed element"
2533+ ) ;
2534+ } ) ;
2535+
2536+ QUnit [ QUnit . jQuerySelectors ? "test" : "skip" ] ( "jQuery.find.select with pre-compiled function" , function ( assert ) {
2537+ assert . expect ( 6 ) ;
2538+
2539+ supportjQuery . each ( [
2540+ "#qunit-fixture #first" ,
2541+ "ol#listWithTabIndex > li[tabindex]" ,
2542+ "#liveSpan1"
2543+ ] , function ( i , selector ) {
2544+ var compiled = jQuery . find . compile ( selector ) ;
2545+ assert . equal ( jQuery . find . select ( compiled , document ) . length ,
2546+ 1 , "Should match using a compiled selector function" ) ;
2547+ assert . equal (
2548+ jQuery . find . select ( compiled , jQuery ( "#first" ) [ 0 ] ) . length ,
2549+ 0 , "Should not match with different context" ) ;
2550+ } ) ;
2551+ } ) ;
2552+
2553+ // Internal, but we test it for backwards compatibility for edge cases
2554+ QUnit [ QUnit . jQuerySelectors ? "test" : "skip" ] ( "jQuery.find.tokenize" , function ( assert ) {
2555+ assert . expect ( 1 ) ;
2556+
2557+ var selector = "#id .class > div[prop=\"value\"] + input:nth-child(1):button, span:contains(\"Text\") ~ div:has(div:has(span)):not(.not-this.not-that > div)" ,
2558+ tokens = [
2559+ [
2560+ {
2561+ "value" : "#id" ,
2562+ "type" : "ID" ,
2563+ "matches" : [
2564+ "id"
2565+ ]
2566+ } ,
2567+ {
2568+ "value" : " " ,
2569+ "type" : " "
2570+ } ,
2571+ {
2572+ "value" : ".class" ,
2573+ "type" : "CLASS" ,
2574+ "matches" : [
2575+ "class"
2576+ ]
2577+ } ,
2578+ {
2579+ "value" : " > " ,
2580+ "type" : ">"
2581+ } ,
2582+ {
2583+ "value" : "div" ,
2584+ "type" : "TAG" ,
2585+ "matches" : [
2586+ "div"
2587+ ]
2588+ } ,
2589+ {
2590+ "value" : "[prop=\"value\"]" ,
2591+ "type" : "ATTR" ,
2592+ "matches" : [
2593+ "prop" ,
2594+ "=" ,
2595+ "value"
2596+ ]
2597+ } ,
2598+ {
2599+ "value" : " + " ,
2600+ "type" : "+"
2601+ } ,
2602+ {
2603+ "value" : "input" ,
2604+ "type" : "TAG" ,
2605+ "matches" : [
2606+ "input"
2607+ ]
2608+ } ,
2609+ {
2610+ "value" : ":nth-child(1)" ,
2611+ "type" : "CHILD" ,
2612+ "matches" : [
2613+ "nth" ,
2614+ "child" ,
2615+ "1" ,
2616+ 0 ,
2617+ 1 ,
2618+ undefined ,
2619+ "" ,
2620+ "1"
2621+ ]
2622+ } ,
2623+ {
2624+ "value" : ":button" ,
2625+ "type" : "PSEUDO" ,
2626+ "matches" : [
2627+ "button" ,
2628+ undefined
2629+ ]
2630+ }
2631+ ] ,
2632+ [
2633+ {
2634+ "value" : "span" ,
2635+ "type" : "TAG" ,
2636+ "matches" : [
2637+ "span"
2638+ ]
2639+ } ,
2640+ {
2641+ "value" : ":contains(\"Text\")" ,
2642+ "type" : "PSEUDO" ,
2643+ "matches" : [
2644+ "contains" ,
2645+ "Text"
2646+ ]
2647+ } ,
2648+ {
2649+ "value" : " ~ " ,
2650+ "type" : "~"
2651+ } ,
2652+ {
2653+ "value" : "div" ,
2654+ "type" : "TAG" ,
2655+ "matches" : [
2656+ "div"
2657+ ]
2658+ } ,
2659+ {
2660+ "value" : ":has(div:has(span))" ,
2661+ "type" : "PSEUDO" ,
2662+ "matches" : [
2663+ "has" ,
2664+ "div:has(span)"
2665+ ]
2666+ } ,
2667+ {
2668+ "value" : ":not(.not-this.not-that > div)" ,
2669+ "type" : "PSEUDO" ,
2670+ "matches" : [
2671+ "not" ,
2672+ ".not-this.not-that > div"
2673+ ]
2674+ }
2675+ ]
2676+ ] ;
2677+
2678+ assert . deepEqual ( jQuery . find . tokenize ( selector ) , tokens , "Tokenization successful" ) ;
2679+ } ) ;
0 commit comments