22
33const { isNativeElement } = require ( '../utils/is-native-element' ) ;
44const { getStaticAttrValue } = require ( '../utils/static-attr-value' ) ;
5+ const { classifyAttribute } = require ( '../utils/glimmer-attr-presence' ) ;
56
67function findAttr ( node , name ) {
78 return node . attributes ?. find ( ( a ) => a . name === name ) ;
@@ -63,22 +64,12 @@ function isDisabledFormControl(node, tag) {
6364 return false ;
6465 }
6566 const attr = findAttr ( node , 'disabled' ) ;
66- if ( ! attr ) {
67- return false ;
68- }
69- // Per docs/glimmer-attribute-behavior.md, ONLY bare-mustache boolean-false
70- // (`disabled={{false}}`) renders as omitted at runtime — concat
71- // (`disabled="{{false}}"`) and string-literal (`disabled={{"false"}}`) forms
72- // still render the attribute as present and the control IS disabled.
73- const v = attr . value ;
74- if (
75- v ?. type === 'GlimmerMustacheStatement' &&
76- v . path ?. type === 'GlimmerBooleanLiteral' &&
77- v . path . value === false
78- ) {
79- return false ;
80- }
81- return true ;
67+ // Per docs/glimmer-attribute-behavior.md (rows d3, d6 plus cross-attribute
68+ // observation on falsy-coercion), bare-mustache falsy literals on a boolean
69+ // HTML attribute cause Glimmer to omit the attribute at runtime. We use
70+ // classifyAttribute so the runtime-rendered presence drives the answer
71+ // rather than AST-presence.
72+ return classifyAttribute ( attr ) . presence === 'present' ;
8273}
8374
8475// Narrow rule-local "keyboard-focusable" check. Intentionally distinct from
@@ -98,8 +89,11 @@ function isKeyboardFocusable(node, getTextAttrValueFn) {
9889 }
9990
10091 // Any tabindex (including "-1") makes the element at least programmatically
101- // focusable — still a keyboard-trap risk under aria-hidden.
102- if ( findAttr ( node , 'tabindex' ) ) {
92+ // focusable — still a keyboard-trap risk under aria-hidden. Use
93+ // classifyAttribute so bare `{{false}}` / `{{null}}` / `{{undefined}}`
94+ // (rows t6, t7) — which Glimmer omits at runtime — are NOT treated as
95+ // having a tabindex.
96+ if ( classifyAttribute ( findAttr ( node , 'tabindex' ) ) . presence === 'present' ) {
10397 return true ;
10498 }
10599
0 commit comments