React-modal: ReactModal focuses on last input/button when modal closes

Created on 16 Aug 2018  路  6Comments  路  Source: reactjs/react-modal

Summary:

When the modal is closed it focuses on the last focused input field/button. This is unexpected and not clearly documented. I had a button that was only visible when focusing on a particular element using a CSS transform. Focusing on the input field caused it's container to scroll to the button which caused the CSS transform to hide the button on focus.

Steps to reproduce:

  1. Code for react modal component is used by a stateful component that will open model.
  2. In same stateful component have another component that uses a CSS transition on hover to show a button to open the modal.
  3. On hover to view the button click on the button and the modal will open.
  4. Closing the modal will cause the hidden button to always be displayed.
  5. Hovering over the component will cause the button to be hidden.

With example

  1. Go to https://codesandbox.io/s/74x8ynqr6q
  2. Hover over the box with the red border
  3. Click on the button to open react modal
  4. Close the modal

Results: The CSS transformation is no longer in its original state. The focus is now placed on the button which caused the container to scroll to the button. Hovering over it hides the button and reveals whatever is below. In my case there was nothing below the buttons.

Expected behavior:

Modal will close without restoring focus on last focused input field / button.

Link to example of issue:

https://codesandbox.io/s/74x8ynqr6q

Additional notes:

When I hover over the menu the visible icon scrolls out of view and a button to open a modal scrolls into view. When clicking on the button it brings up the react-modal. When the react modal is closed the icon is no longer visible though the button to open the modal is visible. The CSS transformation now shows nothing when hovering over the menu.

ReactModal is placing focus on the hidden button causing the view of the menu to focus on the wrong thing in it's initial state.

bug

Most helpful comment

would the shouldReturnFocusAfterClose prop fix your problem?

http://reactcommunity.org/react-modal/#usage

All 6 comments

I found a work around to this. In the function that gets called onClick I blur off of the input field/button before opening the modal and it appears to have solved the issue.

<button onClick={ (e) => {
      e.currentTarget.blur();
      props.openModal()
  }}> Open Modal </button>

would the shouldReturnFocusAfterClose prop fix your problem?

http://reactcommunity.org/react-modal/#usage

@mattlub yeah that would work great.

@trevlar Thanks for reporting this issue and the example. I'll try to find sometime to debug this.

@mattlub Thanks for the help.

react-modal relies on the last document.activeElement to know which element it should give back focus. Ideally, the expected behaviour should be "Open React Modal" button to be the last active element.

Firefox and Safari have the same behaviour - they don't set the button as the active element after click on it.
Chrome will actually focus the button when clicked.
IE and Edge - needs testing.

  openModal = () => {
    debugger;
    document.activeElement; // to make it easy to inspect.
    this.setState({ modalOpen: true });
  };

After changing the openModal method, you can step through to see which element has been the last element on the document.activeElement.

Using the keyboard to navigate will produce the expected behaviour on all browsers.

Safari: Version 11.1.2 (13605.3.8)
Firefox: 61.0.2 (64-bit)
Chrome: Version 68.0.3440.106 (Official Build) (64-bit)

Was this page helpful?
0 / 5 - 0 ratings

Related issues

yaoyao1024 picture yaoyao1024  路  3Comments

gavmck picture gavmck  路  3Comments

claydiffrient picture claydiffrient  路  4Comments

jrock17 picture jrock17  路  4Comments

davidmfoley picture davidmfoley  路  3Comments