-
Notifications
You must be signed in to change notification settings - Fork 4.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
CustomSelectControl
: explore ariakit refactor
#55234
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
To note, this is just temporary CSS added from the Ariakit example.
const { label, onChange, options } = props; | ||
|
||
const store = Ariakit.useSelectStore( { | ||
setValue: ( value ) => onChange?.( value ), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Our current CustomSelectControl
expects an object to be returned via the onChange
event:
gutenberg/packages/components/src/custom-select-control/index.js
Lines 100 to 107 in 887cf3d
} = useSelect( { | |
initialSelectedItem: items[ 0 ], | |
items, | |
itemToString, | |
onSelectedItemChange, | |
...( typeof _selectedItem !== 'undefined' && _selectedItem !== null | |
? { selectedItem: _selectedItem } | |
: undefined ), |
Which is managed by useSelect
; part of the package downshift
.
In Ariakit, setValue
appears to be what we'd use in lieu of useSelect
, but value
/setValue
expect a string (or an array of strings for multi-select).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It appears that the object passed to onSelectItemChange
has the following structure:
{
selectedItem: "Curium",
type: "__item_click__",
highlightedIndex: -1,
isOpen: false,
inputValue: "",
}
I'm not sure if all the elements in this structure are part of the public API. The type
value, in particular, seems obscure. I'm also unsure about the meaning of highlightedIndex
, as it always appears to be -1
.
Regardless, everything except for type
can be readily accessed from within the setValue
callback. You can use store.getState()
in this context as well:
const store = useSelectStore({
async setValue(selectedItem) {
if (!onChange) return;
// Executes the logic in a microtask after the popup is closed. This might not be necessary.
// This is simply to ensure the isOpen state matches that in Downshift.
await Promise.resolve();
const state = store.getState();
const changeObject = {
selectedItem,
type: "__item_click__",
highlightedIndex: state.renderedItems.findIndex((item) => item.value === selectedItem),
isOpen: state.open,
inputValue: "",
};
onChange(changeObject);
},
});
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you for this! We finally have gotten a chance to try this out. 🙂
What?
WIP
Tracked in #55023
Why?
How?
CustomSelectControl
CustomSelectControl
children
for more flexibility and customizationTesting Instructions
Testing Instructions for Keyboard
Screenshots or screencast