Files
Brandy Carney 20073e10c9 fix(angular): remove the tabindex set by routerLink from Ionic components (#29744)
Issue number: resolves #20632

---------

## What is the current behavior?
When using the `routerLink` directive in Angular, it automatically adds
`tabindex="0"` to the element. This creates issues with Ionic components
that render native button or anchor elements, as they have their own
focus management. As a result, when navigating between list items with
`routerLink` using the `Tab` key, you need to press the `Tab` key twice
to move to the next item. This problem is illustrated in the following
demo:

[![Open in
StackBlitz](https://developer.stackblitz.com/img/open_in_stackblitz.svg)](https://stackblitz.com/edit/angular-blfa7h?file=src%2Fapp%2Fexample.component.html)

Related Angular issue: https://github.com/angular/angular/issues/28345

## What is the new behavior?
Updated our `RouterLinkDelegateDirective` to check if the element using
`routerLink` is one of the following Ionic components:
`ion-back-button`, `ion-breadcrumb`, `ion-button`, `ion-card`,
`ion-fab-button`, `ion-item`, `ion-item-option`, `ion-menu-button`,
`ion-segment-button`, or `ion-tab-button`. If so, it removes the
`tabindex` attribute from the element. This allows these Ionic
components to let the native button or anchor element handle the focus.

This solution is demonstrated in the following demo:

[![Open in
StackBlitz](https://developer.stackblitz.com/img/open_in_stackblitz.svg)](https://stackblitz.com/edit/angular-blfa7h-svmguh?file=src%2Fapp%2Fexample.component.html)

> [!NOTE]
> I did not include the `ion-router-link` component in the list to
remove `tabindex` because [the router link
documentation](https://ionicframework.com/docs/api/router-link) does not
recommend using it with Angular:
>> Note: this component should only be used with vanilla and Stencil
JavaScript projects. For Angular projects, use an `<a>` and `routerLink`
with the Angular router.

## Does this introduce a breaking change?

- [ ] Yes
- [x] No

## Other information

Dev build: `8.2.7-dev.11722448707.1e8c66e6`
2024-08-08 15:02:35 +00:00
..
2024-07-24 16:23:11 -04:00
2024-07-24 16:23:11 -04:00
2024-07-24 16:23:11 -04:00

@ionic/angular

Ionic Angular specific building blocks on top of @ionic/core components.

License

Testing ng-add in ionic

  1. Pull the latest from main
  2. Build ionic/angular: npm run build
  3. Run npm link from ionic/angular/dist directory
  4. Create a blank angular project
ng new add-test
// Say yes to including the router, we need it
cd add-test
  1. To run schematics locally, we need the schematics-cli (once published, this will not be needed)
npm install @angular-devkit/schematics-cli
  1. Link @ionic/angular
npm link @ionic/angular
  1. Run the local copy of the ng-add schematic
$ npx schematics @ionic/angular:ng-add

You'll now be able to add ionic components to a vanilla Angular app setup.

Project Structure

common

This is where logic that is shared between lazy loaded and standalone components live. For example, the lazy loaded IonPopover and standalone IonPopover components extend from a base IonPopover implementation that exists in this directory.

Note: This directory exposes internal APIs and is only accessed in the standalone and src submodules. Ionic developers should never import directly from @ionic/angular/common. Instead, they should import from @ionic/angular or @ionic/angular/standalone.

standalone

This is where the standalone component implementations live. It was added as a separate entry point to avoid any lazy loaded logic from accidentally being pulled in to the final build. Having a separate directory allows the lazy loaded implementation to remain accessible from @ionic/angular for backwards compatibility.

Ionic developers can access this by importing from @ionic/angular/standalone.

src

This is where the lazy loaded component implementations live.

Ionic developers can access this by importing from @ionic/angular.