tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

nested-declarations-matching.html (6100B)


      1 <!DOCTYPE html>
      2 <title>CSS Nesting: CSSNestedDeclarations matching</title>
      3 <link rel="help" href="https://drafts.csswg.org/css-nesting-1/#nested-declarations-rule">
      4 <script src="/resources/testharness.js"></script>
      5 <script src="/resources/testharnessreport.js"></script>
      6 
      7 <style>
      8  .trailing {
      9    --x: FAIL;
     10    & { --x: FAIL; }
     11    --x: PASS;
     12  }
     13 </style>
     14 <div class=trailing></div>
     15 <script>
     16  test(() => {
     17    let e = document.querySelector('.trailing');
     18    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
     19  }, 'Trailing declarations apply after any preceding rules');
     20 </script>
     21 
     22 
     23 <style>
     24  .trailing_no_leading {
     25    & { --x: FAIL; }
     26    --x: PASS;
     27  }
     28 </style>
     29 <div class=trailing_no_leading></div>
     30 <script>
     31  test(() => {
     32    let e = document.querySelector('.trailing_no_leading');
     33    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
     34  }, 'Trailing declarations apply after any preceding rules (no leading)');
     35 </script>
     36 
     37 
     38 <style>
     39  .trailing_multiple {
     40    --x: FAIL;
     41    --y: FAIL;
     42    --z: FAIL;
     43    --w: FAIL;
     44    & { --x: FAIL; }
     45    --x: PASS;
     46    --y: PASS;
     47    & { --z: FAIL; }
     48    --z: PASS;
     49    --w: PASS;
     50  }
     51 </style>
     52 <div class=trailing_multiple></div>
     53 <script>
     54  test(() => {
     55    let e = document.querySelector('.trailing_multiple');
     56    let s = getComputedStyle(e);
     57    assert_equals(s.getPropertyValue('--x'), 'PASS');
     58    assert_equals(s.getPropertyValue('--y'), 'PASS');
     59    assert_equals(s.getPropertyValue('--z'), 'PASS');
     60    assert_equals(s.getPropertyValue('--w'), 'PASS');
     61  }, 'Trailing declarations apply after any preceding rules (multiple)');
     62 </script>
     63 
     64 
     65 <style>
     66  .trailing_specificity {
     67    --x: FAIL;
     68    :is(&, div.nomatch2) { --x: PASS; } /* Specificity: (0, 1, 1) */
     69    --x: FAIL; /* Specificity: (0, 1, 0) */
     70  }
     71 </style>
     72 <div class=trailing_specificity></div>
     73 <script>
     74  test(() => {
     75    let e = document.querySelector('.trailing_specificity');
     76    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
     77  }, 'Nested declarations rule has same specificity as outer selector');
     78 </script>
     79 
     80 
     81 <style>
     82  #nomatch, .specificity_top_level {
     83    --x: FAIL;
     84    :is(&, div.nomatch2) { --x: PASS; } /* Specificity: (0, 1, 1) */
     85    --x: FAIL; /* Specificity: (0, 1, 0). In particular, this does not have
     86               specificity like :is(#nomatch, .specificity_top_level). */
     87  }
     88 </style>
     89 <div class=specificity_top_level></div>
     90 <script>
     91  test(() => {
     92    let e = document.querySelector('.specificity_top_level');
     93    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
     94  }, 'Nested declarations rule has top-level specificity behavior');
     95 </script>
     96 
     97 
     98 <style>
     99  #nomatch, .specificity_top_level_max, div.specificity_top_level_max {
    100    --x: FAIL;
    101    :is(:where(&), div.nomatch2) { --x: FAIL; } /* Specificity: (0, 1, 1) */
    102    --x: PASS; /* Specificity: (0, 1, 1) (for div.specificity_top_level_max) */
    103  }
    104 </style>
    105 <div class=specificity_top_level_max></div>
    106 <script>
    107  test(() => {
    108    let e = document.querySelector('.specificity_top_level_max');
    109    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
    110  }, 'Nested declarations rule has top-level specificity behavior (max matching)');
    111 </script>
    112 
    113 <style>
    114  .nested_pseudo::after {
    115    --x: FAIL;
    116    @media (width > 0px) {
    117      --x: PASS;
    118    }
    119  }
    120 </style>
    121 <div class=nested_pseudo></div>
    122 <script>
    123  test(() => {
    124    let e = document.querySelector('.nested_pseudo');
    125    assert_equals(getComputedStyle(e, '::after').getPropertyValue('--x'), 'PASS');
    126  }, 'Bare declartaion in nested grouping rule can match pseudo-element');
    127 </script>
    128 
    129 <style>
    130  #nomatch, .nested_group_rule {
    131    --x: FAIL;
    132    @media (width > 0px) {
    133      --x: FAIL; /* Specificity: (0, 1, 0) */
    134    }
    135    --x: PASS;
    136  }
    137 </style>
    138 <div class=nested_group_rule></div>
    139 <script>
    140  test(() => {
    141    let e = document.querySelector('.nested_group_rule');
    142    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
    143  }, 'Nested group rules have top-level specificity behavior');
    144 </script>
    145 
    146 
    147 <style>
    148  .nested_scope_rule {
    149    div:where(&) { /* Specificity: (0, 0, 1) */
    150      --x: PASS;
    151    }
    152    @scope (&) {
    153      --x: FAIL; /* Specificity: (0, 0, 0) */
    154    }
    155  }
    156 </style>
    157 <div class=nested_scope_rule></div>
    158 <script>
    159  test(() => {
    160    let e = document.querySelector('.nested_scope_rule');
    161    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
    162  }, 'Nested @scope rules behave like :where(:scope)');
    163 </script>
    164 
    165 
    166 <style>
    167  .nested_scope_rule_trailing {
    168    div:where(&) { /* Specificity: (0, 0, 1) */
    169      --x: PASS;
    170    }
    171    @scope (&) {
    172      --ignored: 1;
    173      .ignored {}
    174      --x: FAIL; /* Specificity: (0, 0, 0) */
    175    }
    176  }
    177 </style>
    178 <div class=nested_scope_rule_trailing></div>
    179 <script>
    180  test(() => {
    181    let e = document.querySelector('.nested_scope_rule_trailing');
    182    assert_equals(getComputedStyle(e).getPropertyValue('--x'), 'PASS');
    183  }, 'Nested @scope rules behave like :where(:scope) (trailing)');
    184 </script>
    185 
    186 
    187 <style id=set_parent_selector_text_style>
    188  .set_parent_selector_text {
    189    div {
    190      color: red;
    191    }
    192    .a1 {
    193      .ignored {}
    194      color: green;
    195    }
    196  }
    197 </style>
    198 <div class=set_parent_selector_text>
    199  <div class=a1>A1</div>
    200  <div class=a2>A2</div>
    201 </div>
    202 <script>
    203  test(() => {
    204    let a1 = document.querySelector('.set_parent_selector_text > .a1');
    205    let a2 = document.querySelector('.set_parent_selector_text > .a2');
    206    assert_equals(getComputedStyle(a1).color, 'rgb(0, 128, 0)');
    207    assert_equals(getComputedStyle(a2).color, 'rgb(255, 0, 0)');
    208 
    209    let rules = set_parent_selector_text_style.sheet.cssRules;
    210    assert_equals(rules.length, 1);
    211    assert_equals(rules[0].cssRules.length, 2);
    212 
    213    let a_rule = rules[0].cssRules[1];
    214    assert_equals(a_rule.selectorText, '& .a1');
    215    a_rule.selectorText = '.a2';
    216    assert_equals(a_rule.selectorText, '& .a2');
    217 
    218    assert_equals(getComputedStyle(a1).color, 'rgb(255, 0, 0)');
    219    assert_equals(getComputedStyle(a2).color, 'rgb(0, 128, 0)');
    220  }, 'Nested declarations rule responds to parent selector text change');
    221 </script>