mirror of
https://github.com/invoke-ai/InvokeAI
synced 2024-08-30 20:32:17 +00:00
Merge branch 'main' into feat/onnx
This commit is contained in:
@ -20,15 +20,18 @@ const selector = createSelector(
|
||||
export default function ParamAdvancedCollapse() {
|
||||
const { activeLabel } = useAppSelector(selector);
|
||||
const shouldShowAdvancedOptions = useAppSelector(
|
||||
(state: RootState) => state.ui.shouldShowAdvancedOptions
|
||||
(state: RootState) => state.generation.shouldShowAdvancedOptions
|
||||
);
|
||||
|
||||
if (!shouldShowAdvancedOptions) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return (
|
||||
shouldShowAdvancedOptions && (
|
||||
<IAICollapse label={'Advanced'} activeLabel={activeLabel}>
|
||||
<Flex sx={{ flexDir: 'column', gap: 2 }}>
|
||||
<ParamClipSkip />
|
||||
</Flex>
|
||||
</IAICollapse>
|
||||
)
|
||||
<IAICollapse label={'Advanced'} activeLabel={activeLabel}>
|
||||
<Flex sx={{ flexDir: 'column', gap: 2 }}>
|
||||
<ParamClipSkip />
|
||||
</Flex>
|
||||
</IAICollapse>
|
||||
);
|
||||
}
|
||||
|
@ -2,28 +2,10 @@ import { RootState } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAISlider from 'common/components/IAISlider';
|
||||
import { setClipSkip } from 'features/parameters/store/generationSlice';
|
||||
import { clipSkipMap } from 'features/parameters/types/constants';
|
||||
import { useCallback, useMemo } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
export const clipSkipMap = {
|
||||
'sd-1': {
|
||||
maxClip: 12,
|
||||
markers: [0, 1, 2, 3, 4, 8, 12],
|
||||
},
|
||||
'sd-2': {
|
||||
maxClip: 24,
|
||||
markers: [0, 1, 2, 3, 5, 10, 15, 20, 24],
|
||||
},
|
||||
sdxl: {
|
||||
maxClip: 24,
|
||||
markers: [0, 1, 2, 3, 5, 10, 15, 20, 24],
|
||||
},
|
||||
'sdxl-refiner': {
|
||||
maxClip: 24,
|
||||
markers: [0, 1, 2, 3, 5, 10, 15, 20, 24],
|
||||
},
|
||||
};
|
||||
|
||||
export default function ParamClipSkip() {
|
||||
const clipSkip = useAppSelector(
|
||||
(state: RootState) => state.generation.clipSkip
|
||||
|
@ -1,23 +1,20 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAISlider from 'common/components/IAISlider';
|
||||
import { roundToMultiple } from 'common/util/roundDownToMultiple';
|
||||
import {
|
||||
canvasSelector,
|
||||
isStagingSelector,
|
||||
} from 'features/canvas/store/canvasSelectors';
|
||||
import { isStagingSelector } from 'features/canvas/store/canvasSelectors';
|
||||
import { setBoundingBoxDimensions } from 'features/canvas/store/canvasSlice';
|
||||
import { uiSelector } from 'features/ui/store/uiSelectors';
|
||||
import { memo } from 'react';
|
||||
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
[canvasSelector, isStagingSelector, uiSelector],
|
||||
(canvas, isStaging, ui) => {
|
||||
[stateSelector, isStagingSelector],
|
||||
({ canvas, generation }, isStaging) => {
|
||||
const { boundingBoxDimensions } = canvas;
|
||||
const { aspectRatio } = ui;
|
||||
const { aspectRatio } = generation;
|
||||
return {
|
||||
boundingBoxDimensions,
|
||||
isStaging,
|
||||
|
@ -1,23 +1,20 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAISlider from 'common/components/IAISlider';
|
||||
import { roundToMultiple } from 'common/util/roundDownToMultiple';
|
||||
import {
|
||||
canvasSelector,
|
||||
isStagingSelector,
|
||||
} from 'features/canvas/store/canvasSelectors';
|
||||
import { isStagingSelector } from 'features/canvas/store/canvasSelectors';
|
||||
import { setBoundingBoxDimensions } from 'features/canvas/store/canvasSlice';
|
||||
import { uiSelector } from 'features/ui/store/uiSelectors';
|
||||
import { memo } from 'react';
|
||||
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
[canvasSelector, isStagingSelector, uiSelector],
|
||||
(canvas, isStaging, ui) => {
|
||||
[stateSelector, isStagingSelector],
|
||||
({ canvas, generation }, isStaging) => {
|
||||
const { boundingBoxDimensions } = canvas;
|
||||
const { aspectRatio } = ui;
|
||||
const { aspectRatio } = generation;
|
||||
return {
|
||||
boundingBoxDimensions,
|
||||
isStaging,
|
||||
|
@ -0,0 +1,21 @@
|
||||
import { Box } from '@chakra-ui/react';
|
||||
import { useCanvasGenerationMode } from 'features/canvas/hooks/useCanvasGenerationMode';
|
||||
|
||||
const GENERATION_MODE_NAME_MAP = {
|
||||
txt2img: 'Text to Image',
|
||||
img2img: 'Image to Image',
|
||||
inpaint: 'Inpaint',
|
||||
outpaint: 'Inpaint',
|
||||
};
|
||||
|
||||
const GenerationModeStatusText = () => {
|
||||
const generationMode = useCanvasGenerationMode();
|
||||
|
||||
return (
|
||||
<Box>
|
||||
Mode: {generationMode ? GENERATION_MODE_NAME_MAP[generationMode] : '...'}
|
||||
</Box>
|
||||
);
|
||||
};
|
||||
|
||||
export default GenerationModeStatusText;
|
@ -1,5 +1,6 @@
|
||||
import { Divider, Flex } from '@chakra-ui/react';
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAICollapse from 'common/components/IAICollapse';
|
||||
@ -9,20 +10,18 @@ import ParamControlNetFeatureToggle from 'features/controlNet/components/paramet
|
||||
import {
|
||||
controlNetAdded,
|
||||
controlNetModelChanged,
|
||||
controlNetSelector,
|
||||
} from 'features/controlNet/store/controlNetSlice';
|
||||
import { getValidControlNets } from 'features/controlNet/util/getValidControlNets';
|
||||
import { useFeatureStatus } from 'features/system/hooks/useFeatureStatus';
|
||||
import { map } from 'lodash-es';
|
||||
import { Fragment, memo, useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { FaPlus } from 'react-icons/fa';
|
||||
import { useGetControlNetModelsQuery } from 'services/api/endpoints/models';
|
||||
import { v4 as uuidv4 } from 'uuid';
|
||||
|
||||
const selector = createSelector(
|
||||
controlNetSelector,
|
||||
(controlNet) => {
|
||||
[stateSelector],
|
||||
({ controlNet }) => {
|
||||
const { controlNets, isEnabled } = controlNet;
|
||||
|
||||
const validControlNets = getValidControlNets(controlNets);
|
||||
@ -38,7 +37,6 @@ const selector = createSelector(
|
||||
);
|
||||
|
||||
const ParamControlNetCollapse = () => {
|
||||
const { t } = useTranslation();
|
||||
const { controlNetsArray, activeLabel } = useAppSelector(selector);
|
||||
const isControlNetDisabled = useFeatureStatus('controlNet').isFeatureDisabled;
|
||||
const dispatch = useAppDispatch();
|
||||
|
@ -2,19 +2,19 @@ import { ButtonGroup, Flex } from '@chakra-ui/react';
|
||||
import { RootState } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAIButton from 'common/components/IAIButton';
|
||||
import { setAspectRatio } from 'features/ui/store/uiSlice';
|
||||
import { setAspectRatio } from 'features/parameters/store/generationSlice';
|
||||
import { activeTabNameSelector } from '../../../../ui/store/uiSelectors';
|
||||
|
||||
const aspectRatios = [
|
||||
{ name: 'Free', value: null },
|
||||
{ name: 'Portrait', value: 0.67 / 1 },
|
||||
{ name: 'Wide', value: 16 / 9 },
|
||||
{ name: 'Square', value: 1 / 1 },
|
||||
{ name: '2:3', value: 2 / 3 },
|
||||
{ name: '16:9', value: 16 / 9 },
|
||||
{ name: '1:1', value: 1 / 1 },
|
||||
];
|
||||
|
||||
export default function ParamAspectRatio() {
|
||||
const aspectRatio = useAppSelector(
|
||||
(state: RootState) => state.ui.aspectRatio
|
||||
(state: RootState) => state.generation.aspectRatio
|
||||
);
|
||||
|
||||
const dispatch = useAppDispatch();
|
||||
|
@ -1,19 +1,16 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAINumberInput from 'common/components/IAINumberInput';
|
||||
import IAISlider from 'common/components/IAISlider';
|
||||
import { generationSelector } from 'features/parameters/store/generationSelectors';
|
||||
import { setCfgScale } from 'features/parameters/store/generationSlice';
|
||||
import { configSelector } from 'features/system/store/configSelectors';
|
||||
import { hotkeysSelector } from 'features/ui/store/hotkeysSlice';
|
||||
import { uiSelector } from 'features/ui/store/uiSelectors';
|
||||
import { memo, useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
[generationSelector, configSelector, uiSelector, hotkeysSelector],
|
||||
(generation, config, ui, hotkeys) => {
|
||||
[stateSelector],
|
||||
({ generation, config, ui, hotkeys }) => {
|
||||
const { initial, min, sliderMax, inputMax } = config.sd.guidance;
|
||||
const { cfgScale } = generation;
|
||||
const { shouldUseSliders } = ui;
|
||||
|
@ -1,23 +1,20 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAISlider, { IAIFullSliderProps } from 'common/components/IAISlider';
|
||||
import { roundToMultiple } from 'common/util/roundDownToMultiple';
|
||||
import { generationSelector } from 'features/parameters/store/generationSelectors';
|
||||
import { setHeight, setWidth } from 'features/parameters/store/generationSlice';
|
||||
import { configSelector } from 'features/system/store/configSelectors';
|
||||
import { hotkeysSelector } from 'features/ui/store/hotkeysSlice';
|
||||
import { uiSelector } from 'features/ui/store/uiSelectors';
|
||||
import { memo, useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
[generationSelector, hotkeysSelector, configSelector, uiSelector],
|
||||
(generation, hotkeys, config, ui) => {
|
||||
[stateSelector],
|
||||
({ generation, hotkeys, config }) => {
|
||||
const { initial, min, sliderMax, inputMax, fineStep, coarseStep } =
|
||||
config.sd.height;
|
||||
const { height } = generation;
|
||||
const { aspectRatio } = ui;
|
||||
const { aspectRatio } = generation;
|
||||
|
||||
const step = hotkeys.shift ? fineStep : coarseStep;
|
||||
|
||||
|
@ -4,6 +4,7 @@ import { memo } from 'react';
|
||||
import ParamMainModelSelect from '../MainModel/ParamMainModelSelect';
|
||||
import ParamVAEModelSelect from '../VAEModel/ParamVAEModelSelect';
|
||||
import ParamScheduler from './ParamScheduler';
|
||||
import ParamVAEPrecision from '../VAEModel/ParamVAEPrecision';
|
||||
|
||||
const ParamModelandVAEandScheduler = () => {
|
||||
const isVaeEnabled = useFeatureStatus('vae').isFeatureEnabled;
|
||||
@ -13,16 +14,15 @@ const ParamModelandVAEandScheduler = () => {
|
||||
<Box w="full">
|
||||
<ParamMainModelSelect />
|
||||
</Box>
|
||||
<Flex gap={3} w="full">
|
||||
{isVaeEnabled && (
|
||||
<Box w="full">
|
||||
<ParamVAEModelSelect />
|
||||
</Box>
|
||||
)}
|
||||
<Box w="full">
|
||||
<ParamScheduler />
|
||||
</Box>
|
||||
</Flex>
|
||||
<Box w="full">
|
||||
<ParamScheduler />
|
||||
</Box>
|
||||
{isVaeEnabled && (
|
||||
<Flex w="full" gap={3}>
|
||||
<ParamVAEModelSelect />
|
||||
<ParamVAEPrecision />
|
||||
</Flex>
|
||||
)}
|
||||
</Flex>
|
||||
);
|
||||
};
|
||||
|
@ -1,12 +1,15 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { SCHEDULER_LABEL_MAP, SCHEDULER_NAMES } from 'app/constants';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAIMantineSearchableSelect from 'common/components/IAIMantineSearchableSelect';
|
||||
import { generationSelector } from 'features/parameters/store/generationSelectors';
|
||||
import { setScheduler } from 'features/parameters/store/generationSlice';
|
||||
import { SchedulerParam } from 'features/parameters/types/parameterSchemas';
|
||||
import {
|
||||
SCHEDULER_LABEL_MAP,
|
||||
SchedulerParam,
|
||||
} from 'features/parameters/types/parameterSchemas';
|
||||
import { uiSelector } from 'features/ui/store/uiSelectors';
|
||||
import { map } from 'lodash-es';
|
||||
import { memo, useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
@ -16,10 +19,10 @@ const selector = createSelector(
|
||||
const { scheduler } = generation;
|
||||
const { favoriteSchedulers: enabledSchedulers } = ui;
|
||||
|
||||
const data = SCHEDULER_NAMES.map((schedulerName) => ({
|
||||
value: schedulerName,
|
||||
label: SCHEDULER_LABEL_MAP[schedulerName as SchedulerParam],
|
||||
group: enabledSchedulers.includes(schedulerName)
|
||||
const data = map(SCHEDULER_LABEL_MAP, (label, name) => ({
|
||||
value: name,
|
||||
label: label,
|
||||
group: enabledSchedulers.includes(name as SchedulerParam)
|
||||
? 'Favorites'
|
||||
: undefined,
|
||||
})).sort((a, b) => a.label.localeCompare(b.label));
|
||||
|
@ -1,23 +1,20 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAINumberInput from 'common/components/IAINumberInput';
|
||||
|
||||
import IAISlider from 'common/components/IAISlider';
|
||||
import { generationSelector } from 'features/parameters/store/generationSelectors';
|
||||
import {
|
||||
clampSymmetrySteps,
|
||||
setSteps,
|
||||
} from 'features/parameters/store/generationSlice';
|
||||
import { configSelector } from 'features/system/store/configSelectors';
|
||||
import { hotkeysSelector } from 'features/ui/store/hotkeysSlice';
|
||||
import { uiSelector } from 'features/ui/store/uiSelectors';
|
||||
import { memo, useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
[generationSelector, configSelector, uiSelector, hotkeysSelector],
|
||||
(generation, config, ui, hotkeys) => {
|
||||
[stateSelector],
|
||||
({ generation, config, ui, hotkeys }) => {
|
||||
const { initial, min, sliderMax, inputMax, fineStep, coarseStep } =
|
||||
config.sd.steps;
|
||||
const { steps } = generation;
|
||||
|
@ -1,23 +1,19 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAISlider, { IAIFullSliderProps } from 'common/components/IAISlider';
|
||||
import { roundToMultiple } from 'common/util/roundDownToMultiple';
|
||||
import { generationSelector } from 'features/parameters/store/generationSelectors';
|
||||
import { setHeight, setWidth } from 'features/parameters/store/generationSlice';
|
||||
import { configSelector } from 'features/system/store/configSelectors';
|
||||
import { hotkeysSelector } from 'features/ui/store/hotkeysSlice';
|
||||
import { uiSelector } from 'features/ui/store/uiSelectors';
|
||||
import { memo, useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
[generationSelector, hotkeysSelector, configSelector, uiSelector],
|
||||
(generation, hotkeys, config, ui) => {
|
||||
[stateSelector],
|
||||
({ generation, hotkeys, config }) => {
|
||||
const { initial, min, sliderMax, inputMax, fineStep, coarseStep } =
|
||||
config.sd.width;
|
||||
const { width } = generation;
|
||||
const { aspectRatio } = ui;
|
||||
const { width, aspectRatio } = generation;
|
||||
|
||||
const step = hotkeys.shift ? fineStep : coarseStep;
|
||||
|
||||
|
@ -1,17 +1,15 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAISlider from 'common/components/IAISlider';
|
||||
import { generationSelector } from 'features/parameters/store/generationSelectors';
|
||||
import { setImg2imgStrength } from 'features/parameters/store/generationSlice';
|
||||
import { configSelector } from 'features/system/store/configSelectors';
|
||||
import { hotkeysSelector } from 'features/ui/store/hotkeysSlice';
|
||||
import { memo, useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
[generationSelector, hotkeysSelector, configSelector],
|
||||
(generation, hotkeys, config) => {
|
||||
[stateSelector],
|
||||
({ generation, hotkeys, config }) => {
|
||||
const { initial, min, sliderMax, inputMax, fineStep, coarseStep } =
|
||||
config.sd.img2imgStrength;
|
||||
const { img2imgStrength } = generation;
|
||||
|
@ -27,12 +27,9 @@ const selector = createSelector(
|
||||
const InitialImage = () => {
|
||||
const { initialImage } = useAppSelector(selector);
|
||||
|
||||
const {
|
||||
currentData: imageDTO,
|
||||
isLoading,
|
||||
isError,
|
||||
isSuccess,
|
||||
} = useGetImageDTOQuery(initialImage?.imageName ?? skipToken);
|
||||
const { currentData: imageDTO } = useGetImageDTOQuery(
|
||||
initialImage?.imageName ?? skipToken
|
||||
);
|
||||
|
||||
const draggableData = useMemo<TypesafeDraggableData | undefined>(() => {
|
||||
if (imageDTO) {
|
||||
|
@ -5,12 +5,11 @@ import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAIIconButton from 'common/components/IAIIconButton';
|
||||
import { useImageUploadButton } from 'common/hooks/useImageUploadButton';
|
||||
import useImageUploader from 'common/hooks/useImageUploader';
|
||||
import { clearInitialImage } from 'features/parameters/store/generationSlice';
|
||||
import { useCallback } from 'react';
|
||||
import { FaUndo, FaUpload } from 'react-icons/fa';
|
||||
import { PostUploadAction } from 'services/api/thunks/image';
|
||||
import InitialImage from './InitialImage';
|
||||
import { PostUploadAction } from 'services/api/types';
|
||||
|
||||
const selector = createSelector(
|
||||
[stateSelector],
|
||||
@ -30,7 +29,6 @@ const postUploadAction: PostUploadAction = {
|
||||
const InitialImageDisplay = () => {
|
||||
const { isResetButtonDisabled } = useAppSelector(selector);
|
||||
const dispatch = useAppDispatch();
|
||||
const { openUploader } = useImageUploader();
|
||||
|
||||
const { getUploadButtonProps, getUploadInputProps } = useImageUploadButton({
|
||||
postUploadAction,
|
||||
@ -40,10 +38,6 @@ const InitialImageDisplay = () => {
|
||||
dispatch(clearInitialImage());
|
||||
}, [dispatch]);
|
||||
|
||||
const handleUpload = useCallback(() => {
|
||||
openUploader();
|
||||
}, [openUploader]);
|
||||
|
||||
return (
|
||||
<Flex
|
||||
layerStyle={'first'}
|
||||
@ -85,7 +79,6 @@ const InitialImageDisplay = () => {
|
||||
tooltip={'Upload Initial Image'}
|
||||
aria-label={'Upload Initial Image'}
|
||||
icon={<FaUpload />}
|
||||
onClick={handleUpload}
|
||||
{...getUploadButtonProps()}
|
||||
/>
|
||||
<IAIIconButton
|
||||
|
@ -4,6 +4,7 @@ import { useTranslation } from 'react-i18next';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAIMantineSearchableSelect from 'common/components/IAIMantineSearchableSelect';
|
||||
|
||||
import { Box, Flex } from '@chakra-ui/react';
|
||||
import { SelectItem } from '@mantine/core';
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
@ -11,12 +12,16 @@ import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import { modelSelected } from 'features/parameters/store/actions';
|
||||
import { MODEL_TYPE_MAP } from 'features/parameters/types/constants';
|
||||
import { modelIdToMainModelParam } from 'features/parameters/util/modelIdToMainModelParam';
|
||||
import SyncModelsButton from 'features/ui/components/tabs/ModelManager/subpanels/ModelManagerSettingsPanel/SyncModelsButton';
|
||||
import { activeTabNameSelector } from 'features/ui/store/uiSelectors';
|
||||
import { forEach } from 'lodash-es';
|
||||
import {
|
||||
useGetMainModelsQuery,
|
||||
useGetOnnxModelsQuery,
|
||||
} from 'services/api/endpoints/models';
|
||||
import { modelIdToOnnxModelField } from 'features/nodes/util/modelIdToOnnxModelField';
|
||||
import { NON_REFINER_BASE_MODELS } from 'services/api/constants';
|
||||
import { useFeatureStatus } from '../../../../system/hooks/useFeatureStatus';
|
||||
|
||||
const selector = createSelector(
|
||||
stateSelector,
|
||||
@ -30,9 +35,14 @@ const ParamMainModelSelect = () => {
|
||||
|
||||
const { model } = useAppSelector(selector);
|
||||
|
||||
const { data: mainModels, isLoading } = useGetMainModelsQuery();
|
||||
const isSyncModelEnabled = useFeatureStatus('syncModels').isFeatureEnabled;
|
||||
const { data: mainModels, isLoading } = useGetMainModelsQuery(
|
||||
NON_REFINER_BASE_MODELS
|
||||
);
|
||||
const { data: onnxModels, isLoading: onnxLoading } = useGetOnnxModelsQuery();
|
||||
|
||||
const activeTabName = useAppSelector(activeTabNameSelector);
|
||||
|
||||
const data = useMemo(() => {
|
||||
if (!mainModels) {
|
||||
return [];
|
||||
@ -41,7 +51,10 @@ const ParamMainModelSelect = () => {
|
||||
const data: SelectItem[] = [];
|
||||
|
||||
forEach(mainModels.entities, (model, id) => {
|
||||
if (!model || ['sdxl', 'sdxl-refiner'].includes(model.base_model)) {
|
||||
if (
|
||||
!model ||
|
||||
(activeTabName === 'unifiedCanvas' && model.base_model === 'sdxl')
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
@ -64,7 +77,7 @@ const ParamMainModelSelect = () => {
|
||||
});
|
||||
|
||||
return data;
|
||||
}, [mainModels, onnxModels]);
|
||||
}, [mainModels, onnxModels, activeTabName]);
|
||||
|
||||
// grab the full model entity from the RTK Query cache
|
||||
// TODO: maybe we should just store the full model entity in state?
|
||||
@ -107,16 +120,24 @@ const ParamMainModelSelect = () => {
|
||||
data={[]}
|
||||
/>
|
||||
) : (
|
||||
<IAIMantineSearchableSelect
|
||||
tooltip={selectedModel?.description}
|
||||
label={t('modelManager.model')}
|
||||
value={selectedModel?.id}
|
||||
placeholder={data.length > 0 ? 'Select a model' : 'No models available'}
|
||||
data={data}
|
||||
error={data.length === 0}
|
||||
disabled={data.length === 0}
|
||||
onChange={handleChangeModel}
|
||||
/>
|
||||
<Flex w="100%" alignItems="center" gap={3}>
|
||||
<IAIMantineSearchableSelect
|
||||
tooltip={selectedModel?.description}
|
||||
label={t('modelManager.model')}
|
||||
value={selectedModel?.id}
|
||||
placeholder={data.length > 0 ? 'Select a model' : 'No models available'}
|
||||
data={data}
|
||||
error={data.length === 0}
|
||||
disabled={data.length === 0}
|
||||
onChange={handleChangeModel}
|
||||
w="100%"
|
||||
/>
|
||||
{isSyncModelEnabled && (
|
||||
<Box mt={7}>
|
||||
<SyncModelsButton iconMode />
|
||||
</Box>
|
||||
)}
|
||||
</Flex>
|
||||
);
|
||||
};
|
||||
|
||||
|
@ -5,7 +5,6 @@ import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAISwitch from 'common/components/IAISwitch';
|
||||
import { shouldUseCpuNoiseChanged } from 'features/parameters/store/generationSlice';
|
||||
import { ChangeEvent } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const selector = createSelector(
|
||||
stateSelector,
|
||||
@ -23,8 +22,6 @@ export const ParamCpuNoiseToggle = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
const { isDisabled, shouldUseCpuNoise } = useAppSelector(selector);
|
||||
|
||||
const { t } = useTranslation();
|
||||
|
||||
const handleChange = (e: ChangeEvent<HTMLInputElement>) =>
|
||||
dispatch(shouldUseCpuNoiseChanged(e.target.checked));
|
||||
|
||||
|
@ -3,7 +3,6 @@ import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAISwitch from 'common/components/IAISwitch';
|
||||
import { setShouldUseNoiseSettings } from 'features/parameters/store/generationSlice';
|
||||
import { ChangeEvent } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
export const ParamNoiseToggle = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
@ -12,8 +11,6 @@ export const ParamNoiseToggle = () => {
|
||||
(state: RootState) => state.generation.shouldUseNoiseSettings
|
||||
);
|
||||
|
||||
const { t } = useTranslation();
|
||||
|
||||
const handleChange = (e: ChangeEvent<HTMLInputElement>) =>
|
||||
dispatch(setShouldUseNoiseSettings(e.target.checked));
|
||||
|
||||
|
@ -1,33 +0,0 @@
|
||||
import { RootState } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAISwitch from 'common/components/IAISwitch';
|
||||
import { setSeamless } from 'features/parameters/store/generationSlice';
|
||||
import { ChangeEvent } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
/**
|
||||
* Seamless tiling toggle
|
||||
*/
|
||||
const ParamSeamlessToggle = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
|
||||
const seamless = useAppSelector(
|
||||
(state: RootState) => state.generation.seamless
|
||||
);
|
||||
|
||||
const handleChangeSeamless = (e: ChangeEvent<HTMLInputElement>) =>
|
||||
dispatch(setSeamless(e.target.checked));
|
||||
|
||||
const { t } = useTranslation();
|
||||
|
||||
return (
|
||||
<IAISwitch
|
||||
label={t('parameters.seamlessTiling')}
|
||||
fontSize="md"
|
||||
isChecked={seamless}
|
||||
onChange={handleChangeSeamless}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
export default ParamSeamlessToggle;
|
@ -32,11 +32,6 @@ export default function ParamSeed() {
|
||||
isInvalid={seed < 0 && shouldGenerateVariations}
|
||||
onChange={handleChangeSeed}
|
||||
value={seed}
|
||||
formControlProps={{
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
gap: 3, // really this should work with 2 but seems to need to be 3 to match gap 2?
|
||||
}}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
@ -1,48 +0,0 @@
|
||||
import { Flex } from '@chakra-ui/react';
|
||||
import ParamSeed from './ParamSeed';
|
||||
import { memo, useCallback } from 'react';
|
||||
import ParamSeedShuffle from './ParamSeedShuffle';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { generationSelector } from 'features/parameters/store/generationSelectors';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import { setShouldRandomizeSeed } from 'features/parameters/store/generationSlice';
|
||||
import IAICollapse from 'common/components/IAICollapse';
|
||||
|
||||
const selector = createSelector(
|
||||
generationSelector,
|
||||
(generation) => {
|
||||
const { shouldRandomizeSeed } = generation;
|
||||
|
||||
return { shouldRandomizeSeed };
|
||||
},
|
||||
defaultSelectorOptions
|
||||
);
|
||||
|
||||
const ParamSeedSettings = () => {
|
||||
const { t } = useTranslation();
|
||||
const dispatch = useAppDispatch();
|
||||
const { shouldRandomizeSeed } = useAppSelector(selector);
|
||||
|
||||
const handleToggle = useCallback(
|
||||
() => dispatch(setShouldRandomizeSeed(!shouldRandomizeSeed)),
|
||||
[dispatch, shouldRandomizeSeed]
|
||||
);
|
||||
|
||||
return (
|
||||
<IAICollapse
|
||||
label={t('parameters.seed')}
|
||||
isOpen={!shouldRandomizeSeed}
|
||||
onToggle={handleToggle}
|
||||
withSwitch
|
||||
>
|
||||
<Flex sx={{ gap: 4 }}>
|
||||
<ParamSeed />
|
||||
<ParamSeedShuffle />
|
||||
</Flex>
|
||||
</IAICollapse>
|
||||
);
|
||||
};
|
||||
|
||||
export default memo(ParamSeedSettings);
|
@ -6,7 +6,7 @@ import ParamSeedRandomize from './ParamSeedRandomize';
|
||||
|
||||
const ParamSeedFull = () => {
|
||||
return (
|
||||
<Flex sx={{ gap: 4, alignItems: 'center' }}>
|
||||
<Flex sx={{ gap: 3, alignItems: 'flex-end' }}>
|
||||
<ParamSeed />
|
||||
<ParamSeedShuffle />
|
||||
<ParamSeedRandomize />
|
||||
|
@ -7,7 +7,6 @@ import {
|
||||
ESRGANModelName,
|
||||
esrganModelNameChanged,
|
||||
} from 'features/parameters/store/postprocessingSlice';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
export const ESRGAN_MODEL_NAMES: SelectItem[] = [
|
||||
{
|
||||
|
@ -0,0 +1,46 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAIMantineSelect from 'common/components/IAIMantineSelect';
|
||||
import { vaePrecisionChanged } from 'features/parameters/store/generationSlice';
|
||||
import { PrecisionParam } from 'features/parameters/types/parameterSchemas';
|
||||
import { memo, useCallback } from 'react';
|
||||
|
||||
const selector = createSelector(
|
||||
stateSelector,
|
||||
({ generation }) => {
|
||||
const { vaePrecision } = generation;
|
||||
return { vaePrecision };
|
||||
},
|
||||
defaultSelectorOptions
|
||||
);
|
||||
|
||||
const DATA = ['fp16', 'fp32'];
|
||||
|
||||
const ParamVAEModelSelect = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
const { vaePrecision } = useAppSelector(selector);
|
||||
|
||||
const handleChange = useCallback(
|
||||
(v: string | null) => {
|
||||
if (!v) {
|
||||
return;
|
||||
}
|
||||
|
||||
dispatch(vaePrecisionChanged(v as PrecisionParam));
|
||||
},
|
||||
[dispatch]
|
||||
);
|
||||
|
||||
return (
|
||||
<IAIMantineSelect
|
||||
label="VAE Precision"
|
||||
value={vaePrecision}
|
||||
data={DATA}
|
||||
onChange={handleChange}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
export default memo(ParamVAEModelSelect);
|
@ -1,47 +1,51 @@
|
||||
import { Flex } from '@chakra-ui/react';
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAICollapse from 'common/components/IAICollapse';
|
||||
import { useFeatureStatus } from 'features/system/hooks/useFeatureStatus';
|
||||
import { memo } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import ParamVariationAmount from './ParamVariationAmount';
|
||||
import { ParamVariationToggle } from './ParamVariationToggle';
|
||||
import ParamVariationWeights from './ParamVariationWeights';
|
||||
// TODO: variations
|
||||
|
||||
const selector = createSelector(
|
||||
stateSelector,
|
||||
(state) => {
|
||||
const activeLabel = state.generation.shouldGenerateVariations
|
||||
? 'Enabled'
|
||||
: undefined;
|
||||
// import { Flex } from '@chakra-ui/react';
|
||||
// import { createSelector } from '@reduxjs/toolkit';
|
||||
// import { stateSelector } from 'app/store/store';
|
||||
// import { useAppSelector } from 'app/store/storeHooks';
|
||||
// import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
// import IAICollapse from 'common/components/IAICollapse';
|
||||
// import { useFeatureStatus } from 'features/system/hooks/useFeatureStatus';
|
||||
// import { memo } from 'react';
|
||||
// import { useTranslation } from 'react-i18next';
|
||||
// import ParamVariationAmount from './ParamVariationAmount';
|
||||
// import { ParamVariationToggle } from './ParamVariationToggle';
|
||||
// import ParamVariationWeights from './ParamVariationWeights';
|
||||
|
||||
return { activeLabel };
|
||||
},
|
||||
defaultSelectorOptions
|
||||
);
|
||||
// const selector = createSelector(
|
||||
// stateSelector,
|
||||
// (state) => {
|
||||
// const activeLabel = state.generation.shouldGenerateVariations
|
||||
// ? 'Enabled'
|
||||
// : undefined;
|
||||
|
||||
const ParamVariationCollapse = () => {
|
||||
const { t } = useTranslation();
|
||||
const { activeLabel } = useAppSelector(selector);
|
||||
// return { activeLabel };
|
||||
// },
|
||||
// defaultSelectorOptions
|
||||
// );
|
||||
|
||||
const isVariationEnabled = useFeatureStatus('variation').isFeatureEnabled;
|
||||
// const ParamVariationCollapse = () => {
|
||||
// const { t } = useTranslation();
|
||||
// const { activeLabel } = useAppSelector(selector);
|
||||
|
||||
if (!isVariationEnabled) {
|
||||
return null;
|
||||
}
|
||||
// const isVariationEnabled = useFeatureStatus('variation').isFeatureEnabled;
|
||||
|
||||
return (
|
||||
<IAICollapse label={t('parameters.variations')} activeLabel={activeLabel}>
|
||||
<Flex sx={{ gap: 2, flexDirection: 'column' }}>
|
||||
<ParamVariationToggle />
|
||||
<ParamVariationAmount />
|
||||
<ParamVariationWeights />
|
||||
</Flex>
|
||||
</IAICollapse>
|
||||
);
|
||||
};
|
||||
// if (!isVariationEnabled) {
|
||||
// return null;
|
||||
// }
|
||||
|
||||
export default memo(ParamVariationCollapse);
|
||||
// return (
|
||||
// <IAICollapse label={t('parameters.variations')} activeLabel={activeLabel}>
|
||||
// <Flex sx={{ gap: 2, flexDirection: 'column' }}>
|
||||
// <ParamVariationToggle />
|
||||
// <ParamVariationAmount />
|
||||
// <ParamVariationWeights />
|
||||
// </Flex>
|
||||
// </IAICollapse>
|
||||
// );
|
||||
// };
|
||||
|
||||
// export default memo(ParamVariationCollapse);
|
||||
|
||||
export default {};
|
||||
|
@ -3,7 +3,6 @@ import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAISwitch from 'common/components/IAISwitch';
|
||||
import { setShouldGenerateVariations } from 'features/parameters/store/generationSlice';
|
||||
import { ChangeEvent } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
export const ParamVariationToggle = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
@ -12,8 +11,6 @@ export const ParamVariationToggle = () => {
|
||||
(state: RootState) => state.generation.shouldGenerateVariations
|
||||
);
|
||||
|
||||
const { t } = useTranslation();
|
||||
|
||||
const handleChange = (e: ChangeEvent<HTMLInputElement>) =>
|
||||
dispatch(setShouldGenerateVariations(e.target.checked));
|
||||
|
||||
|
@ -1,37 +1,41 @@
|
||||
import { RootState } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAIInput from 'common/components/IAIInput';
|
||||
import { validateSeedWeights } from 'common/util/seedWeightPairs';
|
||||
import { setSeedWeights } from 'features/parameters/store/generationSlice';
|
||||
import { ChangeEvent } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
// TODO: variations
|
||||
|
||||
export default function ParamVariationWeights() {
|
||||
const seedWeights = useAppSelector(
|
||||
(state: RootState) => state.generation.seedWeights
|
||||
);
|
||||
// import { RootState } from 'app/store/store';
|
||||
// import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
// import IAIInput from 'common/components/IAIInput';
|
||||
// import { validateSeedWeights } from 'common/util/seedWeightPairs';
|
||||
// import { setSeedWeights } from 'features/parameters/store/generationSlice';
|
||||
// import { ChangeEvent } from 'react';
|
||||
// import { useTranslation } from 'react-i18next';
|
||||
|
||||
const shouldGenerateVariations = useAppSelector(
|
||||
(state: RootState) => state.generation.shouldGenerateVariations
|
||||
);
|
||||
// export default function ParamVariationWeights() {
|
||||
// const seedWeights = useAppSelector(
|
||||
// (state: RootState) => state.generation.seedWeights
|
||||
// );
|
||||
|
||||
const { t } = useTranslation();
|
||||
// const shouldGenerateVariations = useAppSelector(
|
||||
// (state: RootState) => state.generation.shouldGenerateVariations
|
||||
// );
|
||||
|
||||
const dispatch = useAppDispatch();
|
||||
// const { t } = useTranslation();
|
||||
|
||||
const handleChangeSeedWeights = (e: ChangeEvent<HTMLInputElement>) =>
|
||||
dispatch(setSeedWeights(e.target.value));
|
||||
// const dispatch = useAppDispatch();
|
||||
|
||||
return (
|
||||
<IAIInput
|
||||
label={t('parameters.seedWeights')}
|
||||
value={seedWeights}
|
||||
isInvalid={
|
||||
shouldGenerateVariations &&
|
||||
!(validateSeedWeights(seedWeights) || seedWeights === '')
|
||||
}
|
||||
isDisabled={!shouldGenerateVariations}
|
||||
onChange={handleChangeSeedWeights}
|
||||
/>
|
||||
);
|
||||
}
|
||||
// const handleChangeSeedWeights = (e: ChangeEvent<HTMLInputElement>) =>
|
||||
// dispatch(setSeedWeights(e.target.value));
|
||||
|
||||
// return (
|
||||
// <IAIInput
|
||||
// label={t('parameters.seedWeights')}
|
||||
// value={seedWeights}
|
||||
// isInvalid={
|
||||
// shouldGenerateVariations &&
|
||||
// !(validateSeedWeights(seedWeights) || seedWeights === '')
|
||||
// }
|
||||
// isDisabled={!shouldGenerateVariations}
|
||||
// onChange={handleChangeSeedWeights}
|
||||
// />
|
||||
// );
|
||||
// }
|
||||
|
||||
export default {};
|
||||
|
@ -1,75 +0,0 @@
|
||||
import { Flex, Text } from '@chakra-ui/react';
|
||||
import { memo, useMemo } from 'react';
|
||||
|
||||
export const ratioToCSSString = (
|
||||
ratio: AspectRatio,
|
||||
orientation: Orientation
|
||||
) => {
|
||||
if (orientation === 'portrait') {
|
||||
return `${ratio[0]}/${ratio[1]}`;
|
||||
}
|
||||
return `${ratio[1]}/${ratio[0]}`;
|
||||
};
|
||||
|
||||
export const ratioToDisplayString = (
|
||||
ratio: AspectRatio,
|
||||
orientation: Orientation
|
||||
) => {
|
||||
if (orientation === 'portrait') {
|
||||
return `${ratio[0]}:${ratio[1]}`;
|
||||
}
|
||||
return `${ratio[1]}:${ratio[0]}`;
|
||||
};
|
||||
|
||||
type AspectRatioPreviewProps = {
|
||||
ratio: AspectRatio;
|
||||
orientation: Orientation;
|
||||
size: string;
|
||||
};
|
||||
|
||||
export type AspectRatio = [number, number];
|
||||
|
||||
export type Orientation = 'portrait' | 'landscape';
|
||||
|
||||
const AspectRatioPreview = (props: AspectRatioPreviewProps) => {
|
||||
const { ratio, size, orientation } = props;
|
||||
|
||||
const ratioCSSString = useMemo(() => {
|
||||
if (orientation === 'portrait') {
|
||||
return `${ratio[0]}/${ratio[1]}`;
|
||||
}
|
||||
return `${ratio[1]}/${ratio[0]}`;
|
||||
}, [ratio, orientation]);
|
||||
|
||||
const ratioDisplayString = useMemo(() => `${ratio[0]}:${ratio[1]}`, [ratio]);
|
||||
|
||||
return (
|
||||
<Flex
|
||||
sx={{
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
w: size,
|
||||
h: size,
|
||||
}}
|
||||
>
|
||||
<Flex
|
||||
sx={{
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
bg: 'base.700',
|
||||
color: 'base.400',
|
||||
borderRadius: 'base',
|
||||
aspectRatio: ratioCSSString,
|
||||
objectFit: 'contain',
|
||||
...(orientation === 'landscape' ? { h: 'full' } : { w: 'full' }),
|
||||
}}
|
||||
>
|
||||
<Text sx={{ size: 'xs', userSelect: 'none' }}>
|
||||
{ratioDisplayString}
|
||||
</Text>
|
||||
</Flex>
|
||||
</Flex>
|
||||
);
|
||||
};
|
||||
|
||||
export default memo(AspectRatioPreview);
|
@ -1,76 +0,0 @@
|
||||
import { Box, Flex, FormControl, FormLabel, Select } from '@chakra-ui/react';
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { RootState } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAISlider from 'common/components/IAISlider';
|
||||
import { setWidth } from 'features/parameters/store/generationSlice';
|
||||
import { memo, useState } from 'react';
|
||||
import AspectRatioPreview, {
|
||||
AspectRatio,
|
||||
Orientation,
|
||||
} from './AspectRatioPreview';
|
||||
|
||||
const RATIOS: AspectRatio[] = [
|
||||
[1, 1],
|
||||
[5, 4],
|
||||
[3, 2],
|
||||
[16, 10],
|
||||
[16, 9],
|
||||
];
|
||||
|
||||
RATIOS.forEach((r) => {
|
||||
const float = r[0] / r[1];
|
||||
console.log((512 * float) / 8);
|
||||
});
|
||||
|
||||
const dimensionsSettingsSelector = createSelector(
|
||||
(state: RootState) => state.generation,
|
||||
(generation) => {
|
||||
const { width, height } = generation;
|
||||
|
||||
return { width, height };
|
||||
}
|
||||
);
|
||||
|
||||
const DimensionsSettings = () => {
|
||||
const { width, height } = useAppSelector(dimensionsSettingsSelector);
|
||||
const dispatch = useAppDispatch();
|
||||
const [ratioIndex, setRatioIndex] = useState(4);
|
||||
const [orientation, setOrientation] = useState<Orientation>('portrait');
|
||||
|
||||
return (
|
||||
<Flex gap={3}>
|
||||
<Box flexShrink={0}>
|
||||
<AspectRatioPreview
|
||||
ratio={RATIOS[ratioIndex]}
|
||||
orientation={orientation}
|
||||
size="4rem"
|
||||
/>
|
||||
</Box>
|
||||
<FormControl>
|
||||
<FormLabel>Aspect Ratio</FormLabel>
|
||||
<Select
|
||||
onChange={(e) => {
|
||||
setRatioIndex(Number(e.target.value));
|
||||
}}
|
||||
>
|
||||
{RATIOS.map((r, i) => (
|
||||
<option key={r.join()} value={i}>{`${r[0]}:${r[1]}`}</option>
|
||||
))}
|
||||
</Select>
|
||||
</FormControl>
|
||||
<IAISlider
|
||||
label="Size"
|
||||
value={width}
|
||||
min={64}
|
||||
max={2048}
|
||||
step={8}
|
||||
onChange={(v) => {
|
||||
dispatch(setWidth(v));
|
||||
}}
|
||||
/>
|
||||
</Flex>
|
||||
);
|
||||
};
|
||||
|
||||
export default memo(DimensionsSettings);
|
@ -1,6 +1,9 @@
|
||||
import { Box, ChakraProps } from '@chakra-ui/react';
|
||||
import { Box, ChakraProps, Tooltip } from '@chakra-ui/react';
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { userInvoked } from 'app/store/actions';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { defaultSelectorOptions } from 'app/store/util/defaultMemoizeOptions';
|
||||
import IAIButton, { IAIButtonProps } from 'common/components/IAIButton';
|
||||
import IAIIconButton, {
|
||||
IAIIconButtonProps,
|
||||
@ -8,11 +11,13 @@ import IAIIconButton, {
|
||||
import { useIsReadyToInvoke } from 'common/hooks/useIsReadyToInvoke';
|
||||
import { clampSymmetrySteps } from 'features/parameters/store/generationSlice';
|
||||
import ProgressBar from 'features/system/components/ProgressBar';
|
||||
import { selectIsBusy } from 'features/system/store/systemSelectors';
|
||||
import { activeTabNameSelector } from 'features/ui/store/uiSelectors';
|
||||
import { useCallback } from 'react';
|
||||
import { useHotkeys } from 'react-hotkeys-hook';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { FaPlay } from 'react-icons/fa';
|
||||
import { useBoardName } from 'services/api/hooks/useBoardName';
|
||||
|
||||
const IN_PROGRESS_STYLES: ChakraProps['sx'] = {
|
||||
_disabled: {
|
||||
@ -26,6 +31,20 @@ const IN_PROGRESS_STYLES: ChakraProps['sx'] = {
|
||||
},
|
||||
};
|
||||
|
||||
const selector = createSelector(
|
||||
[stateSelector, activeTabNameSelector, selectIsBusy],
|
||||
({ gallery }, activeTabName, isBusy) => {
|
||||
const { autoAddBoardId } = gallery;
|
||||
|
||||
return {
|
||||
isBusy,
|
||||
autoAddBoardId,
|
||||
activeTabName,
|
||||
};
|
||||
},
|
||||
defaultSelectorOptions
|
||||
);
|
||||
|
||||
interface InvokeButton
|
||||
extends Omit<IAIButtonProps | IAIIconButtonProps, 'aria-label'> {
|
||||
iconButton?: boolean;
|
||||
@ -35,8 +54,8 @@ export default function InvokeButton(props: InvokeButton) {
|
||||
const { iconButton = false, ...rest } = props;
|
||||
const dispatch = useAppDispatch();
|
||||
const isReady = useIsReadyToInvoke();
|
||||
const activeTabName = useAppSelector(activeTabNameSelector);
|
||||
const isProcessing = useAppSelector((state) => state.system.isProcessing);
|
||||
const { isBusy, autoAddBoardId, activeTabName } = useAppSelector(selector);
|
||||
const autoAddBoardName = useBoardName(autoAddBoardId);
|
||||
|
||||
const handleInvoke = useCallback(() => {
|
||||
dispatch(clampSymmetrySteps());
|
||||
@ -75,43 +94,52 @@ export default function InvokeButton(props: InvokeButton) {
|
||||
<ProgressBar />
|
||||
</Box>
|
||||
)}
|
||||
{iconButton ? (
|
||||
<IAIIconButton
|
||||
aria-label={t('parameters.invoke')}
|
||||
type="submit"
|
||||
icon={<FaPlay />}
|
||||
isDisabled={!isReady || isProcessing}
|
||||
onClick={handleInvoke}
|
||||
tooltip={t('parameters.invoke')}
|
||||
tooltipProps={{ placement: 'top' }}
|
||||
colorScheme="accent"
|
||||
id="invoke-button"
|
||||
{...rest}
|
||||
sx={{
|
||||
w: 'full',
|
||||
flexGrow: 1,
|
||||
...(isProcessing ? IN_PROGRESS_STYLES : {}),
|
||||
}}
|
||||
/>
|
||||
) : (
|
||||
<IAIButton
|
||||
aria-label={t('parameters.invoke')}
|
||||
type="submit"
|
||||
isDisabled={!isReady || isProcessing}
|
||||
onClick={handleInvoke}
|
||||
colorScheme="accent"
|
||||
id="invoke-button"
|
||||
{...rest}
|
||||
sx={{
|
||||
w: 'full',
|
||||
flexGrow: 1,
|
||||
fontWeight: 700,
|
||||
...(isProcessing ? IN_PROGRESS_STYLES : {}),
|
||||
}}
|
||||
>
|
||||
Invoke
|
||||
</IAIButton>
|
||||
)}
|
||||
<Tooltip
|
||||
placement="top"
|
||||
hasArrow
|
||||
openDelay={500}
|
||||
label={
|
||||
autoAddBoardId ? `Auto-Adding to ${autoAddBoardName}` : undefined
|
||||
}
|
||||
>
|
||||
{iconButton ? (
|
||||
<IAIIconButton
|
||||
aria-label={t('parameters.invoke')}
|
||||
type="submit"
|
||||
icon={<FaPlay />}
|
||||
isDisabled={!isReady || isBusy}
|
||||
onClick={handleInvoke}
|
||||
tooltip={t('parameters.invoke')}
|
||||
tooltipProps={{ placement: 'top' }}
|
||||
colorScheme="accent"
|
||||
id="invoke-button"
|
||||
{...rest}
|
||||
sx={{
|
||||
w: 'full',
|
||||
flexGrow: 1,
|
||||
...(isBusy ? IN_PROGRESS_STYLES : {}),
|
||||
}}
|
||||
/>
|
||||
) : (
|
||||
<IAIButton
|
||||
aria-label={t('parameters.invoke')}
|
||||
type="submit"
|
||||
isDisabled={!isReady || isBusy}
|
||||
onClick={handleInvoke}
|
||||
colorScheme="accent"
|
||||
id="invoke-button"
|
||||
{...rest}
|
||||
sx={{
|
||||
w: 'full',
|
||||
flexGrow: 1,
|
||||
fontWeight: 700,
|
||||
...(isBusy ? IN_PROGRESS_STYLES : {}),
|
||||
}}
|
||||
>
|
||||
Invoke
|
||||
</IAIButton>
|
||||
)}
|
||||
</Tooltip>
|
||||
</Box>
|
||||
</Box>
|
||||
);
|
||||
|
@ -1,33 +0,0 @@
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import IAIIconButton from 'common/components/IAIIconButton';
|
||||
import { postprocessingSelector } from 'features/parameters/store/postprocessingSelectors';
|
||||
import { setShouldLoopback } from 'features/parameters/store/postprocessingSlice';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { FaRecycle } from 'react-icons/fa';
|
||||
|
||||
const loopbackSelector = createSelector(
|
||||
postprocessingSelector,
|
||||
({ shouldLoopback }) => shouldLoopback
|
||||
);
|
||||
|
||||
const LoopbackButton = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
const shouldLoopback = useAppSelector(loopbackSelector);
|
||||
|
||||
const { t } = useTranslation();
|
||||
|
||||
return (
|
||||
<IAIIconButton
|
||||
aria-label={t('parameters.toggleLoopback')}
|
||||
tooltip={t('parameters.toggleLoopback')}
|
||||
isChecked={shouldLoopback}
|
||||
icon={<FaRecycle />}
|
||||
onClick={() => {
|
||||
dispatch(setShouldLoopback(!shouldLoopback));
|
||||
}}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
export default LoopbackButton;
|
@ -9,7 +9,6 @@ const ProcessButtons = () => {
|
||||
return (
|
||||
<Flex gap={2}>
|
||||
<InvokeButton />
|
||||
{/* {activeTabName === 'img2img' && <LoopbackButton />} */}
|
||||
<CancelButton />
|
||||
</Flex>
|
||||
);
|
||||
|
@ -3,7 +3,6 @@ import { useAppDispatch } from 'app/store/storeHooks';
|
||||
import { useCallback } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { UnsafeImageMetadata } from 'services/api/endpoints/images';
|
||||
import { isImageField } from 'services/api/guards';
|
||||
import { ImageDTO } from 'services/api/types';
|
||||
import { initialImageSelected, modelSelected } from '../store/actions';
|
||||
import {
|
||||
@ -244,22 +243,7 @@ export const useRecallParameters = () => {
|
||||
[dispatch, parameterSetToast, parameterNotSetToast]
|
||||
);
|
||||
|
||||
/**
|
||||
* Sets initial image with toast
|
||||
*/
|
||||
const recallInitialImage = useCallback(
|
||||
async (image: unknown) => {
|
||||
if (!isImageField(image)) {
|
||||
parameterNotSetToast();
|
||||
return;
|
||||
}
|
||||
dispatch(initialImageSelected(image.image_name));
|
||||
parameterSetToast();
|
||||
},
|
||||
[dispatch, parameterSetToast, parameterNotSetToast]
|
||||
);
|
||||
|
||||
/**
|
||||
/*
|
||||
* Sets image as initial image with toast
|
||||
*/
|
||||
const sendToImageToImage = useCallback(
|
||||
@ -330,7 +314,6 @@ export const useRecallParameters = () => {
|
||||
recallPositivePrompt,
|
||||
recallNegativePrompt,
|
||||
recallSeed,
|
||||
recallInitialImage,
|
||||
recallCfgScale,
|
||||
recallModel,
|
||||
recallScheduler,
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { createAction } from '@reduxjs/toolkit';
|
||||
import { ImageDTO, MainModelField, OnnxModelField } from 'services/api/types';
|
||||
|
||||
export const initialImageSelected = createAction<ImageDTO | string | undefined>(
|
||||
export const initialImageSelected = createAction<ImageDTO | undefined>(
|
||||
'generation/initialImageSelected'
|
||||
);
|
||||
|
||||
|
@ -1,21 +1,17 @@
|
||||
import type { PayloadAction } from '@reduxjs/toolkit';
|
||||
import { createSlice } from '@reduxjs/toolkit';
|
||||
import { DEFAULT_SCHEDULER_NAME } from 'app/constants';
|
||||
import { roundToMultiple } from 'common/util/roundDownToMultiple';
|
||||
import { configChanged } from 'features/system/store/configSlice';
|
||||
import {
|
||||
setAspectRatio,
|
||||
setShouldShowAdvancedOptions,
|
||||
} from 'features/ui/store/uiSlice';
|
||||
import { clamp } from 'lodash-es';
|
||||
import { ImageDTO, MainModelField, OnnxModelField } from 'services/api/types';
|
||||
import { clipSkipMap } from '../components/Parameters/Advanced/ParamClipSkip';
|
||||
import { clipSkipMap } from '../types/constants';
|
||||
import {
|
||||
CfgScaleParam,
|
||||
HeightParam,
|
||||
MainModelParam,
|
||||
NegativePromptParam,
|
||||
PositivePromptParam,
|
||||
PrecisionParam,
|
||||
SchedulerParam,
|
||||
SeedParam,
|
||||
StepsParam,
|
||||
@ -56,10 +52,13 @@ export interface GenerationState {
|
||||
verticalSymmetrySteps: number;
|
||||
model: MainModelField | OnnxModelField | null;
|
||||
vae: VaeModelParam | null;
|
||||
vaePrecision: PrecisionParam;
|
||||
seamlessXAxis: boolean;
|
||||
seamlessYAxis: boolean;
|
||||
clipSkip: number;
|
||||
shouldUseCpuNoise: boolean;
|
||||
shouldShowAdvancedOptions: boolean;
|
||||
aspectRatio: number | null;
|
||||
}
|
||||
|
||||
export const initialGenerationState: GenerationState = {
|
||||
@ -71,7 +70,7 @@ export const initialGenerationState: GenerationState = {
|
||||
perlin: 0,
|
||||
positivePrompt: '',
|
||||
negativePrompt: '',
|
||||
scheduler: DEFAULT_SCHEDULER_NAME,
|
||||
scheduler: 'euler',
|
||||
seamBlur: 16,
|
||||
seamSize: 96,
|
||||
seamSteps: 30,
|
||||
@ -92,10 +91,13 @@ export const initialGenerationState: GenerationState = {
|
||||
verticalSymmetrySteps: 0,
|
||||
model: null,
|
||||
vae: null,
|
||||
vaePrecision: 'fp32',
|
||||
seamlessXAxis: false,
|
||||
seamlessYAxis: false,
|
||||
clipSkip: 0,
|
||||
shouldUseCpuNoise: true,
|
||||
shouldShowAdvancedOptions: false,
|
||||
aspectRatio: null,
|
||||
};
|
||||
|
||||
const initialState: GenerationState = initialGenerationState;
|
||||
@ -245,12 +247,28 @@ export const generationSlice = createSlice({
|
||||
// null is a valid VAE!
|
||||
state.vae = action.payload;
|
||||
},
|
||||
vaePrecisionChanged: (state, action: PayloadAction<PrecisionParam>) => {
|
||||
state.vaePrecision = action.payload;
|
||||
},
|
||||
setClipSkip: (state, action: PayloadAction<number>) => {
|
||||
state.clipSkip = action.payload;
|
||||
},
|
||||
shouldUseCpuNoiseChanged: (state, action: PayloadAction<boolean>) => {
|
||||
state.shouldUseCpuNoise = action.payload;
|
||||
},
|
||||
setShouldShowAdvancedOptions: (state, action: PayloadAction<boolean>) => {
|
||||
state.shouldShowAdvancedOptions = action.payload;
|
||||
if (!action.payload) {
|
||||
state.clipSkip = 0;
|
||||
}
|
||||
},
|
||||
setAspectRatio: (state, action: PayloadAction<number | null>) => {
|
||||
const newAspectRatio = action.payload;
|
||||
state.aspectRatio = newAspectRatio;
|
||||
if (newAspectRatio) {
|
||||
state.height = roundToMultiple(state.width / newAspectRatio, 8);
|
||||
}
|
||||
},
|
||||
},
|
||||
extraReducers: (builder) => {
|
||||
builder.addCase(configChanged, (state, action) => {
|
||||
@ -274,12 +292,6 @@ export const generationSlice = createSlice({
|
||||
const advancedOptionsStatus = action.payload;
|
||||
if (!advancedOptionsStatus) state.clipSkip = 0;
|
||||
});
|
||||
builder.addCase(setAspectRatio, (state, action) => {
|
||||
const ratio = action.payload;
|
||||
if (ratio) {
|
||||
state.height = roundToMultiple(state.width / ratio, 8);
|
||||
}
|
||||
});
|
||||
},
|
||||
});
|
||||
|
||||
@ -323,6 +335,9 @@ export const {
|
||||
setSeamlessYAxis,
|
||||
setClipSkip,
|
||||
shouldUseCpuNoiseChanged,
|
||||
setShouldShowAdvancedOptions,
|
||||
setAspectRatio,
|
||||
vaePrecisionChanged,
|
||||
} = generationSlice.actions;
|
||||
|
||||
export default generationSlice.reducer;
|
||||
|
@ -4,3 +4,22 @@ export const MODEL_TYPE_MAP = {
|
||||
sdxl: 'Stable Diffusion XL',
|
||||
'sdxl-refiner': 'Stable Diffusion XL Refiner',
|
||||
};
|
||||
|
||||
export const clipSkipMap = {
|
||||
'sd-1': {
|
||||
maxClip: 12,
|
||||
markers: [0, 1, 2, 3, 4, 8, 12],
|
||||
},
|
||||
'sd-2': {
|
||||
maxClip: 24,
|
||||
markers: [0, 1, 2, 3, 5, 10, 15, 20, 24],
|
||||
},
|
||||
sdxl: {
|
||||
maxClip: 24,
|
||||
markers: [0, 1, 2, 3, 5, 10, 15, 20, 24],
|
||||
},
|
||||
'sdxl-refiner': {
|
||||
maxClip: 24,
|
||||
markers: [0, 1, 2, 3, 5, 10, 15, 20, 24],
|
||||
},
|
||||
};
|
||||
|
@ -1,4 +1,4 @@
|
||||
import { NUMPY_RAND_MAX, SCHEDULER_NAMES_AS_CONST } from 'app/constants';
|
||||
import { NUMPY_RAND_MAX } from 'app/constants';
|
||||
import { z } from 'zod';
|
||||
|
||||
/**
|
||||
@ -42,6 +42,42 @@ export const isValidNegativePrompt = (
|
||||
val: unknown
|
||||
): val is NegativePromptParam => zNegativePrompt.safeParse(val).success;
|
||||
|
||||
/**
|
||||
* Zod schema for SDXL positive style prompt parameter
|
||||
*/
|
||||
export const zPositiveStylePromptSDXL = z.string();
|
||||
/**
|
||||
* Type alias for SDXL positive style prompt parameter, inferred from its zod schema
|
||||
*/
|
||||
export type PositiveStylePromptSDXLParam = z.infer<
|
||||
typeof zPositiveStylePromptSDXL
|
||||
>;
|
||||
/**
|
||||
* Validates/type-guards a value as a SDXL positive style prompt parameter
|
||||
*/
|
||||
export const isValidSDXLPositiveStylePrompt = (
|
||||
val: unknown
|
||||
): val is PositiveStylePromptSDXLParam =>
|
||||
zPositiveStylePromptSDXL.safeParse(val).success;
|
||||
|
||||
/**
|
||||
* Zod schema for SDXL negative style prompt parameter
|
||||
*/
|
||||
export const zNegativeStylePromptSDXL = z.string();
|
||||
/**
|
||||
* Type alias for SDXL negative style prompt parameter, inferred from its zod schema
|
||||
*/
|
||||
export type NegativeStylePromptSDXLParam = z.infer<
|
||||
typeof zNegativeStylePromptSDXL
|
||||
>;
|
||||
/**
|
||||
* Validates/type-guards a value as a SDXL negative style prompt parameter
|
||||
*/
|
||||
export const isValidSDXLNegativeStylePrompt = (
|
||||
val: unknown
|
||||
): val is NegativeStylePromptSDXLParam =>
|
||||
zNegativeStylePromptSDXL.safeParse(val).success;
|
||||
|
||||
/**
|
||||
* Zod schema for steps parameter
|
||||
*/
|
||||
@ -73,7 +109,30 @@ export const isValidCfgScale = (val: unknown): val is CfgScaleParam =>
|
||||
/**
|
||||
* Zod schema for scheduler parameter
|
||||
*/
|
||||
export const zScheduler = z.enum(SCHEDULER_NAMES_AS_CONST);
|
||||
export const zScheduler = z.enum([
|
||||
'euler',
|
||||
'deis',
|
||||
'ddim',
|
||||
'ddpm',
|
||||
'dpmpp_2s',
|
||||
'dpmpp_2m',
|
||||
'dpmpp_2m_sde',
|
||||
'dpmpp_sde',
|
||||
'heun',
|
||||
'kdpm_2',
|
||||
'lms',
|
||||
'pndm',
|
||||
'unipc',
|
||||
'euler_k',
|
||||
'dpmpp_2s_k',
|
||||
'dpmpp_2m_k',
|
||||
'dpmpp_2m_sde_k',
|
||||
'dpmpp_sde_k',
|
||||
'heun_k',
|
||||
'lms_k',
|
||||
'euler_a',
|
||||
'kdpm_2_a',
|
||||
]);
|
||||
/**
|
||||
* Type alias for scheduler parameter, inferred from its zod schema
|
||||
*/
|
||||
@ -84,6 +143,31 @@ export type SchedulerParam = z.infer<typeof zScheduler>;
|
||||
export const isValidScheduler = (val: unknown): val is SchedulerParam =>
|
||||
zScheduler.safeParse(val).success;
|
||||
|
||||
export const SCHEDULER_LABEL_MAP: Record<SchedulerParam, string> = {
|
||||
euler: 'Euler',
|
||||
deis: 'DEIS',
|
||||
ddim: 'DDIM',
|
||||
ddpm: 'DDPM',
|
||||
dpmpp_sde: 'DPM++ SDE',
|
||||
dpmpp_2s: 'DPM++ 2S',
|
||||
dpmpp_2m: 'DPM++ 2M',
|
||||
dpmpp_2m_sde: 'DPM++ 2M SDE',
|
||||
heun: 'Heun',
|
||||
kdpm_2: 'KDPM 2',
|
||||
lms: 'LMS',
|
||||
pndm: 'PNDM',
|
||||
unipc: 'UniPC',
|
||||
euler_k: 'Euler Karras',
|
||||
dpmpp_sde_k: 'DPM++ SDE Karras',
|
||||
dpmpp_2s_k: 'DPM++ 2S Karras',
|
||||
dpmpp_2m_k: 'DPM++ 2M Karras',
|
||||
dpmpp_2m_sde_k: 'DPM++ 2M SDE Karras',
|
||||
heun_k: 'Heun Karras',
|
||||
lms_k: 'LMS Karras',
|
||||
euler_a: 'Euler Ancestral',
|
||||
kdpm_2_a: 'KDPM 2 Ancestral',
|
||||
};
|
||||
|
||||
/**
|
||||
* Zod schema for seed parameter
|
||||
*/
|
||||
@ -221,6 +305,20 @@ export type StrengthParam = z.infer<typeof zStrength>;
|
||||
export const isValidStrength = (val: unknown): val is StrengthParam =>
|
||||
zStrength.safeParse(val).success;
|
||||
|
||||
/**
|
||||
* Zod schema for a precision parameter
|
||||
*/
|
||||
export const zPrecision = z.enum(['fp16', 'fp32']);
|
||||
/**
|
||||
* Type alias for precision parameter, inferred from its zod schema
|
||||
*/
|
||||
export type PrecisionParam = z.infer<typeof zPrecision>;
|
||||
/**
|
||||
* Validates/type-guards a value as a precision parameter
|
||||
*/
|
||||
export const isValidPrecision = (val: unknown): val is PrecisionParam =>
|
||||
zPrecision.safeParse(val).success;
|
||||
|
||||
// /**
|
||||
// * Zod schema for BaseModelType
|
||||
// */
|
||||
|
@ -1,13 +1,12 @@
|
||||
import { log } from 'app/logging/useLogger';
|
||||
import { logger } from 'app/logging/logger';
|
||||
import { zControlNetModel } from 'features/parameters/types/parameterSchemas';
|
||||
import { ControlNetModelField } from 'services/api/types';
|
||||
|
||||
const moduleLog = log.child({ module: 'models' });
|
||||
|
||||
export const modelIdToControlNetModelParam = (
|
||||
controlNetModelId: string
|
||||
): ControlNetModelField | undefined => {
|
||||
const [base_model, model_type, model_name] = controlNetModelId.split('/');
|
||||
const log = logger('models');
|
||||
const [base_model, _model_type, model_name] = controlNetModelId.split('/');
|
||||
|
||||
const result = zControlNetModel.safeParse({
|
||||
base_model,
|
||||
@ -15,7 +14,7 @@ export const modelIdToControlNetModelParam = (
|
||||
});
|
||||
|
||||
if (!result.success) {
|
||||
moduleLog.error(
|
||||
log.error(
|
||||
{
|
||||
controlNetModelId,
|
||||
errors: result.error.format(),
|
||||
|
@ -1,12 +1,12 @@
|
||||
import { logger } from 'app/logging/logger';
|
||||
import { LoRAModelParam, zLoRAModel } from '../types/parameterSchemas';
|
||||
import { log } from 'app/logging/useLogger';
|
||||
|
||||
const moduleLog = log.child({ module: 'models' });
|
||||
|
||||
export const modelIdToLoRAModelParam = (
|
||||
loraModelId: string
|
||||
): LoRAModelParam | undefined => {
|
||||
const [base_model, model_type, model_name] = loraModelId.split('/');
|
||||
const log = logger('models');
|
||||
|
||||
const [base_model, _model_type, model_name] = loraModelId.split('/');
|
||||
|
||||
const result = zLoRAModel.safeParse({
|
||||
base_model,
|
||||
@ -14,7 +14,7 @@ export const modelIdToLoRAModelParam = (
|
||||
});
|
||||
|
||||
if (!result.success) {
|
||||
moduleLog.error(
|
||||
log.error(
|
||||
{
|
||||
loraModelId,
|
||||
errors: result.error.format(),
|
||||
|
@ -1,15 +1,14 @@
|
||||
import { logger } from 'app/logging/logger';
|
||||
import {
|
||||
MainModelParam,
|
||||
zMainModel,
|
||||
} from 'features/parameters/types/parameterSchemas';
|
||||
import { log } from 'app/logging/useLogger';
|
||||
|
||||
const moduleLog = log.child({ module: 'models' });
|
||||
|
||||
export const modelIdToMainModelParam = (
|
||||
mainModelId: string
|
||||
): MainModelParam | undefined => {
|
||||
const [base_model, model_type, model_name] = mainModelId.split('/');
|
||||
const log = logger('models');
|
||||
const [base_model, _model_type, model_name] = mainModelId.split('/');
|
||||
|
||||
const result = zMainModel.safeParse({
|
||||
base_model,
|
||||
@ -18,7 +17,7 @@ export const modelIdToMainModelParam = (
|
||||
});
|
||||
|
||||
if (!result.success) {
|
||||
moduleLog.error(
|
||||
log.error(
|
||||
{
|
||||
mainModelId,
|
||||
errors: result.error.format(),
|
||||
|
@ -1,12 +1,11 @@
|
||||
import { logger } from 'app/logging/logger';
|
||||
import { VaeModelParam, zVaeModel } from '../types/parameterSchemas';
|
||||
import { log } from 'app/logging/useLogger';
|
||||
|
||||
const moduleLog = log.child({ module: 'models' });
|
||||
|
||||
export const modelIdToVAEModelParam = (
|
||||
vaeModelId: string
|
||||
): VaeModelParam | undefined => {
|
||||
const [base_model, model_type, model_name] = vaeModelId.split('/');
|
||||
const log = logger('models');
|
||||
const [base_model, _model_type, model_name] = vaeModelId.split('/');
|
||||
|
||||
const result = zVaeModel.safeParse({
|
||||
base_model,
|
||||
@ -14,7 +13,7 @@ export const modelIdToVAEModelParam = (
|
||||
});
|
||||
|
||||
if (!result.success) {
|
||||
moduleLog.error(
|
||||
log.error(
|
||||
{
|
||||
vaeModelId,
|
||||
errors: result.error.format(),
|
||||
|
Reference in New Issue
Block a user