Create New
It would be really cool if there were no result, just as it is possible to render Command.Empty there was also a Command.Create that could render a selected Item with the message Create new "${seach}".
I tried to do this, however, the Command.Item is rendered null when there are no filtered results.
https://github.com/pacocoursey/cmdk/blob/a7c974083d8b201f39dc5a340a65ae8472781574/cmdk/src/index.tsx#L603
Como seria legal que fosse
Proposal 1
<Command>
<Command.Input />
<Command.List>
<Command.Item>Apple</Command.Item>
<Command.Item create>Create New</Command.Item>
</Command.List>
</Command>
Command.Item create would only be displayed when the filter count was 0 (like Command.Empty).
Proposal 2
<Command>
<Command.Input />
<Command.List>
<Command.Item>Apple</Command.Item>
<Command.Create>Create New</Command.Create>
</Command.List>
</Command>
Command.Create would only be displayed when the filter count was 0 (like Command.Empty).
Hi.
Have you tried rendering a Command.Item where the value is the current input value?
<Command>
<Command.Input value={inputValue} onChange={e => setInputValue(e.target.value)} />
<Command.List>
<Command.Item value={inputValue} onSelect={createNew}>
Create new {inputValue}
</Command.Item>
</Command.List>
</Command>
This way it should always match the input query and even show up when no other results are matching.
You may also wish to use the (advanced) useCommandState hook documented here:
const search = useCommandState((state) => state.search)
const isEmpty = useCommandState((state) => state.filtered.count === 0)
You may also wish to use the (advanced)
useCommandStatehook documented here:const search = useCommandState((state) => state.search) const isEmpty = useCommandState((state) => state.filtered.count === 0)
I tried that way, but I couldn't render the Command.Item anyway.
Have you tried rendering a Command.Item where the value is the current input value?
I'll test this approach.
@raunofreiberg it worked, however when I search for something that ends with a space, the count goes to 0, thus removing the create new button.
So a strange behavior is when I search for a compound name it keeps blinking every space. Example:
"rauno" = true
"rauno " = false
"rauno f" = true
I'm currently in a similar situation, where I have to implement several selectable items that should be displayed once there are no other matching items.
I have tried using the current search value from the state hook, managed to solve the problem mentioned here before but there was another flaw I couldn't figure out yet.
const search = useCommandState((state) => state.search);
return <Command.Item value={`create:${search}:`}>...</Command.Item>;
As you can see I added a character at the end of the current search value when using it as a value for the Item. This solves the issues described by @emersonlaurentino and makes the Item match even with spaces at the end.
With this solution (and any of the other I've tried so far too be honest) however, two problems remain:
-
While entering new characters in the input,
filteredjumps randomly between{ count: 1, items: {}, groups: {} }and{ count: 0, items: {}, groups: {} }. Whencountis 0 it will show theCommand.Emptyeven though it still renders the dynamic item just fine. When removing characters, the count stays 1 the whole time. -
If (for some reason) I repeat the same character a bunch of times, the whole tab eventually crashes. For my 16GB RAM M1 Pro and the newest Firefox version, entering
a~30 times did the trick, no matter how much I waited between the keypresses. No errors in the console or anything and I don't encounter this issue without a "dynamic" item.
Any updates on this? @vainamov even with your suggested solution, the empty screen keeps popping up with a space
It's the third time this week I've encountered this problem and I still have no good solution in mind. Sometimes it just works, sometimes it doesn't.
Got this working using:
<Command
filter={(item, query) => {
if (item === "+create+") {
return 1;
}
if (item.toLowerCase().includes(query.trim().toLowerCase())) {
return 1;
}
return 0;
}}
>
and
const CommandCreateItem = ({ onSelect }: { onSelect: (value: string) => void }) => {
const query = useCommandState((state) => state.search);
if (!query || !onCreate) return null;
return (
<CommandItem
forceMount
value="+create+"
onSelect={() => onSelect(query)}
>
<MdAdd className="mr-2" /> {query}
</CommandItem>
);
});
This definitely should be part of the lib.
I'm also having this issue. Passing search as the value causes React 18 to freak out with too many state changes. Ironically, that only happens inside of <Command.Empty> - the one inside List doesn't seem to mind.
If I create a new component without using Command.Item then keyboard navigation breaks.
Has anyone managed to get this working?
cah4a's resolution overrides the filtering - and I don't want that.