Repository navigation
[web] Hide synthetic autofill inputs from assistive technology - #195618
Conversation
There was a problem hiding this comment.
Code Review
This pull request introduces a mechanism to hide synthetic autofill elements from assistive technology in semantics mode by setting the aria-hidden attribute to 'true' and tabIndex to -1. It also adds tests to verify this behavior and ensure that these attributes are not applied when semantics are disabled. There are no review comments, and I have no feedback to provide.
|
Can you verify autofill and credential-save still work in semantics mode before landing and add it to PR description and code comments? |
Verified in Chrome with semantics on and off, before and after: credential save and autofill work the same in all four cases. Added a Verification section with all four demo links to the description, and a note in the doc comment. |
…er#195618) Fixes flutter#195174 ## Problem With semantics enabled, the web engine keeps a hidden autofill form in the page so the browser can autofill and save credentials. The synthetic inputs in that form have no label and are not hidden from assistive technology, so screen readers and checkers like axe find extra unnamed text boxes holding the user's input. The form stays in the page for the rest of the session. ## Fix In semantics mode, synthetic autofill inputs now get `aria-hidden="true"` and `tabIndex = -1` at both creation sites. Each field is already exposed through its own semantics element, browser autofill does not read ARIA, and the element being edited is never a synthetic one. Without semantics the inputs are left as they are, because password manager extensions fill them and some skip `aria-hidden` inputs. ## Demo Before: https://flutter-demo-88-before.web.app After: https://flutter-demo-88-after.web.app Type in Username and Password, then press "Inspect hidden form". Before, both hidden inputs are exposed and the accessibility tree has two unnamed text boxes. After, they are `aria-hidden` and only the two real fields are exposed. ## Verification Tested in Chrome, before and after this change, with semantics on and off: | | Semantics on | Semantics off | |---|---|---| | Before | https://flutter-demo-88-before.web.app | https://flutter-demo-88-before.web.app/?semantics=off | | After | https://flutter-demo-88-after.web.app | https://flutter-demo-88-after.web.app/?semantics=off | Type a username and password, press Sign in, which calls `TextInput.finishAutofillContext()`, and save the credential. Then reload and pick the saved credential. - Credential save: Chrome saves the typed username and password in all four cases. - Autofill: selecting the saved credential fills both Username and Password in all four cases.
Roll Flutter from fcfb4f203eae to 934720261be0 (38 revisions) flutter/flutter@fcfb4f2...9347202 2026-11-03 [email protected] Roll Skia from 5bceaa033999 to c733ad3e37cb (5 revisions) (flutter/flutter#195872) 2026-11-03 [email protected] Roll Skia from 34d2bf479385 to 5bceaa033999 (9 revisions) (flutter/flutter#195864) 2026-11-03 [email protected] fix: prefer pointer events over semantics tap for mouse clicks on web (flutter/flutter#191529) 2026-11-03 [email protected] [VPAT] Expose a semantics text field value while it is not being edited (flutter/flutter#195445) 2026-11-03 [email protected] [Impeller] Make a GL context current before constructing an AiksContext without a surface (flutter/flutter#195629) 2026-11-03 [email protected] [flutter_tools] Eliminate globals.dart from project.dart (flutter/flutter#194066) 2026-11-03 [email protected] [tool] Complete context runner elimination and migrate AppContext usages to ToolContext (flutter/flutter#190797) 2026-11-03 [email protected] [web] Unify font collections between CanvasKit and Skwasm (flutter/flutter#195539) 2026-11-03 [email protected] [Android] Replay predictive back state for retained engines (flutter/flutter#192286) 2026-11-03 [email protected] [vulkan]: Adds depth/stencil synchronization for subpasses (flutter/flutter#195689) 2026-11-03 [email protected] [web] Honor requested upscaling in instantiateImageCodecWithSize and ImageDescriptor.instantiateCodec (flutter/flutter#195836) 2026-11-03 [email protected] Roll Skia from 866b61ca92c9 to 34d2bf479385 (9 revisions) (flutter/flutter#195848) 2026-11-03 [email protected] Roll Fuchsia Test Scripts from xl1LWBuppzu-BnOzV... to B6zarykZp6PKWRueg... (flutter/flutter#195847) 2026-11-03 [email protected] Remove unused ffi (flutter/flutter#195710) 2026-11-02 [email protected] Revert: [Android] Let the raster thread use every core of a chip without little cores (flutter/flutter#195838) 2026-11-02 [email protected] Run 10 impeller iOS benchmarks as one devicelab task (flutter/flutter#195661) 2026-11-02 [email protected] Use named uniforms instead of setFloat in StretchEffect (flutter/flutter#195372) 2026-11-02 [email protected] [flutter_tools] Report when the browser disconnects during a web test run (flutter/flutter#192198) 2026-11-02 [email protected] fix: Resolve memory leak in image_list example (flutter/flutter#189526) 2026-11-02 [email protected] Only run the common local engine configurations in presubmit (flutter/flutter#195688) 2026-11-02 [email protected] Update gcloud_version to version [email protected] (flutter/flutter#195769) 2026-11-02 [email protected] [Impeller] Order the Vulkan copy-texture-to-texture layout transition after the copy (flutter/flutter#195814) 2026-11-02 [email protected] [Impeller] Order the Vulkan ResizeTexture layout transition after its blit (flutter/flutter#195721) 2026-11-02 [email protected] [web] Fix CanvasKit fragment shader uniforms being freed or mutated after recording (flutter/flutter#195718) 2026-11-02 [email protected] Roll Fuchsia Linux SDK from MqypI6RNyVZ_FLUE-... to T_-6-6X1lDMghhAvX... (flutter/flutter#195809) 2026-11-02 [email protected] [Android] Log why Impeller falls back to OpenGLES (flutter/flutter#194764) 2026-11-02 [email protected] Roll Skia from 3f35fb6e591b to 866b61ca92c9 (11 revisions) (flutter/flutter#195802) 2026-11-02 [email protected] Roll Skia from 3f35fb6e591b to 866b61ca92c9 (11 revisions) (flutter/flutter#195802) 2026-11-02 [email protected] Only run the common local engine configurations in presubmit (flutter/flutter#195688) 2026-11-02 [email protected] Balance tool_integration_tests subshards by expected duration (flutter/flutter#195628) 2026-11-02 [email protected] [web_paragraph] Map code units without a cluster to a cluster (flutter/flutter#195384) 2026-11-02 [email protected] [web] Hide synthetic autofill inputs from assistive technology (flutter/flutter#195618) 2026-11-02 [email protected] Roll Packages from 3742a4e to 3f34a6f (8 revisions) (flutter/flutter#195795) 2026-11-02 [email protected] [web] Unskip web tests that pass on CanvasKit and Skwasm: platform_view_test, route_notification_messages_test (flutter/flutter#195605) 2026-11-02 [email protected] Roll Skia from e5ad3868b8db to 3f35fb6e591b (1 revision) (flutter/flutter#195789) 2026-11-02 [email protected] Roll Skia from f5215e74aa16 to e5ad3868b8db (3 revisions) (flutter/flutter#195779) 2026-11-02 [email protected] Roll Skia from e43478a2f9f8 to f5215e74aa16 (1 revision) (flutter/flutter#195776) 2026-11-01 [email protected] Roll Fuchsia Linux SDK from kW0A0xxNkqf38ljm4... to MqypI6RNyVZ_FLUE-... (flutter/flutter#195768) If this roll has caused a breakage, revert this CL and set the roller to dry run mode using the controls here: https://autoroll.skia.org/r/flutter-packages Please CC [email protected],[email protected] on the revert to ensure that a human is aware of the problem. To file a bug in Packages: https://github.com/flutter/flutter/issues/new/choose ...
Fixes #195174
Problem
With semantics enabled, the web engine keeps a hidden autofill form in the page so the browser can autofill and save credentials. The synthetic inputs in that form have no label and are not hidden from assistive technology, so screen readers and checkers like axe find extra unnamed text boxes holding the user's input. The form stays in the page for the rest of the session.
Fix
In semantics mode, synthetic autofill inputs now get
aria-hidden="true"andtabIndex = -1at both creation sites. Each field is already exposed through its own semantics element, browser autofill does not read ARIA, and the element being edited is never a synthetic one. Without semantics the inputs are left as they are, because password manager extensions fill them and some skiparia-hiddeninputs.Demo
Before: https://flutter-demo-88-before.web.app
After: https://flutter-demo-88-after.web.app
Type in Username and Password, then press "Inspect hidden form". Before, both hidden inputs are exposed and the accessibility tree has two unnamed text boxes. After, they are
aria-hiddenand only the two real fields are exposed.Verification
Tested in Chrome, before and after this change, with semantics on and off:
Type a username and password, press Sign in, which calls
TextInput.finishAutofillContext(), and save the credential. Then reload and pick the saved credential.