Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions packages/react-aria-components/test/ComboBox.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -798,6 +798,30 @@ describe('ComboBox', () => {
expect(comboboxTester.combobox).toHaveValue('Test');
});

it.each(['{Escape}', '{Enter}', '{Tab}'])('should preserve multi-select value with custom input on %s', async (key) => {
let {container, queryByRole} = render(
<TestComboBox
selectionMode="multiple"
allowsCustomValue
defaultValue={['1', '2']}
defaultInputValue="" />
);
let comboboxTester = testUtilUser.createTester('ComboBox', {root: container});
let value = container.querySelector('.react-aria-ComboBoxValue');

expect(value).toHaveTextContent('Cat and Dog');

await user.tab();
await user.keyboard('Den');
expect(comboboxTester.combobox).toHaveValue('Den');

await user.keyboard(key);

expect(queryByRole('listbox')).toBeNull();
expect(comboboxTester.combobox).toHaveValue('Den');
expect(value).toHaveTextContent('Cat and Dog');
});

it('should allow the user to deselect items with keyboard when multiselect (uncontrolled)', async () => {
let onChange = jest.fn();
let {container} = render(<TestComboBox defaultValue={['1', '2']} selectionMode="multiple" onChange={onChange} />);
Expand Down
12 changes: 9 additions & 3 deletions packages/react-stately/src/combobox/useComboBoxState.ts
Original file line number Diff line number Diff line change
Expand Up @@ -147,8 +147,6 @@ export interface ComboBoxStateOptions<T, M extends SelectionMode = 'single'> ext
shouldCloseOnBlur?: boolean
}

const EMPTY_VALUE: Key[] = [];

/**
* Provides state management for a combo box component. Handles building a collection
* of items from props and manages the option selection state of the combo box. In addition, it tracks the input value,
Expand Down Expand Up @@ -426,7 +424,15 @@ export function useComboBoxState<T extends object, M extends SelectionMode = 'si
};

let commitCustomValue = () => {
let value = selectionMode === 'multiple' ? EMPTY_VALUE : null;
if (selectionMode === 'multiple') {
// In multi-select mode, the input's custom text is independent from the selected items.
// Closing or committing the field should not clear the existing selection.
setLastValue(inputValue);
closeMenu();
return;
}

let value = null;
lastValueRef.current = value as any;
setValue(value);
closeMenu();
Expand Down
Loading