Skip to content
This repository has been archived by the owner on May 24, 2024. It is now read-only.

[terra-show-hide] prop to focus on the element added #3838

Merged
merged 107 commits into from
Aug 14, 2023

Conversation

adoroshk
Copy link
Contributor

@adoroshk adoroshk commented Jul 7, 2023

Summary

  • A new focusRef prop was added to pass a ref to the element that should be focused after the full text is shown.
  • A <Focuser> component has been added for cases when user needs to set focus to a text which is not normally focusable.
  • When read by screen readers, upon expanding the content the screen reader starts reading the content on the newly revealed content when the component is expanded.
  • Documentation was updated with the examples and implementation guidance.
  • A fall-back behavior for no focusRef provided by customers was preserved for passivity, however it doesn't provide full accessibility.
  • aria-controls property has been added to the ShowHide button. It contains the id of the ShowHide content <div>

Testing

This change was tested using:

  • WDIO
  • Jest
  • Visual testing (please attach a screenshot or recording)
  • Other (please describe below)
  • No tests are needed

The following specific cases has been tested with assistive technologies:

  • Microsoft Edge + JAWS, Safari, Chrome, Firefox + VO: tested for being walk-able with TAB and VO + Right/Left Arrow.
  • JAWS + Microsoft Edge: tested the show-hide content to be walk-able with Up/Down Arrow.
  • Safari + VO: tested the content to be walk-able via Up/Down Arrow.

Reviews

In addition to engineering reviews, this PR needs:

  • UX review
  • Accessibility review
  • Functional review

This PR resolves:

UXPLATFORM-9213
UXPLATFORM-9055

@adoroshk adoroshk changed the title prop to focus on the element added [terra-show-hide] prop to focus on the element added Jul 7, 2023
@adoroshk adoroshk marked this pull request as ready for review July 7, 2023 14:36
@adoroshk adoroshk requested a review from a team as a code owner July 7, 2023 14:36
@@ -97,3 +154,4 @@ ShowHide.propTypes = propTypes;
ShowHide.defaultProps = defaultProps;

export default injectIntl(ShowHide);
export { ShowHideFocuser };
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is the ShowHide component exporting the ShowHideFocuser component as well?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The ShowHideFocuser provides additional HTML structure around text to allow JAWS walk throw the text with Down Arrow. The user needs to import it along with ShowHide component from the show-hide package. Exporting ShowHideFocuser from the ShowHide.jsx allows to import it as one line with ShowHide like this:

import ShowHide, {ShowHideFocuser} from 'terra-show-hide';
similarly to how we import this:
import React, {useState} from 'react';

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we have an index.js file and do the exports over there? It feels awkward to use this component to also export a second component.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@sdadn index file added: 822fe03

ref={ref}
tabIndex={focusable ? '-1' : null}
role={focusable ? 'group' : null}
onBlur={() => setFocusable(false)}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How does the component ever get back to a focusable state? Should this not be allowed?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The only purpose of the focus in this component is to make the assistive technologies announce the text upon opening. For that we need the component to be only focus-able once, and when it looses focus - lose it forever. The only option for the component to become focus-able able again is if user closes and open it back. Does it make sense or I misunderstood the question?

@mjpalazzo mjpalazzo added ⭐ Accessibility Reviewed Accessibility has been reviewed and approved. and removed Accessibility Review Required labels Aug 10, 2023
@mjpalazzo
Copy link
Contributor

@adoroshk - Upgrading JAWS to the latest version fixed the problem I observed. :)

Comment on lines 15 to 17
afterEach(() => {
jest.restoreAllMocks();
});
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

restoreAllMocks only works with spies.

https://jestjs.io/docs/jest-object#jestrestoreallmocks

You should use resetAllMocks instead. However, that should be done once at the end in the afterAll function.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed here: aa41c4b

import React from 'react';
import ShowHideFocuser from '../../src/ShowHideFocuser';

jest.mock('uuid', () => ({ v4: () => '00000000-0000-0000-0000-000000000000' }));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

let's move this to a beforeAll function so we are setting and reseting them in the same place.

Copy link
Contributor Author

@adoroshk adoroshk Aug 11, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For some reason I can't make it work with beforeAll. I looked for examples and everything I was able to find is in the way it is in this implementation. Can we make this change separately, outside of this PR as it is the way it's done terra-wide?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's fine by me!

@@ -5,6 +5,8 @@ import ThemeContextProvider from 'terra-theme-context/lib/ThemeContextProvider';
import { mountWithIntl } from 'terra-enzyme-intl';
import ShowHide from '../../src/ShowHide';

jest.mock('uuid', () => ({ v4: () => '00000000-0000-0000-0000-000000000000' }));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This mock needs to be reset.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you get an example if it's not what's done here: aa41c4b

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm okay with doing this in a separate PR as suggested here:
https://github.com/cerner/terra-core/pull/3838/files#r1291684878

packages/terra-show-hide/package.json Outdated Show resolved Hide resolved
Comment on lines +73 to +74
- Enter key activates the disclosure control and toggles the visibility of the disclosure content.
- Space key activates the disclosure control and toggles the visibility of the disclosure content.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this correct? They both say the same thing.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I guess @mjpalazzo put it that way in purpose. He can answer that better than me.

packages/terra-show-hide/src/ShowHide.jsx Outdated Show resolved Hide resolved
packages/terra-show-hide/src/ShowHide.jsx Show resolved Hide resolved
@@ -97,3 +154,4 @@ ShowHide.propTypes = propTypes;
ShowHide.defaultProps = defaultProps;

export default injectIntl(ShowHide);
export { ShowHideFocuser };
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we have an index.js file and do the exports over there? It feels awkward to use this component to also export a second component.

packages/terra-show-hide/src/ShowHideFocuser.jsx Outdated Show resolved Hide resolved
@adoroshk
Copy link
Contributor Author

adoroshk commented Aug 11, 2023

@sdadn for some reason I can't answer to the original comment, so adding it here. Index file added for exports: 822fe03

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this can be just a .js file as we're not using any .jsx features.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh, that's right, I thought I created a .js file. Fixing it, will push a commit in a minute.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here it is: 41cac25

@github-actions github-actions bot temporarily deployed to preview-pr-3838 August 14, 2023 02:23 Destroyed
@adoroshk adoroshk merged commit ee85dd7 into main Aug 14, 2023
21 checks passed
@adoroshk adoroshk deleted the terra-show-hide-focusing branch August 14, 2023 15:13
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
📦 terra-show-hide ⭐ Accessibility Reviewed Accessibility has been reviewed and approved. ⭐ UX Reviewed UX Reviewed and approved.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

8 participants