feat: Add DWPose to Linear UI

This commit is contained in:
blessedcoolant 2024-02-10 01:44:15 +05:30 committed by Kent Keirsey
parent 675c73c94f
commit f7998b4be0
7 changed files with 1812 additions and 26 deletions

View File

@ -235,6 +235,9 @@
"fill": "Fill",
"h": "H",
"handAndFace": "Hand and Face",
"face": "Face",
"body": "Body",
"hands": "Hands",
"hed": "HED",
"hedDescription": "Holistically-Nested Edge Detection",
"hideAdvanced": "Hide Advanced",
@ -263,6 +266,8 @@
"normalBaeDescription": "Normal BAE processing",
"openPose": "Openpose",
"openPoseDescription": "Human pose estimation using Openpose",
"dwPose": "DWPose",
"dwPoseDescription": "Human pose estimation using DWPose",
"pidi": "PIDI",
"pidiDescription": "PIDI image processing",
"processor": "Processor",

View File

@ -6,6 +6,7 @@ import CannyProcessor from './processors/CannyProcessor';
import ColorMapProcessor from './processors/ColorMapProcessor';
import ContentShuffleProcessor from './processors/ContentShuffleProcessor';
import DepthAnyThingProcessor from './processors/DepthAnyThingProcessor';
import DWPoseProcessor from './processors/DWPoseProcessor';
import HedProcessor from './processors/HedProcessor';
import LineartAnimeProcessor from './processors/LineartAnimeProcessor';
import LineartProcessor from './processors/LineartProcessor';
@ -77,6 +78,10 @@ const ControlAdapterProcessorComponent = ({ id }: Props) => {
return <OpenposeProcessor controlNetId={id} processorNode={processorNode} isEnabled={isEnabled} />;
}
if (processorNode.type === 'dwpose_image_processor') {
return <DWPoseProcessor controlNetId={id} processorNode={processorNode} isEnabled={isEnabled} />;
}
if (processorNode.type === 'pidi_image_processor') {
return <PidiProcessor controlNetId={id} processorNode={processorNode} isEnabled={isEnabled} />;
}

View File

@ -0,0 +1,66 @@
import { Flex, FormControl, FormLabel, Switch } from '@invoke-ai/ui-library';
import { useProcessorNodeChanged } from 'features/controlAdapters/components/hooks/useProcessorNodeChanged';
import { CONTROLNET_PROCESSORS } from 'features/controlAdapters/store/constants';
import type { RequiredDWPoseImageProcessorInvocation } from 'features/controlAdapters/store/types';
import type { ChangeEvent } from 'react';
import { memo, useCallback } from 'react';
import { useTranslation } from 'react-i18next';
import ProcessorWrapper from './common/ProcessorWrapper';
const DEFAULTS = CONTROLNET_PROCESSORS.dwpose_image_processor.default as RequiredDWPoseImageProcessorInvocation;
type Props = {
controlNetId: string;
processorNode: RequiredDWPoseImageProcessorInvocation;
isEnabled: boolean;
};
const DWPoseProcessor = (props: Props) => {
const { controlNetId, processorNode, isEnabled } = props;
const { draw_body, draw_face, draw_hands } = processorNode;
const processorChanged = useProcessorNodeChanged();
const { t } = useTranslation();
const handleDrawBodyChanged = useCallback(
(e: ChangeEvent<HTMLInputElement>) => {
processorChanged(controlNetId, { draw_body: e.target.checked });
},
[controlNetId, processorChanged]
);
const handleDrawFaceChanged = useCallback(
(e: ChangeEvent<HTMLInputElement>) => {
processorChanged(controlNetId, { draw_face: e.target.checked });
},
[controlNetId, processorChanged]
);
const handleDrawHandsChanged = useCallback(
(e: ChangeEvent<HTMLInputElement>) => {
processorChanged(controlNetId, { draw_hands: e.target.checked });
},
[controlNetId, processorChanged]
);
return (
<ProcessorWrapper>
<Flex sx={{ flexDir: 'row', gap: 6 }}>
<FormControl isDisabled={!isEnabled} w="max-content">
<FormLabel>{t('controlnet.body')}</FormLabel>
<Switch defaultChecked={DEFAULTS.draw_body} isChecked={draw_body} onChange={handleDrawBodyChanged} />
</FormControl>
<FormControl isDisabled={!isEnabled} w="max-content">
<FormLabel>{t('controlnet.face')}</FormLabel>
<Switch defaultChecked={DEFAULTS.draw_face} isChecked={draw_face} onChange={handleDrawFaceChanged} />
</FormControl>
<FormControl isDisabled={!isEnabled} w="max-content">
<FormLabel>{t('controlnet.hands')}</FormLabel>
<Switch defaultChecked={DEFAULTS.draw_hands} isChecked={draw_hands} onChange={handleDrawHandsChanged} />
</FormControl>
</Flex>
</ProcessorWrapper>
);
};
export default memo(DWPoseProcessor);

View File

@ -221,6 +221,22 @@ export const CONTROLNET_PROCESSORS: ControlNetProcessorsDict = {
hand_and_face: false,
},
},
dwpose_image_processor: {
type: 'dwpose_image_processor',
get label() {
return i18n.t('controlnet.dwPose');
},
get description() {
return i18n.t('controlnet.dwPoseDescription');
},
default: {
id: 'dwpose_image_processor',
type: 'dwpose_image_processor',
draw_body: true,
draw_face: false,
draw_hands: false,
},
},
pidi_image_processor: {
type: 'pidi_image_processor',
get label() {
@ -266,7 +282,7 @@ export const CONTROLNET_MODEL_DEFAULT_PROCESSORS: {
lineart_anime: 'lineart_anime_image_processor',
softedge: 'hed_image_processor',
shuffle: 'content_shuffle_image_processor',
openpose: 'openpose_image_processor',
openpose: 'dwpose_image_processor',
mediapipe: 'mediapipe_face_processor',
pidi: 'pidi_image_processor',
zoe: 'zoe_depth_image_processor',

View File

@ -11,6 +11,7 @@ import type {
ColorMapImageProcessorInvocation,
ContentShuffleImageProcessorInvocation,
DepthAnythingImageProcessorInvocation,
DWPoseImageProcessorInvocation,
HedImageProcessorInvocation,
LineartAnimeImageProcessorInvocation,
LineartImageProcessorInvocation,
@ -41,6 +42,7 @@ export type ControlAdapterProcessorNode =
| MlsdImageProcessorInvocation
| NormalbaeImageProcessorInvocation
| OpenposeImageProcessorInvocation
| DWPoseImageProcessorInvocation
| PidiImageProcessorInvocation
| ZoeDepthImageProcessorInvocation;
@ -150,6 +152,14 @@ export type RequiredOpenposeImageProcessorInvocation = O.Required<
'type' | 'detect_resolution' | 'image_resolution' | 'hand_and_face'
>;
/**
* The DWPose processor node, with parameters flagged as required
*/
export type RequiredDWPoseImageProcessorInvocation = O.Required<
DWPoseImageProcessorInvocation,
'type' | 'draw_body' | 'draw_face' | 'draw_hands'
>;
/**
* The Pidi processor node, with parameters flagged as required
*/
@ -180,6 +190,7 @@ export type RequiredControlAdapterProcessorNode =
| RequiredMlsdImageProcessorInvocation
| RequiredNormalbaeImageProcessorInvocation
| RequiredOpenposeImageProcessorInvocation
| RequiredDWPoseImageProcessorInvocation
| RequiredPidiImageProcessorInvocation
| RequiredZoeDepthImageProcessorInvocation,
'id'
@ -308,6 +319,16 @@ export const isOpenposeImageProcessorInvocation = (obj: unknown): obj is Openpos
return false;
};
/**
* Type guard for DWPoseImageProcessorInvocation
*/
export const isDWPoseImageProcessorInvocation = (obj: unknown): obj is DWPoseImageProcessorInvocation => {
if (isObject(obj) && 'type' in obj && obj.type === 'dwpose_image_processor') {
return true;
}
return false;
};
/**
* Type guard for PidiImageProcessorInvocation
*/

File diff suppressed because one or more lines are too long

View File

@ -157,6 +157,7 @@ export type MidasDepthImageProcessorInvocation = s['MidasDepthImageProcessorInvo
export type MlsdImageProcessorInvocation = s['MlsdImageProcessorInvocation'];
export type NormalbaeImageProcessorInvocation = s['NormalbaeImageProcessorInvocation'];
export type OpenposeImageProcessorInvocation = s['OpenposeImageProcessorInvocation'];
export type DWPoseImageProcessorInvocation = s['DWPoseImageProcessorInvocation'];
export type PidiImageProcessorInvocation = s['PidiImageProcessorInvocation'];
export type ZoeDepthImageProcessorInvocation = s['ZoeDepthImageProcessorInvocation'];