From be72765d02e51ddab6caaa8cce02db74be121543 Mon Sep 17 00:00:00 2001 From: psychedelicious <4822129+psychedelicious@users.noreply.github.com> Date: Sat, 20 Jan 2024 20:03:12 +1100 Subject: [PATCH] fix(ui): bump @invoke-ai/ui, fix TS issues --- invokeai/frontend/web/package.json | 6 +- invokeai/frontend/web/pnpm-lock.yaml | 102 +++++++++--------- .../InformationalPopover.tsx} | 75 +++++++------ .../constants.ts | 0 .../InvAutosizeTextarea.tsx | 40 ------- .../InvTextarea.stories.tsx | 21 ---- .../components/InvAutosizeTextarea/types.ts | 7 -- .../ParamControlAdapterControlMode.tsx | 7 +- .../ParamControlAdapterResizeMode.tsx | 7 +- .../parameters/ParamControlAdapterWeight.tsx | 7 +- .../components/DynamicPromptsPreviewModal.tsx | 2 +- .../ParamDynamicPromptsMaxPrompts.tsx | 11 +- .../components/ParamDynamicPromptsPreview.tsx | 50 +++++---- .../ParamDynamicPromptsSeedBehaviour.tsx | 13 ++- .../AddModelsPanel/AdvancedAddCheckpoint.tsx | 17 +-- .../AddModelsPanel/AdvancedAddDiffusers.tsx | 27 +++-- .../subpanels/MergeModelsPanel.tsx | 6 +- .../ModelManagerPanel/CheckpointModelEdit.tsx | 19 ++-- .../ModelManagerPanel/DiffusersModelEdit.tsx | 17 +-- .../ModelManagerPanel/LoRAModelEdit.tsx | 17 +-- .../TopRightPanel/WorkflowEditorSettings.tsx | 20 +++- .../Advanced/ParamCFGRescaleMultiplier.tsx | 7 +- .../components/Advanced/ParamClipSkip.tsx | 7 +- .../ParamCanvasCoherenceMode.tsx | 7 +- .../ParamCanvasCoherenceSteps.tsx | 7 +- .../ParamCanvasCoherenceStrength.tsx | 7 +- .../MaskAdjustment/ParamMaskBlur.tsx | 7 +- .../MaskAdjustment/ParamMaskBlurMethod.tsx | 7 +- .../InfillAndScaling/ParamInfillMethod.tsx | 7 +- .../ParamScaleBeforeProcessing.tsx | 7 +- .../components/Core/ParamCFGScale.tsx | 7 +- .../components/Core/ParamScheduler.tsx | 7 +- .../parameters/components/Core/ParamSteps.tsx | 7 +- .../ImageToImage/ImageToImageStrength.tsx | 7 +- .../components/Seed/ParamSeedNumberInput.tsx | 7 +- .../VAEModel/ParamVAEModelSelect.tsx | 11 +- .../components/VAEModel/ParamVAEPrecision.tsx | 7 +- .../components/QueueIterationsNumberInput.tsx | 6 +- .../SettingsModal/SettingsModal.tsx | 10 +- .../components/WorkflowLibraryPagination.tsx | 2 +- 40 files changed, 313 insertions(+), 292 deletions(-) rename invokeai/frontend/web/src/common/components/{IAIInformationalPopover/IAIInformationalPopover.tsx => InformationalPopover/InformationalPopover.tsx} (70%) rename invokeai/frontend/web/src/common/components/{IAIInformationalPopover => InformationalPopover}/constants.ts (100%) delete mode 100644 invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvAutosizeTextarea.tsx delete mode 100644 invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvTextarea.stories.tsx delete mode 100644 invokeai/frontend/web/src/common/components/InvAutosizeTextarea/types.ts diff --git a/invokeai/frontend/web/package.json b/invokeai/frontend/web/package.json index 0def97ea68..1d90180ef5 100644 --- a/invokeai/frontend/web/package.json +++ b/invokeai/frontend/web/package.json @@ -32,8 +32,8 @@ "fix": "eslint --fix . && prettier --log-level warn --write .", "preinstall": "npx only-allow pnpm", "postinstall": "pnpm run theme", - "theme": "chakra-cli tokens --strict-component-types --strict-token-types node_modules/@invoke-ai/ui", - "theme:watch": "chakra-cli tokens --strict-component-types --strict-token-types node_modules/@invoke-ai/ui --watch", + "theme": "chakra-cli tokens node_modules/@invoke-ai/ui", + "theme:watch": "chakra-cli tokens node_modules/@invoke-ai/ui --watch", "storybook": "storybook dev -p 6006", "build-storybook": "storybook build", "unimported": "npx unimported" @@ -66,7 +66,7 @@ "@emotion/react": "^11.11.3", "@emotion/styled": "^11.11.0", "@fontsource-variable/inter": "^5.0.16", - "@invoke-ai/ui": "file:/home/bat/Documents/Code/ui", + "@invoke-ai/ui": "^0.0.8", "@mantine/form": "6.0.21", "@nanostores/react": "^0.7.1", "@reduxjs/toolkit": "2.0.1", diff --git a/invokeai/frontend/web/pnpm-lock.yaml b/invokeai/frontend/web/pnpm-lock.yaml index bb18789305..6e84da6b86 100644 --- a/invokeai/frontend/web/pnpm-lock.yaml +++ b/invokeai/frontend/web/pnpm-lock.yaml @@ -53,8 +53,8 @@ dependencies: specifier: ^5.0.16 version: 5.0.16 '@invoke-ai/ui': - specifier: file:/home/bat/Documents/Code/ui - version: file:../../../../ui(@chakra-ui/anatomy@2.2.2)(@chakra-ui/icons@2.1.1)(@chakra-ui/layout@2.3.1)(@chakra-ui/portal@2.1.0)(@chakra-ui/react@2.8.2)(@chakra-ui/styled-system@2.9.2)(@chakra-ui/theme-tools@2.1.2)(@emotion/react@11.11.3)(@emotion/styled@11.11.0)(@fontsource-variable/inter@5.0.16)(@nanostores/react@0.7.1)(chakra-react-select@4.7.6)(framer-motion@10.18.0)(lodash-es@4.17.21)(nanostores@0.9.5)(overlayscrollbars-react@0.5.3)(overlayscrollbars@2.4.6)(react-dom@18.2.0)(react-i18next@14.0.0)(react-select@5.8.0)(react@18.2.0) + specifier: ^0.0.8 + version: 0.0.8(@chakra-ui/anatomy@2.2.2)(@chakra-ui/icons@2.1.1)(@chakra-ui/layout@2.3.1)(@chakra-ui/portal@2.1.0)(@chakra-ui/react@2.8.2)(@chakra-ui/styled-system@2.9.2)(@chakra-ui/theme-tools@2.1.2)(@emotion/react@11.11.3)(@emotion/styled@11.11.0)(@fontsource-variable/inter@5.0.16)(@nanostores/react@0.7.1)(chakra-react-select@4.7.6)(framer-motion@10.18.0)(lodash-es@4.17.21)(nanostores@0.9.5)(overlayscrollbars-react@0.5.3)(overlayscrollbars@2.4.6)(react-dom@18.2.0)(react-i18next@14.0.0)(react-select@5.8.0)(react@18.2.0) '@mantine/form': specifier: 6.0.21 version: 6.0.21(react@18.2.0) @@ -3688,6 +3688,54 @@ packages: resolution: {integrity: sha512-dvuCeX5fC9dXgJn9t+X5atfmgQAzUOWqS1254Gh0m6i8wKd10ebXkfNKiRK+1GWi/yTvvLDHpoxLr0xxxeslWw==} dev: true + /@invoke-ai/ui@0.0.8(@chakra-ui/anatomy@2.2.2)(@chakra-ui/icons@2.1.1)(@chakra-ui/layout@2.3.1)(@chakra-ui/portal@2.1.0)(@chakra-ui/react@2.8.2)(@chakra-ui/styled-system@2.9.2)(@chakra-ui/theme-tools@2.1.2)(@emotion/react@11.11.3)(@emotion/styled@11.11.0)(@fontsource-variable/inter@5.0.16)(@nanostores/react@0.7.1)(chakra-react-select@4.7.6)(framer-motion@10.18.0)(lodash-es@4.17.21)(nanostores@0.9.5)(overlayscrollbars-react@0.5.3)(overlayscrollbars@2.4.6)(react-dom@18.2.0)(react-i18next@14.0.0)(react-select@5.8.0)(react@18.2.0): + resolution: {integrity: sha512-FjW9rV2Bh1h+EDU5eMQH+oR4vpA77GBrAOdbuIezeDSVcmACU5tuJXIPxw121ZAsH2ioyhgGPMvfAsF1HkSigA==} + peerDependencies: + '@chakra-ui/anatomy': ^2.2.2 + '@chakra-ui/icons': ^2.1.1 + '@chakra-ui/layout': ^2.3.1 + '@chakra-ui/portal': ^2.1.0 + '@chakra-ui/react': ^2.8.2 + '@chakra-ui/styled-system': ^2.9.2 + '@chakra-ui/theme-tools': ^2.1.2 + '@emotion/react': ^11.11.3 + '@emotion/styled': ^11.11.0 + '@fontsource-variable/inter': ^5.0.16 + '@nanostores/react': ^0.7.1 + chakra-react-select: ^4.7.6 + framer-motion: ^10.18.0 + lodash-es: ^4.17.21 + nanostores: ^0.9.5 + overlayscrollbars: ^2.4.6 + overlayscrollbars-react: ^0.5.3 + react: ^18.2.0 + react-dom: ^18.2.0 + react-i18next: ^14.0.0 + react-select: ^5.8.0 + dependencies: + '@chakra-ui/anatomy': 2.2.2 + '@chakra-ui/icons': 2.1.1(@chakra-ui/system@2.6.2)(react@18.2.0) + '@chakra-ui/layout': 2.3.1(@chakra-ui/system@2.6.2)(react@18.2.0) + '@chakra-ui/portal': 2.1.0(react-dom@18.2.0)(react@18.2.0) + '@chakra-ui/react': 2.8.2(@emotion/react@11.11.3)(@emotion/styled@11.11.0)(@types/react@18.2.48)(framer-motion@10.18.0)(react-dom@18.2.0)(react@18.2.0) + '@chakra-ui/styled-system': 2.9.2 + '@chakra-ui/theme-tools': 2.1.2(@chakra-ui/styled-system@2.9.2) + '@emotion/react': 11.11.3(@types/react@18.2.48)(react@18.2.0) + '@emotion/styled': 11.11.0(@emotion/react@11.11.3)(@types/react@18.2.48)(react@18.2.0) + '@fontsource-variable/inter': 5.0.16 + '@nanostores/react': 0.7.1(nanostores@0.9.5)(react@18.2.0) + chakra-react-select: 4.7.6(@chakra-ui/form-control@2.2.0)(@chakra-ui/icon@3.2.0)(@chakra-ui/layout@2.3.1)(@chakra-ui/media-query@3.3.0)(@chakra-ui/menu@2.2.1)(@chakra-ui/spinner@2.1.0)(@chakra-ui/system@2.6.2)(@emotion/react@11.11.3)(@types/react@18.2.48)(react-dom@18.2.0)(react@18.2.0) + framer-motion: 10.18.0(react-dom@18.2.0)(react@18.2.0) + lodash-es: 4.17.21 + nanostores: 0.9.5 + overlayscrollbars: 2.4.6 + overlayscrollbars-react: 0.5.3(overlayscrollbars@2.4.6)(react@18.2.0) + react: 18.2.0 + react-dom: 18.2.0(react@18.2.0) + react-i18next: 14.0.0(i18next@23.7.16)(react-dom@18.2.0)(react@18.2.0) + react-select: 5.8.0(@types/react@18.2.48)(react-dom@18.2.0)(react@18.2.0) + dev: false + /@isaacs/cliui@8.0.2: resolution: {integrity: sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==} engines: {node: '>=12'} @@ -13745,53 +13793,3 @@ packages: react: 18.2.0 use-sync-external-store: 1.2.0(react@18.2.0) dev: false - - file:../../../../ui(@chakra-ui/anatomy@2.2.2)(@chakra-ui/icons@2.1.1)(@chakra-ui/layout@2.3.1)(@chakra-ui/portal@2.1.0)(@chakra-ui/react@2.8.2)(@chakra-ui/styled-system@2.9.2)(@chakra-ui/theme-tools@2.1.2)(@emotion/react@11.11.3)(@emotion/styled@11.11.0)(@fontsource-variable/inter@5.0.16)(@nanostores/react@0.7.1)(chakra-react-select@4.7.6)(framer-motion@10.18.0)(lodash-es@4.17.21)(nanostores@0.9.5)(overlayscrollbars-react@0.5.3)(overlayscrollbars@2.4.6)(react-dom@18.2.0)(react-i18next@14.0.0)(react-select@5.8.0)(react@18.2.0): - resolution: {directory: ../../../../ui, type: directory} - id: file:../../../../ui - name: '@invoke-ai/ui' - peerDependencies: - '@chakra-ui/anatomy': ^2.2.2 - '@chakra-ui/icons': ^2.1.1 - '@chakra-ui/layout': ^2.3.1 - '@chakra-ui/portal': ^2.1.0 - '@chakra-ui/react': ^2.8.2 - '@chakra-ui/styled-system': ^2.9.2 - '@chakra-ui/theme-tools': ^2.1.2 - '@emotion/react': ^11.11.3 - '@emotion/styled': ^11.11.0 - '@fontsource-variable/inter': ^5.0.16 - '@nanostores/react': ^0.7.1 - chakra-react-select: ^4.7.6 - framer-motion: ^10.18.0 - lodash-es: ^4.17.21 - nanostores: ^0.9.5 - overlayscrollbars: ^2.4.6 - overlayscrollbars-react: ^0.5.3 - react: ^18.2.0 - react-dom: ^18.2.0 - react-i18next: ^14.0.0 - react-select: ^5.8.0 - dependencies: - '@chakra-ui/anatomy': 2.2.2 - '@chakra-ui/icons': 2.1.1(@chakra-ui/system@2.6.2)(react@18.2.0) - '@chakra-ui/layout': 2.3.1(@chakra-ui/system@2.6.2)(react@18.2.0) - '@chakra-ui/portal': 2.1.0(react-dom@18.2.0)(react@18.2.0) - '@chakra-ui/react': 2.8.2(@emotion/react@11.11.3)(@emotion/styled@11.11.0)(@types/react@18.2.48)(framer-motion@10.18.0)(react-dom@18.2.0)(react@18.2.0) - '@chakra-ui/styled-system': 2.9.2 - '@chakra-ui/theme-tools': 2.1.2(@chakra-ui/styled-system@2.9.2) - '@emotion/react': 11.11.3(@types/react@18.2.48)(react@18.2.0) - '@emotion/styled': 11.11.0(@emotion/react@11.11.3)(@types/react@18.2.48)(react@18.2.0) - '@fontsource-variable/inter': 5.0.16 - '@nanostores/react': 0.7.1(nanostores@0.9.5)(react@18.2.0) - chakra-react-select: 4.7.6(@chakra-ui/form-control@2.2.0)(@chakra-ui/icon@3.2.0)(@chakra-ui/layout@2.3.1)(@chakra-ui/media-query@3.3.0)(@chakra-ui/menu@2.2.1)(@chakra-ui/spinner@2.1.0)(@chakra-ui/system@2.6.2)(@emotion/react@11.11.3)(@types/react@18.2.48)(react-dom@18.2.0)(react@18.2.0) - framer-motion: 10.18.0(react-dom@18.2.0)(react@18.2.0) - lodash-es: 4.17.21 - nanostores: 0.9.5 - overlayscrollbars: 2.4.6 - overlayscrollbars-react: 0.5.3(overlayscrollbars@2.4.6)(react@18.2.0) - react: 18.2.0 - react-dom: 18.2.0(react@18.2.0) - react-i18next: 14.0.0(i18next@23.7.16)(react-dom@18.2.0)(react@18.2.0) - react-select: 5.8.0(@types/react@18.2.48)(react-dom@18.2.0)(react@18.2.0) - dev: false diff --git a/invokeai/frontend/web/src/common/components/IAIInformationalPopover/IAIInformationalPopover.tsx b/invokeai/frontend/web/src/common/components/InformationalPopover/InformationalPopover.tsx similarity index 70% rename from invokeai/frontend/web/src/common/components/IAIInformationalPopover/IAIInformationalPopover.tsx rename to invokeai/frontend/web/src/common/components/InformationalPopover/InformationalPopover.tsx index 8248324a26..cd2b320155 100644 --- a/invokeai/frontend/web/src/common/components/IAIInformationalPopover/IAIInformationalPopover.tsx +++ b/invokeai/frontend/web/src/common/components/InformationalPopover/InformationalPopover.tsx @@ -28,51 +28,48 @@ type Props = { children: ReactElement; }; -const IAIInformationalPopover = ({ - feature, - children, - inPortal = true, - ...rest -}: Props) => { - const shouldEnableInformationalPopovers = useAppSelector( - (s) => s.system.shouldEnableInformationalPopovers - ); +export const InformationalPopover = memo( + ({ feature, children, inPortal = true, ...rest }: Props) => { + const shouldEnableInformationalPopovers = useAppSelector( + (s) => s.system.shouldEnableInformationalPopovers + ); - const data = useMemo(() => POPOVER_DATA[feature], [feature]); + const data = useMemo(() => POPOVER_DATA[feature], [feature]); - const popoverProps = useMemo( - () => merge(omit(data, ['image', 'href', 'buttonLabel']), rest), - [data, rest] - ); + const popoverProps = useMemo( + () => merge(omit(data, ['image', 'href', 'buttonLabel']), rest), + [data, rest] + ); - if (!shouldEnableInformationalPopovers) { - return children; - } + if (!shouldEnableInformationalPopovers) { + return children; + } - return ( - <Popover - isLazy - closeOnBlur={false} - trigger="hover" - variant="informational" - openDelay={OPEN_DELAY} - modifiers={POPPER_MODIFIERS} - placement="top" - {...popoverProps} - > - <PopoverTrigger>{children}</PopoverTrigger> - {inPortal ? ( - <Portal> + return ( + <Popover + isLazy + closeOnBlur={false} + trigger="hover" + variant="informational" + openDelay={OPEN_DELAY} + modifiers={POPPER_MODIFIERS} + placement="top" + {...popoverProps} + > + <PopoverTrigger>{children}</PopoverTrigger> + {inPortal ? ( + <Portal> + <Content data={data} feature={feature} /> + </Portal> + ) : ( <Content data={data} feature={feature} /> - </Portal> - ) : ( - <Content data={data} feature={feature} /> - )} - </Popover> - ); -}; + )} + </Popover> + ); + } +); -export default memo(IAIInformationalPopover); +InformationalPopover.displayName = 'InformationalPopover'; type ContentProps = { data?: PopoverData; diff --git a/invokeai/frontend/web/src/common/components/IAIInformationalPopover/constants.ts b/invokeai/frontend/web/src/common/components/InformationalPopover/constants.ts similarity index 100% rename from invokeai/frontend/web/src/common/components/IAIInformationalPopover/constants.ts rename to invokeai/frontend/web/src/common/components/InformationalPopover/constants.ts diff --git a/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvAutosizeTextarea.tsx b/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvAutosizeTextarea.tsx deleted file mode 100644 index b4c7e1ef5a..0000000000 --- a/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvAutosizeTextarea.tsx +++ /dev/null @@ -1,40 +0,0 @@ -import { Box, forwardRef, Textarea as ChakraTextarea } from '@invoke-ai/ui'; -import { useGlobalModifiersSetters } from 'common/hooks/useGlobalModifiers'; -import { stopPastePropagation } from 'common/util/stopPastePropagation'; -import type { KeyboardEvent } from 'react'; -import { memo, useCallback } from 'react'; -import ResizeTextarea from 'react-textarea-autosize'; - -import type { InvAutosizeTextareaProps } from './types'; - -export const InvAutosizeTextarea = memo( - forwardRef<InvAutosizeTextareaProps, typeof ResizeTextarea>( - (props: InvAutosizeTextareaProps, ref) => { - const { setShift } = useGlobalModifiersSetters(); - const onKeyUpDown = useCallback( - (e: KeyboardEvent<HTMLTextAreaElement>) => { - setShift(e.shiftKey); - }, - [setShift] - ); - return ( - <Box pos="relative"> - <ChakraTextarea - as={ResizeTextarea} - ref={ref} - overflow="scroll" - w="100%" - minRows={3} - minH={20} - onPaste={stopPastePropagation} - onKeyUp={onKeyUpDown} - onKeyDown={onKeyUpDown} - {...props} - /> - </Box> - ); - } - ) -); - -InvAutosizeTextarea.displayName = 'InvAutosizeTextarea'; diff --git a/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvTextarea.stories.tsx b/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvTextarea.stories.tsx deleted file mode 100644 index 3a7bd15d8e..0000000000 --- a/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/InvTextarea.stories.tsx +++ /dev/null @@ -1,21 +0,0 @@ -import type { Meta, StoryObj } from '@storybook/react'; - -import { InvAutosizeTextarea } from './InvAutosizeTextarea'; -import type { InvAutosizeTextareaProps } from './types'; - -const meta: Meta<typeof InvAutosizeTextarea> = { - title: 'Primitives/InvAutosizeTextarea', - tags: ['autodocs'], - component: InvAutosizeTextarea, -}; - -export default meta; -type Story = StoryObj<typeof InvAutosizeTextarea>; - -const Component = (props: InvAutosizeTextareaProps) => { - return <InvAutosizeTextarea {...props} />; -}; - -export const Default: Story = { - render: Component, -}; diff --git a/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/types.ts b/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/types.ts deleted file mode 100644 index 350428eaf7..0000000000 --- a/invokeai/frontend/web/src/common/components/InvAutosizeTextarea/types.ts +++ /dev/null @@ -1,7 +0,0 @@ -import type { TextareaProps as ChakraTextareaProps } from '@invoke-ai/ui'; -import type { TextareaAutosizeProps } from 'react-textarea-autosize'; - -export type InvAutosizeTextareaProps = Omit< - ChakraTextareaProps & TextareaAutosizeProps, - 'resize' ->; diff --git a/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterControlMode.tsx b/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterControlMode.tsx index 9819697990..1cee707bb6 100644 --- a/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterControlMode.tsx +++ b/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterControlMode.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { useControlAdapterControlMode } from 'features/controlAdapters/hooks/useControlAdapterControlMode'; import { useControlAdapterIsEnabled } from 'features/controlAdapters/hooks/useControlAdapterIsEnabled'; import { controlAdapterControlModeChanged } from 'features/controlAdapters/store/controlAdaptersSlice'; @@ -53,8 +54,10 @@ const ParamControlAdapterControlMode = ({ id }: Props) => { } return ( - <FormControl isDisabled={!isEnabled} feature="controlNetControlMode"> - <FormLabel>{t('controlnet.controlMode')}</FormLabel> + <FormControl isDisabled={!isEnabled}> + <InformationalPopover feature="controlNetControlMode"> + <FormLabel>{t('controlnet.controlMode')}</FormLabel> + </InformationalPopover> <Combobox value={value} options={CONTROL_MODE_DATA} diff --git a/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterResizeMode.tsx b/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterResizeMode.tsx index 4a652604a8..1ee1fdc2ca 100644 --- a/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterResizeMode.tsx +++ b/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterResizeMode.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { useControlAdapterIsEnabled } from 'features/controlAdapters/hooks/useControlAdapterIsEnabled'; import { useControlAdapterResizeMode } from 'features/controlAdapters/hooks/useControlAdapterResizeMode'; import { controlAdapterResizeModeChanged } from 'features/controlAdapters/store/controlAdaptersSlice'; @@ -54,8 +55,10 @@ const ParamControlAdapterResizeMode = ({ id }: Props) => { } return ( - <FormControl feature="controlNetResizeMode"> - <FormLabel>{t('controlnet.resizeMode')}</FormLabel> + <FormControl> + <InformationalPopover feature="controlNetResizeMode"> + <FormLabel>{t('controlnet.resizeMode')}</FormLabel> + </InformationalPopover> <Combobox value={value} options={options} diff --git a/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterWeight.tsx b/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterWeight.tsx index 95e3a99df5..27a4115ae7 100644 --- a/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterWeight.tsx +++ b/invokeai/frontend/web/src/features/controlAdapters/components/parameters/ParamControlAdapterWeight.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { useControlAdapterIsEnabled } from 'features/controlAdapters/hooks/useControlAdapterIsEnabled'; import { useControlAdapterWeight } from 'features/controlAdapters/hooks/useControlAdapterWeight'; import { controlAdapterWeightChanged } from 'features/controlAdapters/store/controlAdaptersSlice'; @@ -48,8 +49,10 @@ const ParamControlAdapterWeight = ({ id }: ParamControlAdapterWeightProps) => { } return ( - <FormControl isDisabled={!isEnabled} feature="controlNetWeight"> - <FormLabel>{t('controlnet.weight')}</FormLabel> + <FormControl isDisabled={!isEnabled}> + <InformationalPopover feature="controlNetWeight"> + <FormLabel>{t('controlnet.weight')}</FormLabel> + </InformationalPopover> <CompositeSlider value={weight} onChange={onChange} diff --git a/invokeai/frontend/web/src/features/dynamicPrompts/components/DynamicPromptsPreviewModal.tsx b/invokeai/frontend/web/src/features/dynamicPrompts/components/DynamicPromptsPreviewModal.tsx index 8a67e36874..1783ccf9d1 100644 --- a/invokeai/frontend/web/src/features/dynamicPrompts/components/DynamicPromptsPreviewModal.tsx +++ b/invokeai/frontend/web/src/features/dynamicPrompts/components/DynamicPromptsPreviewModal.tsx @@ -25,7 +25,7 @@ export const DynamicPromptsModal = memo(() => { <ModalContent w="80vw" h="80vh" maxW="unset" maxH="unset"> <ModalHeader>{t('dynamicPrompts.dynamicPrompts')}</ModalHeader> <ModalCloseButton /> - <ModalBody as={Flex} flexDir="column" gap={2} w="full" h="full" pb={4}> + <ModalBody as={Flex} flexDir="column" gap={4} w="full" h="full" pb={4}> <Flex gap={4}> <ParamDynamicPromptsSeedBehaviour /> <ParamDynamicPromptsMaxPrompts /> diff --git a/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsMaxPrompts.tsx b/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsMaxPrompts.tsx index e6f5616f13..cd0daaf22a 100644 --- a/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsMaxPrompts.tsx +++ b/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsMaxPrompts.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { maxPromptsChanged } from 'features/dynamicPrompts/store/dynamicPromptsSlice'; import { memo, useCallback } from 'react'; import { useTranslation } from 'react-i18next'; @@ -38,12 +39,10 @@ const ParamDynamicPromptsMaxPrompts = () => { ); return ( - <FormControl - isDisabled={isDisabled} - feature="dynamicPromptsMaxPrompts" - renderInfoPopoverInPortal={false} - > - <FormLabel>{t('dynamicPrompts.maxPrompts')}</FormLabel> + <FormControl isDisabled={isDisabled}> + <InformationalPopover feature="dynamicPromptsMaxPrompts" inPortal={false}> + <FormLabel>{t('dynamicPrompts.maxPrompts')}</FormLabel> + </InformationalPopover> <CompositeSlider min={sliderMin} max={sliderMax} diff --git a/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsPreview.tsx b/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsPreview.tsx index c6c424d479..4b5de0cb85 100644 --- a/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsPreview.tsx +++ b/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsPreview.tsx @@ -1,9 +1,17 @@ import type { ChakraProps } from '@invoke-ai/ui'; -import { Flex, ListItem, OrderedList, Spinner, Text } from '@invoke-ai/ui'; +import { + Flex, + FormControl, + FormLabel, + ListItem, + OrderedList, + Spinner, + Text, +} from '@invoke-ai/ui'; import { createMemoizedSelector } from 'app/store/createMemoizedSelector'; import { useAppSelector } from 'app/store/storeHooks'; import { IAINoContentFallback } from 'common/components/IAIImageFallback'; -import IAIInformationalPopover from 'common/components/IAIInformationalPopover/IAIInformationalPopover'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import ScrollableContent from 'common/components/OverlayScrollbars/ScrollableContent'; import { selectDynamicPromptsSlice } from 'features/dynamicPrompts/store/dynamicPromptsSlice'; import { memo, useMemo } from 'react'; @@ -36,29 +44,27 @@ const ParamDynamicPromptsPreview = () => { if (isError) { return ( - <IAIInformationalPopover feature="dynamicPrompts"> - <Flex - w="full" - h="full" - layerStyle="second" - alignItems="center" - justifyContent="center" - p={8} - > - <IAINoContentFallback - icon={PiWarningCircleBold} - label="Problem generating prompts" - /> - </Flex> - </IAIInformationalPopover> + <Flex + w="full" + h="full" + layerStyle="second" + alignItems="center" + justifyContent="center" + p={8} + > + <IAINoContentFallback + icon={PiWarningCircleBold} + label="Problem generating prompts" + /> + </Flex> ); } return ( - <> - <Text fontSize="sm" fontWeight="bold"> - {label} - </Text> + <FormControl orientation="vertical" w="full" h="full"> + <InformationalPopover feature="dynamicPrompts" inPortal={false}> + <FormLabel>{label}</FormLabel> + </InformationalPopover> <Flex w="full" h="full" @@ -96,7 +102,7 @@ const ParamDynamicPromptsPreview = () => { </Flex> )} </Flex> - </> + </FormControl> ); }; diff --git a/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsSeedBehaviour.tsx b/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsSeedBehaviour.tsx index 069f41ff3c..87a860ac89 100644 --- a/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsSeedBehaviour.tsx +++ b/invokeai/frontend/web/src/features/dynamicPrompts/components/ParamDynamicPromptsSeedBehaviour.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange, ComboboxOption } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { isSeedBehaviour, seedBehaviourChanged, @@ -44,11 +45,13 @@ const ParamDynamicPromptsSeedBehaviour = () => { ); return ( - <FormControl - feature="dynamicPromptsSeedBehaviour" - renderInfoPopoverInPortal={false} - > - <FormLabel>{t('dynamicPrompts.seedBehaviour.label')}</FormLabel> + <FormControl> + <InformationalPopover + feature="dynamicPromptsSeedBehaviour" + inPortal={false} + > + <FormLabel>{t('dynamicPrompts.seedBehaviour.label')}</FormLabel> + </InformationalPopover> <Combobox value={value} options={options} onChange={handleChange} /> </FormControl> ); diff --git a/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddCheckpoint.tsx b/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddCheckpoint.tsx index 1278f31667..0960c51417 100644 --- a/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddCheckpoint.tsx +++ b/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddCheckpoint.tsx @@ -3,6 +3,7 @@ import { Checkbox, Flex, FormControl, + FormErrorMessage, FormLabel, Input, } from '@invoke-ai/ui'; @@ -120,10 +121,7 @@ const AdvancedAddCheckpoint = (props: AdvancedAddCheckpointProps) => { return ( <form onSubmit={handleSubmit(onSubmit)} style={formStyles}> <Flex flexDirection="column" gap={2}> - <FormControl - isInvalid={Boolean(errors.model_name)} - error={errors.model_name?.message} - > + <FormControl isInvalid={Boolean(errors.model_name)}> <FormLabel>{t('modelManager.model')}</FormLabel> <Input {...register('model_name', { @@ -131,15 +129,15 @@ const AdvancedAddCheckpoint = (props: AdvancedAddCheckpointProps) => { value.trim().length > 3 || 'Must be at least 3 characters', })} /> + {errors.model_name?.message && ( + <FormErrorMessage>{errors.model_name?.message}</FormErrorMessage> + )} </FormControl> <BaseModelSelect<CheckpointModelConfig> control={control} name="base_model" /> - <FormControl - isInvalid={Boolean(errors.path)} - error={errors.path?.message} - > + <FormControl isInvalid={Boolean(errors.path)}> <FormLabel>{t('modelManager.modelLocation')}</FormLabel> <Input {...register('path', { @@ -148,6 +146,9 @@ const AdvancedAddCheckpoint = (props: AdvancedAddCheckpointProps) => { onBlur, })} /> + {errors.path?.message && ( + <FormErrorMessage>{errors.path?.message}</FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.description')}</FormLabel> diff --git a/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddDiffusers.tsx b/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddDiffusers.tsx index 2938662150..18e55ff686 100644 --- a/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddDiffusers.tsx +++ b/invokeai/frontend/web/src/features/modelManager/subpanels/AddModelsPanel/AdvancedAddDiffusers.tsx @@ -1,4 +1,11 @@ -import { Button, Flex, FormControl, FormLabel, Input } from '@invoke-ai/ui'; +import { + Button, + Flex, + FormControl, + FormErrorMessage, + FormLabel, + Input, +} from '@invoke-ai/ui'; import { useAppDispatch } from 'app/store/storeHooks'; import { setAdvancedAddScanModel } from 'features/modelManager/store/modelManagerSlice'; import BaseModelSelect from 'features/modelManager/subpanels/shared/BaseModelSelect'; @@ -103,10 +110,7 @@ const AdvancedAddDiffusers = (props: AdvancedAddDiffusersProps) => { return ( <form onSubmit={handleSubmit(onSubmit)} style={formStyles}> <Flex flexDirection="column" gap={2}> - <FormControl - isInvalid={Boolean(errors.model_name)} - error={errors.model_name?.message} - > + <FormControl isInvalid={Boolean(errors.model_name)}> <FormLabel>{t('modelManager.name')}</FormLabel> <Input {...register('model_name', { @@ -114,6 +118,9 @@ const AdvancedAddDiffusers = (props: AdvancedAddDiffusersProps) => { value.trim().length > 3 || 'Must be at least 3 characters', })} /> + {errors.model_name?.message && ( + <FormErrorMessage>{errors.model_name?.message}</FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.baseModel')}</FormLabel> @@ -122,10 +129,7 @@ const AdvancedAddDiffusers = (props: AdvancedAddDiffusersProps) => { name="base_model" /> </FormControl> - <FormControl - isInvalid={Boolean(errors.path)} - error={errors.path?.message} - > + <FormControl isInvalid={Boolean(errors.path)}> <FormLabel>{t('modelManager.modelLocation')}</FormLabel> <Input {...register('path', { @@ -133,7 +137,10 @@ const AdvancedAddDiffusers = (props: AdvancedAddDiffusersProps) => { value.trim().length > 0 || 'Must provide a path', onBlur, })} - /> + />{' '} + {errors.path?.message && ( + <FormErrorMessage>{errors.path?.message}</FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.description')}</FormLabel> diff --git a/invokeai/frontend/web/src/features/modelManager/subpanels/MergeModelsPanel.tsx b/invokeai/frontend/web/src/features/modelManager/subpanels/MergeModelsPanel.tsx index 94d6574c0e..8c113f5da5 100644 --- a/invokeai/frontend/web/src/features/modelManager/subpanels/MergeModelsPanel.tsx +++ b/invokeai/frontend/web/src/features/modelManager/subpanels/MergeModelsPanel.tsx @@ -7,6 +7,7 @@ import { CompositeSlider, Flex, FormControl, + FormHelperText, FormLabel, Input, Radio, @@ -318,7 +319,7 @@ const MergeModelsPanel = () => { gap={4} bg="base.800" > - <FormControl helperText={t('modelManager.modelMergeAlphaHelp')}> + <FormControl> <FormLabel>{t('modelManager.alpha')}</FormLabel> <CompositeSlider min={0.01} @@ -337,6 +338,9 @@ const MergeModelsPanel = () => { onChange={handleChangeModelMergeAlpha} onReset={handleResetModelMergeAlpha} /> + <FormHelperText> + {t('modelManager.modelMergeAlphaHelp')} + </FormHelperText> </FormControl> </Flex> diff --git a/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/CheckpointModelEdit.tsx b/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/CheckpointModelEdit.tsx index 7f76140555..549c725b34 100644 --- a/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/CheckpointModelEdit.tsx +++ b/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/CheckpointModelEdit.tsx @@ -5,6 +5,7 @@ import { Divider, Flex, FormControl, + FormErrorMessage, FormLabel, Input, Text, @@ -139,10 +140,7 @@ const CheckpointModelEdit = (props: CheckpointModelEditProps) => { > <form onSubmit={handleSubmit(onSubmit)}> <Flex flexDirection="column" overflowY="scroll" gap={4}> - <FormControl - isInvalid={Boolean(errors.model_name)} - error={errors.model_name?.message} - > + <FormControl isInvalid={Boolean(errors.model_name)}> <FormLabel>{t('modelManager.name')}</FormLabel> <Input {...register('model_name', { @@ -150,6 +148,11 @@ const CheckpointModelEdit = (props: CheckpointModelEditProps) => { value.trim().length > 3 || 'Must be at least 3 characters', })} /> + {errors.model_name?.message && ( + <FormErrorMessage> + {errors.model_name?.message} + </FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.description')}</FormLabel> @@ -163,10 +166,7 @@ const CheckpointModelEdit = (props: CheckpointModelEditProps) => { control={control} name="variant" /> - <FormControl - isInvalid={Boolean(errors.path)} - error={errors.path?.message} - > + <FormControl isInvalid={Boolean(errors.path)}> <FormLabel>{t('modelManager.modelLocation')}</FormLabel> <Input {...register('path', { @@ -174,6 +174,9 @@ const CheckpointModelEdit = (props: CheckpointModelEditProps) => { value.trim().length > 0 || 'Must provide a path', })} /> + {errors.path?.message && ( + <FormErrorMessage>{errors.path?.message}</FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.vaeLocation')}</FormLabel> diff --git a/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/DiffusersModelEdit.tsx b/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/DiffusersModelEdit.tsx index 03f7c7ffaf..a873d06e61 100644 --- a/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/DiffusersModelEdit.tsx +++ b/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/DiffusersModelEdit.tsx @@ -3,6 +3,7 @@ import { Divider, Flex, FormControl, + FormErrorMessage, FormLabel, Input, Text, @@ -103,10 +104,7 @@ const DiffusersModelEdit = (props: DiffusersModelEditProps) => { <form onSubmit={handleSubmit(onSubmit)}> <Flex flexDirection="column" overflowY="scroll" gap={4}> - <FormControl - isInvalid={Boolean(errors.model_name)} - error={errors.model_name?.message} - > + <FormControl isInvalid={Boolean(errors.model_name)}> <FormLabel>{t('modelManager.name')}</FormLabel> <Input {...register('model_name', { @@ -114,6 +112,9 @@ const DiffusersModelEdit = (props: DiffusersModelEditProps) => { value.trim().length > 3 || 'Must be at least 3 characters', })} /> + {errors.model_name?.message && ( + <FormErrorMessage>{errors.model_name?.message}</FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.description')}</FormLabel> @@ -127,10 +128,7 @@ const DiffusersModelEdit = (props: DiffusersModelEditProps) => { control={control} name="variant" /> - <FormControl - isInvalid={Boolean(errors.path)} - error={errors.path?.message} - > + <FormControl isInvalid={Boolean(errors.path)}> <FormLabel>{t('modelManager.modelLocation')}</FormLabel> <Input {...register('path', { @@ -138,6 +136,9 @@ const DiffusersModelEdit = (props: DiffusersModelEditProps) => { value.trim().length > 0 || 'Must provide a path', })} /> + {errors.path?.message && ( + <FormErrorMessage>{errors.path?.message}</FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.vaeLocation')}</FormLabel> diff --git a/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/LoRAModelEdit.tsx b/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/LoRAModelEdit.tsx index 3e0b4c91ee..67a6f5c1e5 100644 --- a/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/LoRAModelEdit.tsx +++ b/invokeai/frontend/web/src/features/modelManager/subpanels/ModelManagerPanel/LoRAModelEdit.tsx @@ -3,6 +3,7 @@ import { Divider, Flex, FormControl, + FormErrorMessage, FormLabel, Input, Text, @@ -104,10 +105,7 @@ const LoRAModelEdit = (props: LoRAModelEditProps) => { <form onSubmit={handleSubmit(onSubmit)}> <Flex flexDirection="column" overflowY="scroll" gap={4}> - <FormControl - isInvalid={Boolean(errors.model_name)} - error={errors.model_name?.message} - > + <FormControl isInvalid={Boolean(errors.model_name)}> <FormLabel>{t('modelManager.name')}</FormLabel> <Input {...register('model_name', { @@ -115,6 +113,9 @@ const LoRAModelEdit = (props: LoRAModelEditProps) => { value.trim().length > 3 || 'Must be at least 3 characters', })} /> + {errors.model_name?.message && ( + <FormErrorMessage>{errors.model_name?.message}</FormErrorMessage> + )} </FormControl> <FormControl> <FormLabel>{t('modelManager.description')}</FormLabel> @@ -125,10 +126,7 @@ const LoRAModelEdit = (props: LoRAModelEditProps) => { name="base_model" /> - <FormControl - isInvalid={Boolean(errors.path)} - error={errors.path?.message} - > + <FormControl isInvalid={Boolean(errors.path)}> <FormLabel>{t('modelManager.modelLocation')}</FormLabel> <Input {...register('path', { @@ -136,6 +134,9 @@ const LoRAModelEdit = (props: LoRAModelEditProps) => { value.trim().length > 0 || 'Must provide a path', })} /> + {errors.path?.message && ( + <FormErrorMessage>{errors.path?.message}</FormErrorMessage> + )} </FormControl> <Button type="submit" isLoading={isLoading}> {t('modelManager.updateModel')} diff --git a/invokeai/frontend/web/src/features/nodes/components/flow/panels/TopRightPanel/WorkflowEditorSettings.tsx b/invokeai/frontend/web/src/features/nodes/components/flow/panels/TopRightPanel/WorkflowEditorSettings.tsx index ebfa660141..99c4f38ba0 100644 --- a/invokeai/frontend/web/src/features/nodes/components/flow/panels/TopRightPanel/WorkflowEditorSettings.tsx +++ b/invokeai/frontend/web/src/features/nodes/components/flow/panels/TopRightPanel/WorkflowEditorSettings.tsx @@ -2,6 +2,7 @@ import { Divider, Flex, FormControl, + FormHelperText, FormLabel, Heading, Modal, @@ -110,46 +111,55 @@ const WorkflowEditorSettings = ({ children }: Props) => { <ModalBody> <Flex flexDirection="column" gap={4} py={4}> <Heading size="sm">{t('parameters.general')}</Heading> - <FormControl helperText={t('nodes.animatedEdgesHelp')}> + <FormControl> <FormLabel>{t('nodes.animatedEdges')}</FormLabel> <Switch onChange={handleChangeShouldAnimate} isChecked={shouldAnimateEdges} /> + <FormHelperText>{t('nodes.animatedEdgesHelp')}</FormHelperText> </FormControl> <Divider /> - <FormControl helperText={t('nodes.snapToGridHelp')}> + <FormControl> <FormLabel>{t('nodes.snapToGrid')}</FormLabel> <Switch isChecked={shouldSnapToGrid} onChange={handleChangeShouldSnap} /> + <FormHelperText>{t('nodes.snapToGridHelp')}</FormHelperText> </FormControl> <Divider /> - <FormControl helperText={t('nodes.colorCodeEdgesHelp')}> + <FormControl> <FormLabel>{t('nodes.colorCodeEdges')}</FormLabel> <Switch isChecked={shouldColorEdges} onChange={handleChangeShouldColor} /> + <FormHelperText>{t('nodes.colorCodeEdgesHelp')}</FormHelperText> </FormControl> <Divider /> - <FormControl helperText={t('nodes.fullyContainNodesHelp')}> + <FormControl> <FormLabel>{t('nodes.fullyContainNodes')}</FormLabel> <Switch isChecked={selectionModeIsChecked} onChange={handleChangeSelectionMode} /> + <FormHelperText> + {t('nodes.fullyContainNodesHelp')} + </FormHelperText> </FormControl> <Heading size="sm" pt={4}> {t('common.advanced')} </Heading> - <FormControl helperText={t('nodes.validateConnectionsHelp')}> + <FormControl> <FormLabel>{t('nodes.validateConnections')}</FormLabel> <Switch isChecked={shouldValidateGraph} onChange={handleChangeShouldValidate} /> + <FormHelperText> + {t('nodes.validateConnectionsHelp')} + </FormHelperText> </FormControl> <ReloadNodeTemplatesButton /> </Flex> diff --git a/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamCFGRescaleMultiplier.tsx b/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamCFGRescaleMultiplier.tsx index 19f9d6f7da..b1646b9b87 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamCFGRescaleMultiplier.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamCFGRescaleMultiplier.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setCfgRescaleMultiplier } from 'features/parameters/store/generationSlice'; import { memo, useCallback } from 'react'; import { useTranslation } from 'react-i18next'; @@ -44,8 +45,10 @@ const ParamCFGRescaleMultiplier = () => { ); return ( - <FormControl feature="paramCFGRescaleMultiplier"> - <FormLabel>{t('parameters.cfgRescaleMultiplier')}</FormLabel> + <FormControl> + <InformationalPopover feature="paramCFGRescaleMultiplier"> + <FormLabel>{t('parameters.cfgRescaleMultiplier')}</FormLabel> + </InformationalPopover> <CompositeSlider value={cfgRescaleMultiplier} defaultValue={initial} diff --git a/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamClipSkip.tsx b/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamClipSkip.tsx index 939bab747a..ffb2e76829 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamClipSkip.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Advanced/ParamClipSkip.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setClipSkip } from 'features/parameters/store/generationSlice'; import { CLIP_SKIP_MAP } from 'features/parameters/types/constants'; import { memo, useCallback, useMemo } from 'react'; @@ -50,8 +51,10 @@ const ParamClipSkip = () => { } return ( - <FormControl feature="clipSkip"> - <FormLabel>{t('parameters.clipSkip')}</FormLabel> + <FormControl> + <InformationalPopover feature="clipSkip"> + <FormLabel>{t('parameters.clipSkip')}</FormLabel> + </InformationalPopover> <CompositeSlider value={clipSkip} defaultValue={initial} diff --git a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceMode.tsx b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceMode.tsx index 1c6b538c50..fcdc1eee6f 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceMode.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceMode.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange, ComboboxOption } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setCanvasCoherenceMode } from 'features/parameters/store/generationSlice'; import { isParameterCanvasCoherenceMode } from 'features/parameters/types/parameterSchemas'; import { memo, useCallback, useMemo } from 'react'; @@ -39,8 +40,10 @@ const ParamCanvasCoherenceMode = () => { ); return ( - <FormControl feature="compositingCoherenceMode"> - <FormLabel>{t('parameters.coherenceMode')}</FormLabel> + <FormControl> + <InformationalPopover feature="compositingCoherenceMode"> + <FormLabel>{t('parameters.coherenceMode')}</FormLabel> + </InformationalPopover> <Combobox options={options} value={value} onChange={onChange} /> </FormControl> ); diff --git a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceSteps.tsx b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceSteps.tsx index 79fe2d171b..9f6ca54f7a 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceSteps.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceSteps.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setCanvasCoherenceSteps } from 'features/parameters/store/generationSlice'; import { memo, useCallback } from 'react'; import { useTranslation } from 'react-i18next'; @@ -46,8 +47,10 @@ const ParamCanvasCoherenceSteps = () => { ); return ( - <FormControl feature="compositingCoherenceSteps"> - <FormLabel>{t('parameters.coherenceSteps')}</FormLabel> + <FormControl> + <InformationalPopover feature="compositingCoherenceSteps"> + <FormLabel>{t('parameters.coherenceSteps')}</FormLabel> + </InformationalPopover> <CompositeSlider min={sliderMin} max={sliderMax} diff --git a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceStrength.tsx b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceStrength.tsx index 369bdb1f33..ecac32251e 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceStrength.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/CoherencePass/ParamCanvasCoherenceStrength.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setCanvasCoherenceStrength } from 'features/parameters/store/generationSlice'; import { memo, useCallback } from 'react'; import { useTranslation } from 'react-i18next'; @@ -24,8 +25,10 @@ const ParamCanvasCoherenceStrength = () => { ); return ( - <FormControl feature="compositingStrength"> - <FormLabel>{t('parameters.coherenceStrength')}</FormLabel> + <FormControl> + <InformationalPopover feature="compositingStrength"> + <FormLabel>{t('parameters.coherenceStrength')}</FormLabel> + </InformationalPopover> <CompositeSlider min={0} max={1} diff --git a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlur.tsx b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlur.tsx index aa491d39c4..dd250fb6b0 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlur.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlur.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setMaskBlur } from 'features/parameters/store/generationSlice'; import { memo, useCallback } from 'react'; import { useTranslation } from 'react-i18next'; @@ -33,8 +34,10 @@ const ParamMaskBlur = () => { ); return ( - <FormControl feature="compositingBlur"> - <FormLabel>{t('parameters.maskBlur')}</FormLabel> + <FormControl> + <InformationalPopover feature="compositingBlur"> + <FormLabel>{t('parameters.maskBlur')}</FormLabel> + </InformationalPopover> <CompositeSlider min={sliderMin} max={sliderMax} diff --git a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlurMethod.tsx b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlurMethod.tsx index d00ffa955a..b81da48b45 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlurMethod.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Canvas/Compositing/MaskAdjustment/ParamMaskBlurMethod.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange, ComboboxOption } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setMaskBlurMethod } from 'features/parameters/store/generationSlice'; import { isParameterMaskBlurMethod } from 'features/parameters/types/parameterSchemas'; import { memo, useCallback, useMemo } from 'react'; @@ -32,8 +33,10 @@ const ParamMaskBlurMethod = () => { ); return ( - <FormControl feature="compositingBlurMethod"> - <FormLabel>{t('parameters.maskBlurMethod')}</FormLabel> + <FormControl> + <InformationalPopover feature="compositingBlurMethod"> + <FormLabel>{t('parameters.maskBlurMethod')}</FormLabel> + </InformationalPopover> <Combobox value={value} onChange={onChange} options={options} /> </FormControl> ); diff --git a/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamInfillMethod.tsx b/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamInfillMethod.tsx index 51f4bcff9c..62a51fed2c 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamInfillMethod.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamInfillMethod.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange, ComboboxOption } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setInfillMethod } from 'features/parameters/store/generationSlice'; import { memo, useCallback, useMemo } from 'react'; import { useTranslation } from 'react-i18next'; @@ -38,8 +39,10 @@ const ParamInfillMethod = () => { ); return ( - <FormControl isDisabled={options.length === 0} feature="infillMethod"> - <FormLabel>{t('parameters.infillMethod')}</FormLabel> + <FormControl isDisabled={options.length === 0}> + <InformationalPopover feature="infillMethod"> + <FormLabel>{t('parameters.infillMethod')}</FormLabel> + </InformationalPopover> <Combobox value={value} options={options} onChange={onChange} /> </FormControl> ); diff --git a/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamScaleBeforeProcessing.tsx b/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamScaleBeforeProcessing.tsx index 340ec8932c..bf4b9be2ba 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamScaleBeforeProcessing.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Canvas/InfillAndScaling/ParamScaleBeforeProcessing.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange, ComboboxOption } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setBoundingBoxScaleMethod } from 'features/canvas/store/canvasSlice'; import { isBoundingBoxScaleMethod } from 'features/canvas/store/canvasTypes'; import { selectOptimalDimension } from 'features/parameters/store/generationSlice'; @@ -37,8 +38,10 @@ const ParamScaleBeforeProcessing = () => { ); return ( - <FormControl feature="scaleBeforeProcessing"> - <FormLabel>{t('parameters.scaleBeforeProcessing')}</FormLabel> + <FormControl> + <InformationalPopover feature="scaleBeforeProcessing"> + <FormLabel>{t('parameters.scaleBeforeProcessing')}</FormLabel> + </InformationalPopover> <Combobox value={value} options={OPTIONS} onChange={onChange} /> </FormControl> ); diff --git a/invokeai/frontend/web/src/features/parameters/components/Core/ParamCFGScale.tsx b/invokeai/frontend/web/src/features/parameters/components/Core/ParamCFGScale.tsx index 1b39bf4c88..985d5763a5 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Core/ParamCFGScale.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Core/ParamCFGScale.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setCfgScale } from 'features/parameters/store/generationSlice'; import { memo, useCallback, useMemo } from 'react'; import { useTranslation } from 'react-i18next'; @@ -34,8 +35,10 @@ const ParamCFGScale = () => { ); return ( - <FormControl feature="paramCFGScale"> - <FormLabel>{t('parameters.cfgScale')}</FormLabel> + <FormControl> + <InformationalPopover feature="paramCFGScale"> + <FormLabel>{t('parameters.cfgScale')}</FormLabel> + </InformationalPopover> <CompositeSlider value={cfgScale} defaultValue={initial} diff --git a/invokeai/frontend/web/src/features/parameters/components/Core/ParamScheduler.tsx b/invokeai/frontend/web/src/features/parameters/components/Core/ParamScheduler.tsx index 32a6d5fc38..08d0ae635f 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Core/ParamScheduler.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Core/ParamScheduler.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setScheduler } from 'features/parameters/store/generationSlice'; import { SCHEDULER_OPTIONS } from 'features/parameters/types/constants'; import { isParameterScheduler } from 'features/parameters/types/parameterSchemas'; @@ -28,8 +29,10 @@ const ParamScheduler = () => { ); return ( - <FormControl feature="paramScheduler"> - <FormLabel>{t('parameters.scheduler')}</FormLabel> + <FormControl> + <InformationalPopover feature="paramScheduler"> + <FormLabel>{t('parameters.scheduler')}</FormLabel> + </InformationalPopover> <Combobox value={value} options={SCHEDULER_OPTIONS} onChange={onChange} /> </FormControl> ); diff --git a/invokeai/frontend/web/src/features/parameters/components/Core/ParamSteps.tsx b/invokeai/frontend/web/src/features/parameters/components/Core/ParamSteps.tsx index 689fcd42c1..3401f503ea 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Core/ParamSteps.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Core/ParamSteps.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setSteps } from 'features/parameters/store/generationSlice'; import { memo, useCallback, useMemo } from 'react'; import { useTranslation } from 'react-i18next'; @@ -36,8 +37,10 @@ const ParamSteps = () => { ); return ( - <FormControl feature="paramSteps"> - <FormLabel>{t('parameters.steps')}</FormLabel> + <FormControl> + <InformationalPopover feature="paramSteps"> + <FormLabel>{t('parameters.steps')}</FormLabel> + </InformationalPopover> <CompositeSlider value={steps} defaultValue={initial} diff --git a/invokeai/frontend/web/src/features/parameters/components/ImageToImage/ImageToImageStrength.tsx b/invokeai/frontend/web/src/features/parameters/components/ImageToImage/ImageToImageStrength.tsx index 4637ea21ea..7f063aa841 100644 --- a/invokeai/frontend/web/src/features/parameters/components/ImageToImage/ImageToImageStrength.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/ImageToImage/ImageToImageStrength.tsx @@ -5,6 +5,7 @@ import { FormLabel, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setImg2imgStrength } from 'features/parameters/store/generationSlice'; import { memo, useCallback } from 'react'; import { useTranslation } from 'react-i18next'; @@ -39,8 +40,10 @@ const ImageToImageStrength = () => { ); return ( - <FormControl feature="paramDenoisingStrength"> - <FormLabel>{`${t('parameters.denoisingStrength')}`}</FormLabel> + <FormControl> + <InformationalPopover feature="paramDenoisingStrength"> + <FormLabel>{`${t('parameters.denoisingStrength')}`}</FormLabel> + </InformationalPopover> <CompositeSlider step={coarseStep} fineStep={fineStep} diff --git a/invokeai/frontend/web/src/features/parameters/components/Seed/ParamSeedNumberInput.tsx b/invokeai/frontend/web/src/features/parameters/components/Seed/ParamSeedNumberInput.tsx index ab33b3ac6e..be6a980927 100644 --- a/invokeai/frontend/web/src/features/parameters/components/Seed/ParamSeedNumberInput.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/Seed/ParamSeedNumberInput.tsx @@ -1,6 +1,7 @@ import { CompositeNumberInput, FormControl, FormLabel } from '@invoke-ai/ui'; import { NUMPY_RAND_MAX, NUMPY_RAND_MIN } from 'app/constants'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setSeed } from 'features/parameters/store/generationSlice'; import { memo, useCallback } from 'react'; import { useTranslation } from 'react-i18next'; @@ -21,8 +22,10 @@ export const ParamSeedNumberInput = memo(() => { ); return ( - <FormControl flexGrow={1} feature="paramSeed"> - <FormLabel>{t('parameters.seed')}</FormLabel> + <FormControl flexGrow={1}> + <InformationalPopover feature="paramSeed"> + <FormLabel>{t('parameters.seed')}</FormLabel> + </InformationalPopover> <CompositeNumberInput step={1} min={NUMPY_RAND_MIN} diff --git a/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEModelSelect.tsx b/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEModelSelect.tsx index 3188c1ae21..d0072442e7 100644 --- a/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEModelSelect.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEModelSelect.tsx @@ -1,6 +1,7 @@ import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { createMemoizedSelector } from 'app/store/createMemoizedSelector'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { useGroupedModelCombobox } from 'common/hooks/useGroupedModelCombobox'; import { selectGenerationSlice, @@ -46,12 +47,10 @@ const ParamVAEModelSelect = () => { }); return ( - <FormControl - isDisabled={!options.length} - isInvalid={!options.length} - feature="paramVAE" - > - <FormLabel>{t('modelManager.vae')}</FormLabel> + <FormControl isDisabled={!options.length} isInvalid={!options.length}> + <InformationalPopover feature="paramVAE"> + <FormLabel>{t('modelManager.vae')}</FormLabel> + </InformationalPopover> <Combobox isClearable value={value} diff --git a/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEPrecision.tsx b/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEPrecision.tsx index 24cbdb0925..14b4700dea 100644 --- a/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEPrecision.tsx +++ b/invokeai/frontend/web/src/features/parameters/components/VAEModel/ParamVAEPrecision.tsx @@ -1,6 +1,7 @@ import type { ComboboxOnChange } from '@invoke-ai/ui'; import { Combobox, FormControl, FormLabel } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { vaePrecisionChanged } from 'features/parameters/store/generationSlice'; import { isParameterPrecision } from 'features/parameters/types/parameterSchemas'; import { memo, useCallback, useMemo } from 'react'; @@ -33,8 +34,10 @@ const ParamVAEModelSelect = () => { ); return ( - <FormControl feature="paramVAEPrecision" w="14rem" flexShrink={0}> - <FormLabel>{t('modelManager.vaePrecision')}</FormLabel> + <FormControl w="14rem" flexShrink={0}> + <InformationalPopover feature="paramVAEPrecision"> + <FormLabel>{t('modelManager.vaePrecision')}</FormLabel> + </InformationalPopover> <Combobox value={value} options={options} onChange={onChange} /> </FormControl> ); diff --git a/invokeai/frontend/web/src/features/queue/components/QueueIterationsNumberInput.tsx b/invokeai/frontend/web/src/features/queue/components/QueueIterationsNumberInput.tsx index dc50c39b11..10707da730 100644 --- a/invokeai/frontend/web/src/features/queue/components/QueueIterationsNumberInput.tsx +++ b/invokeai/frontend/web/src/features/queue/components/QueueIterationsNumberInput.tsx @@ -1,6 +1,6 @@ import { CompositeNumberInput } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; -import IAIInformationalPopover from 'common/components/IAIInformationalPopover/IAIInformationalPopover'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import { setIterations } from 'features/parameters/store/generationSlice'; import { memo, useCallback } from 'react'; @@ -17,7 +17,7 @@ export const QueueIterationsNumberInput = memo(() => { ); return ( - <IAIInformationalPopover feature="paramIterations"> + <InformationalPopover feature="paramIterations"> <CompositeNumberInput step={coarseStep} fineStep={fineStep} @@ -34,7 +34,7 @@ export const QueueIterationsNumberInput = memo(() => { flexShrink={0} variant="iterations" /> - </IAIInformationalPopover> + </InformationalPopover> ); }); diff --git a/invokeai/frontend/web/src/features/system/components/SettingsModal/SettingsModal.tsx b/invokeai/frontend/web/src/features/system/components/SettingsModal/SettingsModal.tsx index 59dd6677e0..ed81e9de51 100644 --- a/invokeai/frontend/web/src/features/system/components/SettingsModal/SettingsModal.tsx +++ b/invokeai/frontend/web/src/features/system/components/SettingsModal/SettingsModal.tsx @@ -15,6 +15,7 @@ import { useDisclosure, } from '@invoke-ai/ui'; import { useAppDispatch, useAppSelector } from 'app/store/storeHooks'; +import { InformationalPopover } from 'common/components/InformationalPopover/InformationalPopover'; import ScrollableContent from 'common/components/OverlayScrollbars/ScrollableContent'; import { useClearStorage } from 'common/hooks/useClearStorage'; import { shouldUseCpuNoiseChanged } from 'features/parameters/store/generationSlice'; @@ -261,8 +262,13 @@ const SettingsModal = ({ children, config }: SettingsModalProps) => { onChange={handleChangeShouldAntialiasProgressImage} /> </FormControl> - <FormControl feature="noiseUseCPU"> - <FormLabel>{t('parameters.useCpuNoise')}</FormLabel> + <FormControl> + <InformationalPopover + feature="noiseUseCPU" + inPortal={false} + > + <FormLabel>{t('parameters.useCpuNoise')}</FormLabel> + </InformationalPopover> <Switch isChecked={shouldUseCpuNoise} onChange={handleChangeShouldUseCpuNoise} diff --git a/invokeai/frontend/web/src/features/workflowLibrary/components/WorkflowLibraryPagination.tsx b/invokeai/frontend/web/src/features/workflowLibrary/components/WorkflowLibraryPagination.tsx index 997e170942..d000d5863a 100644 --- a/invokeai/frontend/web/src/features/workflowLibrary/components/WorkflowLibraryPagination.tsx +++ b/invokeai/frontend/web/src/features/workflowLibrary/components/WorkflowLibraryPagination.tsx @@ -65,7 +65,7 @@ const WorkflowLibraryPagination = ({ page, setPage, data }: Props) => { w={10} isDisabled={data.pages === 1} onClick={p.page === page ? undefined : p.onClick} - variant={p.page === page ? 'invokeAI' : 'ghost'} + variant={p.page === page ? 'solid' : 'ghost'} key={p.page} transitionDuration="0s" // the delay in animation looks jank >