-
-
Notifications
You must be signed in to change notification settings - Fork 32.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Autocomplete] Improve popup open logic #18815
Comments
What's wrong with this behavior? |
When I switch to another tab, I expect to find my page in the exact same state that I left it when I come back. If the menu of the active element is closed, it is because I wanted it to be closed. switching a tab is not an action that should be interpreted as "the user wants the menu of the active element to be open". It's confusing and so it's bad UX. |
@Janpot One more question. Do you want to popup to open on keyboard focus (not taking the mouse into account)? For instance, when using Tab to navigate the page. |
edit Actually, scratch that, I'm 5 minutes further and I already changed my mind. Need to think more about this. Maybe it should behave more like a button that opens a modal. You wouldn't want the button to open the modal when tab navigating to it. I feel like when using tab I'm just navigating around, to get to the component I want to manipulate. It feels a bit intrusive when that starts popping up menus of elements that I want to skip. Possibly menus that cover op the element I'm trying to navigate to. |
@oliviertassinari How about:
That seems to align with https://webaim.org/techniques/keyboard/ Probably something to look into as well: I was checking how edit |
Set
Duplicate of another issue, fixed in master. |
If I go by the demo, that also disables it on click, so not an option.
Almost, the native select can also select options with spacebar after it is opened. The simple select can't. |
@Janpot So you are looking for the same default behavior as react-select?
This is macOS specific, it won't happen on Linux nor Windows. We decided to go against it: #18754 (comment). |
I think that a good solution would be to add a second |
I'm checking their docs pages and they open on click but not on keyboard focus, they also don't open menu for an active control after switching tabs. so wrt to this behavior, yes. I also think this would be the most sensible default for material-ui. I saw they also don't allow typing a space in an empty control, wrt to that behavior, no. |
@Janpot Would the reason approach work for you? |
Yes that would probably work if I can differentiate between an actual mouse click and another focus event. You don't agree that the current behavior is not ideal accessibility-wise? |
I believe the current logic will allow the make a difference between a focus and a touch/mouse click. It seems that the Autocomplete behaves like the google.com's search, so I don't think that it's very important. |
For me google.com's search doesn't open when I move keyboard focus to it. Neither does it open when it's active and I switch tabs. It does however also not open before I start typing, even when I click it.
I'm specifically referring to focus navigation:
Point being that it's hard to predict where focus will land if a menu is covering some of those elements where focus may land. Anyway, not that important to me 🙂. If I can implement it in userland that's fine, I just disagree with the default. |
Right, you need to fill in a value in the search bar at the top of the page to get the Google's suggestions. It's only then that you will get a display of the popup on focus and an open back behavior when switching tabs. I'm not sure to follow the focus covering issue. The popup should only open if the input is the active element. Does it behave differently in your case? Yes, I would like to get a couple of more user's feedback before we change this aspect. |
oh ok, I was testing the one in the middle of the page when there's no search results, that one seems to behave differently. In any case, I can't get that google box you are looking at in the same state as the matui one (active but closed popup) so I can't compare the tab switching behavior. Which ultimately is the main problem I'd like to solve, the keyboard accessibility is way low on my priority list. However, the gmail searchbar has a autocomplete which can be closed while still staying active, and I can confirm it doesn't open when switching tabs. neither does it open for me on keyboard focus. Edit: Ok, I think I see now, you can look at it as a textfield with a menu. or as a select component with a search box. |
This comment has been minimized.
This comment has been minimized.
@oliviertassinari could the following strategy work? |
@Janpot We have handled tab switch at two occasions in the past:
But with more hindsight, I'm not sure what should be the expected behavior for the Autocomplete. Google's product seems to be highly inconsistent with this, it's almost like the behavior inherits from other decisions, the fruit of chance. |
@oliviertassinari Ok, I think I have a solution: https://codesandbox.io/s/material-demo-ofp6l |
@Janpot Great. I think that we should wait. However, the reason argument could move forward. I think that we can leave this issue open until somebody else faces the problem and needs it. |
This is browser behavior though. When leaving the tab everything gets blurred. When you tab back focus events get fired again This should not be applied to the autocomplete only. Every component doing "something" when focused would need this fix. Considering how |
@eps1lon His sounds like a great plan 👍. I have noticed that Chrome autocomplete and autofill list boxes behave the same way. One note regarding the prop, if we change the default to true, then we should change the prop name |
Think I might give this a go, read through the whole thing and from what I've understood I just need to change |
@haseebdaone This is not a one-line change, it would have had the "good first issue" tag if it was the case. |
@oliviertassinari If you don't mind me asking what other changes are needed? |
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
@haseebdaone See: #18815 (comment) |
@haseebdaone I had a closer look at the changes. I think that a change, in this order, will solve our problem. Note that the tests will also need to be updated :) diff --git a/docs/src/pages/components/autocomplete/GoogleMaps.tsx b/docs/src/pages/components/autocomplete/GoogleMaps.tsx
index 516010ff4..ac8ef4e60 100644
--- a/docs/src/pages/components/autocomplete/GoogleMaps.tsx
+++ b/docs/src/pages/components/autocomplete/GoogleMaps.tsx
@@ -109,7 +109,6 @@ export default function GoogleMaps() {
autoComplete
includeInputInList
freeSolo
- disableOpenOnFocus
renderInput={params => (
<TextField
{...params}
diff --git a/docs/src/pages/components/autocomplete/Playground.tsx b/docs/src/pages/components/autocomplete/Playground.tsx
index c3cae2e6f..874f43bdf 100644
--- a/docs/src/pages/components/autocomplete/Playground.tsx
+++ b/docs/src/pages/components/autocomplete/Playground.tsx
@@ -88,10 +88,10 @@ export default function Playground() {
/>
<Autocomplete
{...defaultProps}
- id="disable-open-on-focus"
- disableOpenOnFocus
+ id="open-on-focus"
+ openOnFocus
renderInput={params => (
- <TextField {...params} label="disableOpenOnFocus" margin="normal" fullWidth />
+ <TextField {...params} label="openOnFocus" margin="normal" fullWidth />
)}
/>
<Autocomplete
diff --git a/packages/material-ui-lab/src/Autocomplete/Autocomplete.js b/packages/material-ui-lab/src/Autocomplete/Autocomplete.js
index 463ff0f2f..fd0097cdf 100644
--- a/packages/material-ui-lab/src/Autocomplete/Autocomplete.js
+++ b/packages/material-ui-lab/src/Autocomplete/Autocomplete.js
@@ -252,7 +252,6 @@ const Autocomplete = React.forwardRef(function Autocomplete(props, ref) {
disableCloseOnSelect = false,
disabled = false,
disableListWrap = false,
- disableOpenOnFocus = false,
disablePortal = false,
filterOptions,
filterSelectedOptions = false,
@@ -276,6 +275,7 @@ const Autocomplete = React.forwardRef(function Autocomplete(props, ref) {
onInputChange,
onOpen,
open,
+ openOnFocus = false,
openText = 'Open',
options,
PaperComponent = Paper,
@@ -566,10 +566,6 @@ Autocomplete.propTypes = {
* If `true`, the list box in the popup will not wrap focus.
*/
disableListWrap: PropTypes.bool,
- /**
- * If `true`, the popup won't open on input focus.
- */
- disableOpenOnFocus: PropTypes.bool,
/**
* Disable the portal behavior.
* The children stay within it's parent DOM hierarchy.
@@ -691,6 +687,10 @@ Autocomplete.propTypes = {
* Control the popup` open state.
*/
open: PropTypes.bool,
+ /**
+ * If `true`, the popup will open on input focus.
+ */
+ openOnFocus: PropTypes.bool,
/**
* Override the default text for the *open popup* icon button.
*
diff --git a/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.d.ts b/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.d.ts
index e616b2b1a..81db8c032 100644
--- a/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.d.ts
+++ b/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.d.ts
@@ -69,10 +69,6 @@ export interface UseAutocompleteCommonProps<T> {
* If `true`, the list box in the popup will not wrap focus.
*/
disableListWrap?: boolean;
- /**
- * If `true`, the popup won't open on input focus.
- */
- disableOpenOnFocus?: boolean;
/**
* A filter function that determines the options that are eligible.
*
@@ -154,6 +150,10 @@ export interface UseAutocompleteCommonProps<T> {
* Control the popup` open state.
*/
open?: boolean;
+ /**
+ * If `true`, the popup will open on input focus.
+ */
+ openOnFocus?: boolean;
/**
* Array of options.
*/
diff --git a/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.js b/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.js
index 3c01bb4b3..bb08631b4 100644
--- a/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.js
+++ b/packages/material-ui-lab/src/useAutocomplete/useAutocomplete.js
@@ -1,7 +1,7 @@
/* eslint-disable no-constant-condition */
import React from 'react';
import PropTypes from 'prop-types';
-import { setRef, useEventCallback, useControlled, ownerDocument } from '@material-ui/core/utils';
+import { setRef, useEventCallback, useControlled } from '@material-ui/core/utils';
// https://stackoverflow.com/questions/990904/remove-accents-diacritics-in-a-string-in-javascript
// Give up on IE 11 support for this feature
@@ -86,12 +86,12 @@ export default function useAutocomplete(props) {
autoSelect = false,
blurOnSelect = false,
clearOnEscape = false,
+ componentName = 'useAutocomplete',
debug = false,
defaultValue = props.multiple ? [] : null,
disableClearable = false,
disableCloseOnSelect = false,
disableListWrap = false,
- disableOpenOnFocus = false,
filterOptions = defaultFilterOptions,
filterSelectedOptions = false,
freeSolo = false,
@@ -105,13 +105,13 @@ export default function useAutocomplete(props) {
multiple = false,
onChange,
onClose,
- onOpen,
onInputChange,
+ onOpen,
open: openProp,
+ openOnFocus = false,
options,
selectOnFocus = !props.freeSolo,
value: valueProp,
- componentName = 'useAutocomplete',
} = props;
const [defaultId, setDefaultId] = React.useState();
@@ -655,7 +655,7 @@ export default function useAutocomplete(props) {
const handleFocus = event => {
setFocused(true);
- if (!disableOpenOnFocus && !ignoreFocus.current) {
+ if (openOnFocus && !ignoreFocus.current) {
handleOpen(event);
}
};
@@ -692,10 +692,6 @@ export default function useAutocomplete(props) {
}
if (newValue === '') {
- if (disableOpenOnFocus) {
- handleClose(event);
- }
-
if (!disableClearable && !multiple) {
handleValue(event, null);
}
@@ -783,8 +779,7 @@ export default function useAutocomplete(props) {
};
const handleInputMouseDown = event => {
- const doc = ownerDocument(inputRef.current);
- if (inputValue === '' && (!disableOpenOnFocus || inputRef.current === doc.activeElement)) {
+ if (inputValue === '') {
handlePopupIndicator(event);
}
};
@@ -968,10 +963,6 @@ useAutocomplete.propTypes = {
* If `true`, the list box in the popup will not wrap focus.
*/
disableListWrap: PropTypes.bool,
- /**
- * If `true`, the popup won't open on input focus.
- */
- disableOpenOnFocus: PropTypes.bool,
/**
* A filter function that determins the options that are eligible.
*
@@ -1051,6 +1042,10 @@ useAutocomplete.propTypes = {
* Control the popup` open state.
*/
open: PropTypes.bool,
+ /**
+ * If `true`, the popup will open on input focus.
+ */
+ openOnFocus: PropTypes.bool,
/**
* Array of options.
*/ |
I'll give this a go |
Current Behavior 😯
When an
Autocomplete
is active and I switch tabs, the menu is opened when I come backExpected Behavior 🤔
The state of the UI is the same as before I switch tabs.
Steps to Reproduce 🕹
Steps:
Context 🔦
I think we're hitting the same as https://stackoverflow.com/questions/10657176/changing-browser-tabs-undesirably-fires-the-focus-event-especially-in-google-ch
Your Environment 🌎
The text was updated successfully, but these errors were encountered: