mirror of
https://github.com/invoke-ai/InvokeAI.git
synced 2026-01-15 06:18:03 -05:00
feat(ui): iterate on model combobox (wip)
This commit is contained in:
@@ -34,6 +34,22 @@ const DefaultGroupHeaderComponent = ({ id }: { id: string }) => {
|
||||
return <Text fontWeight="bold">{id}</Text>;
|
||||
};
|
||||
|
||||
const DefaultNoOptionsFallback = () => {
|
||||
return (
|
||||
<Flex w="full" h="full" alignItems="center" justifyContent="center">
|
||||
<Text variant="subtext">No options available</Text>
|
||||
</Flex>
|
||||
);
|
||||
};
|
||||
|
||||
const DefaultNoMatchesFallback = () => {
|
||||
return (
|
||||
<Flex w="full" h="full" alignItems="center" justifyContent="center">
|
||||
<Text variant="subtext">No matching options</Text>
|
||||
</Flex>
|
||||
);
|
||||
};
|
||||
|
||||
export type PickerProps<T extends object> = {
|
||||
options: (T | Group<T>)[];
|
||||
getOptionId: (option: T) => string;
|
||||
@@ -49,15 +65,21 @@ export type PickerProps<T extends object> = {
|
||||
GroupHeaderComponent?: React.ComponentType<{ group: Group<T> }>;
|
||||
};
|
||||
|
||||
export const getRegex = (searchTerm: string) =>
|
||||
new RegExp(
|
||||
searchTerm
|
||||
.trim()
|
||||
.replace(/[-[\]{}()*+!<=:?./\\^$|#,]/g, '')
|
||||
.split(' ')
|
||||
.join('.*'),
|
||||
'gi'
|
||||
);
|
||||
export const getRegex = (searchTerm: string) => {
|
||||
const terms = searchTerm
|
||||
.trim()
|
||||
.replace(/[-[\]{}()*+!<=:?./\\^$|#,]/g, '')
|
||||
.split(' ')
|
||||
.filter((term) => term.length > 0);
|
||||
|
||||
if (terms.length === 0) {
|
||||
return new RegExp('', 'gi');
|
||||
}
|
||||
|
||||
// Create positive lookaheads for each term - matches in any order
|
||||
const pattern = terms.map((term) => `(?=.*${term})`).join('');
|
||||
return new RegExp(`${pattern}.+`, 'i');
|
||||
};
|
||||
|
||||
const getFirstOption = <T extends object>(options: (T | Group<T>)[]): T | undefined => {
|
||||
const firstOptionOrGroup = options[0];
|
||||
@@ -121,8 +143,8 @@ export const Picker = typedMemo(<T extends object>(props: PickerProps<T>) => {
|
||||
handleRef,
|
||||
isMatch,
|
||||
getIsDisabled,
|
||||
noMatchesFallback,
|
||||
noOptionsFallback,
|
||||
noMatchesFallback = <DefaultNoMatchesFallback />,
|
||||
noOptionsFallback = <DefaultNoOptionsFallback />,
|
||||
onClose,
|
||||
onSelect,
|
||||
selectedItem,
|
||||
|
||||
@@ -216,12 +216,10 @@ const MainModelPicker = memo(() => {
|
||||
getOptionId={getOptionId}
|
||||
onSelect={onSelect}
|
||||
selectedItem={modelConfig}
|
||||
getIsDisabled={getIsDisabled}
|
||||
// getIsDisabled={getIsDisabled}
|
||||
isMatch={isMatch}
|
||||
OptionComponent={PickerItemComponent}
|
||||
GroupHeaderComponent={PickerGroupHeaderComponent}
|
||||
noOptionsFallback={<Text>{t('common.noOptions')}</Text>}
|
||||
noMatchesFallback={<Text>{t('common.noMatches')}</Text>}
|
||||
/>
|
||||
</PopoverBody>
|
||||
</PopoverContent>
|
||||
@@ -233,7 +231,7 @@ MainModelPicker.displayName = 'MainModelPicker';
|
||||
const PickerGroupHeaderComponent = memo(
|
||||
({ group }: { group: Group<AnyModelConfig, { name: string; description: string }> }) => {
|
||||
return (
|
||||
<Flex flexDir="column">
|
||||
<Flex flexDir="column" ps={8}>
|
||||
<Text fontSize="sm" fontWeight="semibold">
|
||||
{group.data.name}
|
||||
</Text>
|
||||
@@ -276,18 +274,11 @@ const BASE_KEYWORDS: { [key in BaseModelType]?: string[] } = {
|
||||
|
||||
const isMatch = (model: AnyModelConfig, searchTerm: string) => {
|
||||
const regex = getRegex(searchTerm);
|
||||
const bases = BASE_KEYWORDS[model.base] ?? [model.base];
|
||||
const testString =
|
||||
`${model.name} ${bases.join(' ')} ${model.type} ${model.description ?? ''} ${model.format}`.toLowerCase();
|
||||
|
||||
if (
|
||||
model.name.toLowerCase().includes(searchTerm) ||
|
||||
regex.test(model.name) ||
|
||||
(BASE_KEYWORDS[model.base] ?? [model.base]).some((kw) => kw.toLowerCase().includes(searchTerm) || regex.test(kw)) ||
|
||||
model.type.toLowerCase().includes(searchTerm) ||
|
||||
regex.test(model.type) ||
|
||||
(model.description ?? '').toLowerCase().includes(searchTerm) ||
|
||||
regex.test(model.description ?? '') ||
|
||||
model.format.toLowerCase().includes(searchTerm) ||
|
||||
regex.test(model.format)
|
||||
) {
|
||||
if (testString.includes(searchTerm) || regex.test(testString)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user