Skip to content

Commit 0fb93ab

Browse files
committed
main - eedc5a6 fix(aria/combobox): readonly behavior (#32169)
1 parent 7ce9d48 commit 0fb93ab

26 files changed

Lines changed: 402 additions & 66 deletions

docs-content/examples-highlighted/aria/combobox/combobox-auto-select/combobox-auto-select-example-ts.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@
6262

6363
<span class="hljs-keyword">if</span> (comboboxRect) {
6464
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">width</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.width}</span>px`</span>;
65-
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom}</span>px`</span>;
65+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom + <span class="hljs-number">4</span>}</span>px`</span>;
6666
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">left</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.left - <span class="hljs-number">1</span>}</span>px`</span>;
6767
}
6868

docs-content/examples-highlighted/aria/combobox/combobox-examples-css.html

Lines changed: 28 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,22 +2,30 @@
22
<span class="hljs-attribute">position</span>: relative;
33
<span class="hljs-attribute">width</span>: <span class="hljs-number">300px</span>;
44
<span class="hljs-attribute">display</span>: flex;
5-
<span class="hljs-attribute">overflow</span>: hidden;
65
<span class="hljs-attribute">flex-direction</span>: column;
76
<span class="hljs-attribute">border</span>: <span class="hljs-number">1px</span> solid <span class="hljs-built_in">var</span>(--mat-sys-outline);
87
<span class="hljs-attribute">border-radius</span>: <span class="hljs-built_in">var</span>(--mat-sys-corner-extra-small);
98
}
109

11-
<span class="hljs-selector-class">.example-combobox-container</span><span class="hljs-selector-pseudo">:has</span>(<span class="hljs-selector-class">.example-combobox-input</span><span class="hljs-selector-attr">[aria-expanded=<span class="hljs-string">&#x27;true&#x27;</span>]</span>) {
12-
<span class="hljs-attribute">border-bottom-right-radius</span>: <span class="hljs-number">0</span>;
13-
<span class="hljs-attribute">border-bottom-left-radius</span>: <span class="hljs-number">0</span>;
14-
}
15-
1610
<span class="hljs-selector-class">.example-combobox-input-container</span> {
1711
<span class="hljs-attribute">display</span>: flex;
18-
<span class="hljs-attribute">overflow</span>: hidden;
1912
<span class="hljs-attribute">position</span>: relative;
2013
<span class="hljs-attribute">align-items</span>: center;
14+
<span class="hljs-attribute">border-radius</span>: <span class="hljs-built_in">var</span>(--mat-sys-corner-extra-small);
15+
}
16+
17+
<span class="hljs-selector-class">.example-combobox-input</span> {
18+
<span class="hljs-attribute">border-radius</span>: <span class="hljs-built_in">var</span>(--mat-sys-corner-extra-small);
19+
}
20+
21+
<span class="hljs-selector-class">.example-combobox-input</span><span class="hljs-selector-attr">[readonly=<span class="hljs-string">&#x27;true&#x27;</span>]</span> {
22+
<span class="hljs-attribute">cursor</span>: pointer;
23+
<span class="hljs-attribute">padding</span>: <span class="hljs-number">0.7rem</span> <span class="hljs-number">1rem</span>;
24+
}
25+
26+
<span class="hljs-selector-class">.example-combobox-container</span><span class="hljs-selector-pseudo">:focus-within</span> <span class="hljs-selector-class">.example-combobox-input</span> {
27+
<span class="hljs-attribute">outline</span>: <span class="hljs-number">1.5px</span> solid <span class="hljs-built_in">var</span>(--mat-sys-primary);
28+
<span class="hljs-attribute">box-shadow</span>: <span class="hljs-number">0</span> <span class="hljs-number">0</span> <span class="hljs-number">0</span> <span class="hljs-number">4px</span> <span class="hljs-built_in">color-mix</span>(in srgb, <span class="hljs-built_in">var</span>(--mat-sys-primary) <span class="hljs-number">25%</span>, transparent);
2129
}
2230

2331
<span class="hljs-selector-class">.example-icon</span> {
@@ -35,6 +43,18 @@
3543
<span class="hljs-attribute">opacity</span>: <span class="hljs-number">0.8</span>;
3644
}
3745

46+
<span class="hljs-selector-class">.example-arrow-icon</span> {
47+
<span class="hljs-attribute">padding</span>: <span class="hljs-number">0</span> <span class="hljs-number">0.5rem</span>;
48+
<span class="hljs-attribute">position</span>: absolute;
49+
<span class="hljs-attribute">right</span>: <span class="hljs-number">0</span>;
50+
<span class="hljs-attribute">opacity</span>: <span class="hljs-number">0.8</span>;
51+
<span class="hljs-attribute">transition</span>: transform <span class="hljs-number">0.2s</span> ease;
52+
}
53+
54+
<span class="hljs-selector-class">.example-combobox-input</span><span class="hljs-selector-attr">[aria-expanded=<span class="hljs-string">&#x27;true&#x27;</span>]</span> + <span class="hljs-selector-class">.example-arrow-icon</span> {
55+
<span class="hljs-attribute">transform</span>: <span class="hljs-built_in">rotate</span>(<span class="hljs-number">180deg</span>);
56+
}
57+
3858
<span class="hljs-selector-class">.example-combobox-input</span> {
3959
<span class="hljs-attribute">width</span>: <span class="hljs-number">100%</span>;
4060
<span class="hljs-attribute">border</span>: none;
@@ -48,8 +68,7 @@
4868
<span class="hljs-attribute">margin</span>: <span class="hljs-number">0</span>;
4969
<span class="hljs-attribute">padding</span>: <span class="hljs-number">0</span>;
5070
<span class="hljs-attribute">border</span>: <span class="hljs-number">1px</span> solid <span class="hljs-built_in">var</span>(--mat-sys-outline);
51-
<span class="hljs-attribute">border-bottom-right-radius</span>: <span class="hljs-built_in">var</span>(--mat-sys-corner-extra-small);
52-
<span class="hljs-attribute">border-bottom-left-radius</span>: <span class="hljs-built_in">var</span>(--mat-sys-corner-extra-small);
71+
<span class="hljs-attribute">border-radius</span>: <span class="hljs-built_in">var</span>(--mat-sys-corner-extra-small);
5372
<span class="hljs-attribute">background-color</span>: <span class="hljs-built_in">var</span>(--mat-sys-surface);
5473
}
5574

docs-content/examples-highlighted/aria/combobox/combobox-highlight/combobox-highlight-example-ts.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@
7171

7272
<span class="hljs-keyword">if</span> (comboboxRect) {
7373
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">width</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.width}</span>px`</span>;
74-
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom}</span>px`</span>;
74+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom + <span class="hljs-number">4</span>}</span>px`</span>;
7575
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">left</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.left - <span class="hljs-number">1</span>}</span>px`</span>;
7676
}
7777

docs-content/examples-highlighted/aria/combobox/combobox-manual/combobox-manual-example-ts.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@
7171

7272
<span class="hljs-keyword">if</span> (comboboxRect) {
7373
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">width</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.width}</span>px`</span>;
74-
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom}</span>px`</span>;
74+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom + <span class="hljs-number">4</span>}</span>px`</span>;
7575
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">left</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.left - <span class="hljs-number">1</span>}</span>px`</span>;
7676
}
7777

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
<span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">ngCombobox</span> #<span class="hljs-attr">combobox</span>=<span class="hljs-string">&quot;ngCombobox&quot;</span> <span class="hljs-attr">class</span>=<span class="hljs-string">&quot;example-combobox-container&quot;</span> [<span class="hljs-attr">readonly</span>]=<span class="hljs-string">&quot;true&quot;</span>&gt;</span>
2+
<span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">class</span>=<span class="hljs-string">&quot;example-combobox-input-container&quot;</span>&gt;</span>
3+
<span class="hljs-tag">&lt;<span class="hljs-name">input</span>
4+
<span class="hljs-attr">ngComboboxInput</span>
5+
<span class="hljs-attr">class</span>=<span class="hljs-string">&quot;example-combobox-input&quot;</span>
6+
<span class="hljs-attr">placeholder</span>=<span class="hljs-string">&quot;Search...&quot;</span>
7+
[(<span class="hljs-attr">value</span>)]=<span class="hljs-string">&quot;searchString&quot;</span>
8+
/&gt;</span>
9+
<span class="hljs-tag">&lt;<span class="hljs-name">span</span> <span class="hljs-attr">class</span>=<span class="hljs-string">&quot;material-symbols-outlined example-icon example-arrow-icon&quot;</span>&gt;</span>arrow_drop_down<span class="hljs-tag">&lt;/<span class="hljs-name">span</span>&gt;</span>
10+
<span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
11+
12+
<span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">popover</span>=<span class="hljs-string">&quot;manual&quot;</span> #<span class="hljs-attr">popover</span> <span class="hljs-attr">class</span>=<span class="hljs-string">&quot;example-popover&quot;</span>&gt;</span>
13+
<span class="hljs-tag">&lt;<span class="hljs-name">ng-template</span> <span class="hljs-attr">ngComboboxPopupContainer</span>&gt;</span>
14+
<span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">ngListbox</span> <span class="hljs-attr">class</span>=<span class="hljs-string">&quot;example-listbox&quot;</span>&gt;</span>
15+
@for (option of options(); track option) {
16+
<span class="hljs-tag">&lt;<span class="hljs-name">div</span>
17+
<span class="hljs-attr">class</span>=<span class="hljs-string">&quot;example-option example-selectable example-stateful&quot;</span>
18+
<span class="hljs-attr">ngOption</span>
19+
[<span class="hljs-attr">value</span>]=<span class="hljs-string">&quot;option&quot;</span>
20+
[<span class="hljs-attr">label</span>]=<span class="hljs-string">&quot;option&quot;</span>
21+
&gt;</span>
22+
<span class="hljs-tag">&lt;<span class="hljs-name">span</span>&gt;</span>{{option}}<span class="hljs-tag">&lt;/<span class="hljs-name">span</span>&gt;</span>
23+
<span class="hljs-tag">&lt;<span class="hljs-name">span</span>
24+
<span class="hljs-attr">aria-hidden</span>=<span class="hljs-string">&quot;true&quot;</span>
25+
<span class="hljs-attr">class</span>=<span class="hljs-string">&quot;material-symbols-outlined example-icon example-selected-icon&quot;</span>
26+
&gt;</span>check&lt;/span
27+
&gt;
28+
<span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
29+
}
30+
<span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
31+
<span class="hljs-tag">&lt;/<span class="hljs-name">ng-template</span>&gt;</span>
32+
<span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
33+
<span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
<span class="hljs-comment">/**
2+
* <span class="hljs-doctag">@license</span>
3+
* Copyright Google LLC All Rights Reserved.
4+
*
5+
* Use of this source code is governed by an MIT-style license that can be
6+
* found in the LICENSE file at https://angular.dev/license
7+
*/</span>
8+
9+
<span class="hljs-keyword">import</span> {
10+
<span class="hljs-title class_">Combobox</span>,
11+
<span class="hljs-title class_">ComboboxInput</span>,
12+
<span class="hljs-title class_">ComboboxPopup</span>,
13+
<span class="hljs-title class_">ComboboxPopupContainer</span>,
14+
} <span class="hljs-keyword">from</span> <span class="hljs-string">&#x27;@angular/aria/combobox&#x27;</span>;
15+
<span class="hljs-keyword">import</span> {<span class="hljs-title class_">Listbox</span>, <span class="hljs-title class_">Option</span>} <span class="hljs-keyword">from</span> <span class="hljs-string">&#x27;@angular/aria/listbox&#x27;</span>;
16+
<span class="hljs-keyword">import</span> {
17+
afterRenderEffect,
18+
<span class="hljs-title class_">ChangeDetectionStrategy</span>,
19+
<span class="hljs-title class_">Component</span>,
20+
<span class="hljs-title class_">ElementRef</span>,
21+
signal,
22+
viewChild,
23+
} <span class="hljs-keyword">from</span> <span class="hljs-string">&#x27;@angular/core&#x27;</span>;
24+
<span class="hljs-keyword">import</span> {<span class="hljs-title class_">FormsModule</span>} <span class="hljs-keyword">from</span> <span class="hljs-string">&#x27;@angular/forms&#x27;</span>;
25+
26+
<span class="hljs-comment">/** <span class="hljs-doctag">@title</span> Readonly combobox. */</span>
27+
<span class="hljs-meta">@Component</span>({
28+
<span class="hljs-attr">selector</span>: <span class="hljs-string">&#x27;combobox-readonly-example&#x27;</span>,
29+
<span class="hljs-attr">templateUrl</span>: <span class="hljs-string">&#x27;combobox-readonly-example.html&#x27;</span>,
30+
<span class="hljs-attr">styleUrl</span>: <span class="hljs-string">&#x27;../combobox-examples.css&#x27;</span>,
31+
<span class="hljs-attr">imports</span>: [
32+
<span class="hljs-title class_">Combobox</span>,
33+
<span class="hljs-title class_">ComboboxInput</span>,
34+
<span class="hljs-title class_">ComboboxPopup</span>,
35+
<span class="hljs-title class_">ComboboxPopupContainer</span>,
36+
<span class="hljs-title class_">Listbox</span>,
37+
<span class="hljs-title class_">Option</span>,
38+
<span class="hljs-title class_">FormsModule</span>,
39+
],
40+
<span class="hljs-attr">changeDetection</span>: <span class="hljs-title class_">ChangeDetectionStrategy</span>.<span class="hljs-property">OnPush</span>,
41+
})
42+
<span class="hljs-keyword">export</span> <span class="hljs-keyword">class</span> <span class="hljs-title class_">ComboboxReadonlyExample</span> {
43+
popover = viewChild&lt;<span class="hljs-title class_">ElementRef</span>&gt;(<span class="hljs-string">&#x27;popover&#x27;</span>);
44+
listbox = viewChild&lt;<span class="hljs-title class_">Listbox</span>&lt;<span class="hljs-built_in">any</span>&gt;&gt;(<span class="hljs-title class_">Listbox</span>);
45+
combobox = viewChild&lt;<span class="hljs-title class_">Combobox</span>&lt;<span class="hljs-built_in">any</span>&gt;&gt;(<span class="hljs-title class_">Combobox</span>);
46+
47+
options = <span class="hljs-function">() =&gt;</span> states;
48+
searchString = <span class="hljs-title function_">signal</span>(<span class="hljs-string">&#x27;&#x27;</span>);
49+
50+
<span class="hljs-title function_">constructor</span>(<span class="hljs-params"></span>) {
51+
<span class="hljs-title function_">afterRenderEffect</span>(<span class="hljs-function">() =&gt;</span> {
52+
<span class="hljs-keyword">const</span> popover = <span class="hljs-variable language_">this</span>.<span class="hljs-title function_">popover</span>()!;
53+
<span class="hljs-keyword">const</span> combobox = <span class="hljs-variable language_">this</span>.<span class="hljs-title function_">combobox</span>()!;
54+
combobox.<span class="hljs-property">pattern</span>.<span class="hljs-title function_">expanded</span>() ? <span class="hljs-variable language_">this</span>.<span class="hljs-title function_">showPopover</span>() : popover.<span class="hljs-property">nativeElement</span>.<span class="hljs-title function_">hidePopover</span>();
55+
56+
<span class="hljs-comment">// TODO(wagnermaciel): Make this easier for developers to do.</span>
57+
<span class="hljs-variable language_">this</span>.<span class="hljs-title function_">listbox</span>()?.<span class="hljs-property">pattern</span>.<span class="hljs-property">inputs</span>.<span class="hljs-title function_">activeItem</span>()?.<span class="hljs-title function_">element</span>().<span class="hljs-title function_">scrollIntoView</span>({<span class="hljs-attr">block</span>: <span class="hljs-string">&#x27;nearest&#x27;</span>});
58+
});
59+
}
60+
61+
<span class="hljs-title function_">showPopover</span>(<span class="hljs-params"></span>) {
62+
<span class="hljs-keyword">const</span> popover = <span class="hljs-variable language_">this</span>.<span class="hljs-title function_">popover</span>()!;
63+
<span class="hljs-keyword">const</span> combobox = <span class="hljs-variable language_">this</span>.<span class="hljs-title function_">combobox</span>()!;
64+
65+
<span class="hljs-keyword">const</span> comboboxRect = combobox.<span class="hljs-property">pattern</span>.<span class="hljs-property">inputs</span>.<span class="hljs-title function_">inputEl</span>()?.<span class="hljs-title function_">getBoundingClientRect</span>();
66+
<span class="hljs-keyword">const</span> popoverEl = popover.<span class="hljs-property">nativeElement</span>;
67+
68+
<span class="hljs-keyword">if</span> (comboboxRect) {
69+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">width</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.width}</span>px`</span>;
70+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom + <span class="hljs-number">4</span>}</span>px`</span>;
71+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">left</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.left - <span class="hljs-number">1</span>}</span>px`</span>;
72+
}
73+
74+
popover.<span class="hljs-property">nativeElement</span>.<span class="hljs-title function_">showPopover</span>();
75+
}
76+
}
77+
78+
<span class="hljs-keyword">const</span> states = [<span class="hljs-string">&#x27;Option 1&#x27;</span>, <span class="hljs-string">&#x27;Option 2&#x27;</span>, <span class="hljs-string">&#x27;Option 3&#x27;</span>];

docs-content/examples-highlighted/aria/combobox/combobox-tree-auto-select/combobox-tree-auto-select-example-ts.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@
9797

9898
<span class="hljs-keyword">if</span> (comboboxRect) {
9999
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">width</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.width}</span>px`</span>;
100-
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom}</span>px`</span>;
100+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom + <span class="hljs-number">4</span>}</span>px`</span>;
101101
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">left</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.left - <span class="hljs-number">1</span>}</span>px`</span>;
102102
}
103103

docs-content/examples-highlighted/aria/combobox/combobox-tree-highlight/combobox-tree-highlight-example-ts.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@
9797

9898
<span class="hljs-keyword">if</span> (comboboxRect) {
9999
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">width</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.width}</span>px`</span>;
100-
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom}</span>px`</span>;
100+
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">top</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.bottom + <span class="hljs-number">4</span>}</span>px`</span>;
101101
popoverEl.<span class="hljs-property">style</span>.<span class="hljs-property">left</span> = <span class="hljs-string">`<span class="hljs-subst">${comboboxRect.left - <span class="hljs-number">1</span>}</span>px`</span>;
102102
}
103103

0 commit comments

Comments
 (0)