feat: add experimental transition focus manager (#29400)

Issue number: resolves #23650

---------

<!-- Please do not submit updates to dependencies unless it fixes an
issue. -->

<!-- Please try to limit your pull request to one type (bugfix, feature,
etc). Submit multiple pull requests if needed. -->

## What is the current behavior?
<!-- Please describe the current behavior that you are modifying. -->

In traditional native applications, navigation will inform screen
readers that the view has changed. This allows screen readers to focus
the correct view. In a single page app on the web, this same concept
does not exist. As a result, transitioning from Page A to Page B results
in screen reader focus remaining on Page A. This means that users who
rely on screen readers are not informed of view changes.

Currently, developers are responsible for implementing this on their
own.

## What is the new behavior?
<!-- Please describe the behavior or changes that are being added by
this PR. -->

- Introduces a new focus manager priority global config. When defined,
the app developer can specify which area of the view focus should be
moved to when the transition ends. The developer does this by specifying
areas in order of priority which allows for fallbacks in the event that
a particular UI component (such as a header) does not exist on a view.

There is some risk here by managing focus for the application. As a
result, this feature is considered experimental and disabled by default.
The team should collect feedback based on usage and enable it by default
when they feel this feature is stable enough.

## Does this introduce a breaking change?

- [ ] Yes
- [x] No

<!--
  If this introduces a breaking change:
1. Describe the impact and migration path for existing applications
below.
  2. Update the BREAKING.md file with the breaking change.
3. Add "BREAKING CHANGE: [...]" to the commit description when merging.
See
https://github.com/ionic-team/ionic-framework/blob/main/docs/CONTRIBUTING.md#footer
for more information.
-->


## Other information

<!-- Any other information that is important to this PR such as
screenshots of how the component looks before and after the change. -->

⚠️ Due to the `tsconfig.json` change, reviewers should restart the
Stencil dev server when checking out these changes locally.

Reviewers: Please test both of the test template files on physical iOS
and Android device with VoiceOver and TalkBack enabled, respectively.

Docs Link: https://github.com/ionic-team/ionic-docs/pull/3627
This commit is contained in:
Liam DeBeasi
2024-05-01 10:09:05 -04:00
committed by GitHub
parent 7c00351680
commit 5b686efc10
9 changed files with 502 additions and 2 deletions

View File

@ -395,6 +395,23 @@ ion-input input::-webkit-date-and-time-value {
}
/**
* When moving focus on page transitions we call .focus() on an element which can
* add an undesired outline ring. This CSS removes the outline ring.
* We also remove the outline ring from elements that are actively being focused
* by the focus manager. We are intentionally selective about which elements this
* applies to so we do not accidentally override outlines set by the developer.
*/
[ion-last-focus],
header[tabindex="-1"]:focus,
[role="banner"][tabindex="-1"]:focus,
main[tabindex="-1"]:focus,
[role="main"][tabindex="-1"]:focus,
h1[tabindex="-1"]:focus,
[role="heading"][aria-level="1"][tabindex="-1"]:focus {
outline: none;
}
/*
* If a popover has a child ion-content (or class equivalent) then the .popover-viewport element
* should not be scrollable to ensure the inner content does scroll. However, if the popover
* does not have a child ion-content (or class equivalent) then the .popover-viewport element