fix(ui): use the old combobox component for dropdowns

Closes #6011
This commit is contained in:
psychedelicious 2024-03-21 15:02:43 +11:00
parent 23606d9e83
commit 9eacc0c189
2 changed files with 64 additions and 34 deletions

View File

@ -1,24 +1,36 @@
import { CustomSelect, FormControl } from '@invoke-ai/ui-library'; import { Combobox, FormControl, Tooltip } from '@invoke-ai/ui-library';
import { createMemoizedSelector } from 'app/store/createMemoizedSelector';
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
import { useModelCustomSelect } from 'common/hooks/useModelCustomSelect'; import { useGroupedModelCombobox } from 'common/hooks/useGroupedModelCombobox';
import { useControlAdapterIsEnabled } from 'features/controlAdapters/hooks/useControlAdapterIsEnabled'; import { useControlAdapterIsEnabled } from 'features/controlAdapters/hooks/useControlAdapterIsEnabled';
import { useControlAdapterModel } from 'features/controlAdapters/hooks/useControlAdapterModel'; import { useControlAdapterModel } from 'features/controlAdapters/hooks/useControlAdapterModel';
import { useControlAdapterModels } from 'features/controlAdapters/hooks/useControlAdapterModels'; import { useControlAdapterModels } from 'features/controlAdapters/hooks/useControlAdapterModels';
import { useControlAdapterType } from 'features/controlAdapters/hooks/useControlAdapterType'; import { useControlAdapterType } from 'features/controlAdapters/hooks/useControlAdapterType';
import { controlAdapterModelChanged } from 'features/controlAdapters/store/controlAdaptersSlice'; import { controlAdapterModelChanged } from 'features/controlAdapters/store/controlAdaptersSlice';
import { selectGenerationSlice } from 'features/parameters/store/generationSlice';
import { memo, useCallback, useMemo } from 'react'; import { memo, useCallback, useMemo } from 'react';
import type { ControlNetModelConfig, IPAdapterModelConfig, T2IAdapterModelConfig } from 'services/api/types'; import { useTranslation } from 'react-i18next';
import type {
AnyModelConfig,
ControlNetModelConfig,
IPAdapterModelConfig,
T2IAdapterModelConfig,
} from 'services/api/types';
type ParamControlAdapterModelProps = { type ParamControlAdapterModelProps = {
id: string; id: string;
}; };
const selectMainModel = createMemoizedSelector(selectGenerationSlice, (generation) => generation.model);
const ParamControlAdapterModel = ({ id }: ParamControlAdapterModelProps) => { const ParamControlAdapterModel = ({ id }: ParamControlAdapterModelProps) => {
const isEnabled = useControlAdapterIsEnabled(id); const isEnabled = useControlAdapterIsEnabled(id);
const controlAdapterType = useControlAdapterType(id); const controlAdapterType = useControlAdapterType(id);
const { modelConfig } = useControlAdapterModel(id); const { modelConfig } = useControlAdapterModel(id);
const dispatch = useAppDispatch(); const dispatch = useAppDispatch();
const currentBaseModel = useAppSelector((s) => s.generation.model?.base); const currentBaseModel = useAppSelector((s) => s.generation.model?.base);
const mainModel = useAppSelector(selectMainModel);
const { t } = useTranslation();
const [modelConfigs, { isLoading }] = useControlAdapterModels(controlAdapterType); const [modelConfigs, { isLoading }] = useControlAdapterModels(controlAdapterType);
@ -42,24 +54,35 @@ const ParamControlAdapterModel = ({ id }: ParamControlAdapterModelProps) => {
[controlAdapterType, modelConfig] [controlAdapterType, modelConfig]
); );
const { items, selectedItem, onChange, placeholder } = useModelCustomSelect({ const getIsDisabled = useCallback(
(model: AnyModelConfig): boolean => {
const isCompatible = currentBaseModel === model.base;
const hasMainModel = Boolean(currentBaseModel);
return !hasMainModel || !isCompatible;
},
[currentBaseModel]
);
const { options, value, onChange, noOptionsMessage } = useGroupedModelCombobox({
modelConfigs, modelConfigs,
isLoading,
selectedModel,
onChange: _onChange, onChange: _onChange,
modelFilter: (model) => model.base === currentBaseModel, selectedModel,
getIsDisabled,
isLoading,
}); });
return ( return (
<FormControl isDisabled={!items.length || !isEnabled} isInvalid={!selectedItem || !items.length}> <Tooltip label={value?.description}>
<CustomSelect <FormControl isDisabled={!isEnabled} isInvalid={!value || mainModel?.base !== modelConfig?.base}>
key={items.length} <Combobox
selectedItem={selectedItem} options={options}
placeholder={placeholder} placeholder={t('controlnet.selectModel')}
items={items} value={value}
onChange={onChange} onChange={onChange}
noOptionsMessage={noOptionsMessage}
/> />
</FormControl> </FormControl>
</Tooltip>
); );
}; };

View File

@ -1,12 +1,12 @@
import { CustomSelect, FormControl, FormLabel } from '@invoke-ai/ui-library'; import { Combobox, FormControl, FormLabel, Tooltip } from '@invoke-ai/ui-library';
import { createMemoizedSelector } from 'app/store/createMemoizedSelector'; import { createMemoizedSelector } from 'app/store/createMemoizedSelector';
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover';
import { useModelCustomSelect } from 'common/hooks/useModelCustomSelect'; import { useGroupedModelCombobox } from 'common/hooks/useGroupedModelCombobox';
import { zModelIdentifierField } from 'features/nodes/types/common'; import { zModelIdentifierField } from 'features/nodes/types/common';
import { modelSelected } from 'features/parameters/store/actions'; import { modelSelected } from 'features/parameters/store/actions';
import { selectGenerationSlice } from 'features/parameters/store/generationSlice'; import { selectGenerationSlice } from 'features/parameters/store/generationSlice';
import { memo, useCallback } from 'react'; import { memo, useCallback, useMemo } from 'react';
import { useTranslation } from 'react-i18next'; import { useTranslation } from 'react-i18next';
import { useMainModels } from 'services/api/hooks/modelsByType'; import { useMainModels } from 'services/api/hooks/modelsByType';
import type { MainModelConfig } from 'services/api/types'; import type { MainModelConfig } from 'services/api/types';
@ -18,7 +18,12 @@ const ParamMainModelSelect = () => {
const { t } = useTranslation(); const { t } = useTranslation();
const selectedModel = useAppSelector(selectModel); const selectedModel = useAppSelector(selectModel);
const [modelConfigs, { isLoading }] = useMainModels(); const [modelConfigs, { isLoading }] = useMainModels();
const tooltipLabel = useMemo(() => {
if (!modelConfigs.length || !selectedModel) {
return;
}
return modelConfigs.find((m) => m.key === selectedModel?.key)?.description;
}, [modelConfigs, selectedModel]);
const _onChange = useCallback( const _onChange = useCallback(
(model: MainModelConfig | null) => { (model: MainModelConfig | null) => {
if (!model) { if (!model) {
@ -33,26 +38,28 @@ const ParamMainModelSelect = () => {
[dispatch] [dispatch]
); );
const { items, selectedItem, onChange, placeholder } = useModelCustomSelect({ const { options, value, onChange, placeholder, noOptionsMessage } = useGroupedModelCombobox({
modelConfigs, modelConfigs,
isLoading,
selectedModel, selectedModel,
onChange: _onChange, onChange: _onChange,
isLoading,
}); });
return ( return (
<FormControl isDisabled={!items.length} isInvalid={!selectedItem || !items.length}> <Tooltip label={tooltipLabel}>
<FormControl isDisabled={!modelConfigs.length} isInvalid={!value || !modelConfigs.length}>
<InformationalPopover feature="paramModel"> <InformationalPopover feature="paramModel">
<FormLabel>{t('modelManager.model')}</FormLabel> <FormLabel>{t('modelManager.model')}</FormLabel>
</InformationalPopover> </InformationalPopover>
<CustomSelect <Combobox
key={items.length} value={value}
selectedItem={selectedItem}
placeholder={placeholder} placeholder={placeholder}
items={items} options={options}
onChange={onChange} onChange={onChange}
noOptionsMessage={noOptionsMessage}
/> />
</FormControl> </FormControl>
</Tooltip>
); );
}; };