Skip to content
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

Combobox selects the active value when the focus is moved away #2934

Closed
tobia opened this issue Jan 19, 2024 · 9 comments
Closed

Combobox selects the active value when the focus is moved away #2934

tobia opened this issue Jan 19, 2024 · 9 comments
Assignees

Comments

@tobia
Copy link

tobia commented Jan 19, 2024

What package within Headless UI are you using?

@headlessui/react

What version of that package are you using?

Both 1.7.18 and 0.0.0-insiders.3b961a6

What browser are you using?

Firefox, Chrome

Reproduction URL

This can be easily reproduced on the demo page: https://headlessui.com/react/combobox

Describe your issue

  1. Open the demo page https://headlessui.com/react/combobox
  2. Click on the double-arrow button to open the list.
  3. Use the keyboard to navigate the list, for instance hitting Down a couple times: this will change the active item, but not the selected item.
  4. Do *not select the item with either Enter or Click, instead use Tab to move out of the field.

Expected behaviour: the field's selected value should remain unchanged.

Actual behaviour: the item that was active in the menu gets selected as the field value.

This is particularly problematic with the new immediate option available in the insiders release, because now you can alter the field values just by Tabbing through a form.

This is because as soon as the focus enters a Combobox in immediate mode, the menu of options is made visible and the first item is automatically made active, then hitting Tab again selects the active item, thus changing the value of the field.

Proposed solution: the active item should become selected only when a specific set of events occur, namely mouse Click or Enter key.

@tobia
Copy link
Author

tobia commented Jan 29, 2024

For what it's worth, I think the two cases in combobox.tsx where the code tests for data.activationTrigger !== ActivationTrigger.Focus should be removed. I replaced both tests with false and it solved the issue without introducing any obvious bugs.

@Hassan1984
Copy link

Hassan1984 commented Feb 2, 2024

or the solution porposed here. Relates to #2932

@Barbapapazes
Copy link

Got the same issue unjs/website#285 Clearly a regression from the previous version.

@reinink reinink self-assigned this Feb 7, 2024
@reinink
Copy link
Member

reinink commented Feb 7, 2024

Hey! So the "tab to select" behavior is intended for this component. This is consistent with how other combobox libraries work, like React Aria Components, as well as with the native <datalist> element (see here).

If you're using the new immediate prop that's available in the insiders release, it will open the combobox immediately, but it won't select the first option if you hit tab right away — that will only happen if you press the up/down arrows to select an option, or if you perform a search. Meaning if you're simply tabbing through multiple inputs in a form, the combobox should not auto select the first option.

I have tested this on the latest insiders version of both the React and Vue libraries. Here's a video demonstrating this behavior (with the immediate prop enabled):

Screen.Recording.2024-02-07.at.5.01.14.PM.mov

Going to close this one for now, since this all feels like expected behavior to me. However, if for some strange reason this isn't what you're experiencing, please provide a minimal reproduction and maybe even a video showing the issue and we can take another look 👍

@sandros94
Copy link

Just throwing my two cents here, mainly on a click navigation:

Isn't the concept of "clicking away, without explicitely selecting something" be considered as "cancel the operation"? With the current implementation it seems to me that there is no way to cancel the operation using only mouse navigation

@tobia
Copy link
Author

tobia commented Mar 22, 2024

@sandros94 I agree 100%. Which is the reason I'm using the patch I outlined in the 2nd post of this issue.

@reinink In addition to the point above, I was seeing a worse behaviour, because I'm loading the list of suggestions on the fly when the user focuses the field.

What happened was:

  • the user focuses the field, eg. using Tab;
  • I show the menu with a Loading spinner and issue a fetch call with an empty search string;
  • the backend returns the first 20 results without filtering, which I show in the menu;
  • Combobox auto-selects the first result; (barely a second has gone by since the initial focus)
  • the user keeps tabbing away, but that action confirms the selected entry (which was never explicitly selected by the user) thus changing the field value.

Would it be possible to have my patch above as a toggle prop? Would you accept a pull requests that adds the prop?

@Fabioni
Copy link

Fabioni commented Mar 22, 2024

this behavior is reasonable in some cases but unreasonable in others, so please give us an option to deactivate it. Clicking away should be aborting the selection.

@reinink
Copy link
Member

reinink commented Mar 25, 2024

@sandros94 @tobia @Fabioni Hey! So just looking at this issue again I am realizing that I never mentioned the nullable prop, which does allow you to click away without having the combobox automatically select the first option.

You can read more about this in my comment here: #2932 (comment)

I think this will solve the issue for you. Right now, by default, the Combobox requires that a value is set, which is why it auto selects the first item if no other value is set already, however the nullable prop allows you to get around this.

We're actually considering making this the default behavior in Headless UI v2, although that's not a guarantee yet.

Hope that helps! 🙏

@reinink
Copy link
Member

reinink commented Apr 2, 2024

Hey folks! Just wanted to let you know that the upcoming v2 release is going to make the combobox "nullable by default". You can read more about this change in #3064.

Thanks for sharing all this feedback! 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

6 participants