From f4a8595dacc20ff46b9c6e9a7506ac7870fba12c Mon Sep 17 00:00:00 2001 From: Pabloader Date: Wed, 15 Apr 2026 08:14:47 +0000 Subject: [PATCH] Add sampler to image generation settings. --- .../storywriter/components/settings/image.tsx | 41 +++++++++++++++++-- src/games/storywriter/contexts/state.tsx | 2 + src/games/storywriter/utils/llm.ts | 18 ++++++++ src/games/storywriter/utils/tools.ts | 3 +- 4 files changed, 59 insertions(+), 5 deletions(-) diff --git a/src/games/storywriter/components/settings/image.tsx b/src/games/storywriter/components/settings/image.tsx index 1b8780e..bcbcd29 100644 --- a/src/games/storywriter/components/settings/image.tsx +++ b/src/games/storywriter/components/settings/image.tsx @@ -3,11 +3,12 @@ import { useInputCallback } from "@common/hooks/useInputCallback"; import { useInputState } from "@common/hooks/useInputState"; import clsx from "clsx"; import styles from "../../assets/settings-modal.module.css"; +import LLM from "../../utils/llm"; import { DEFAULT_IMAGE_GENERATION_SETTINGS, useAppState } from "../../contexts/state"; export const ImageSettings = () => { const { imageGenerationSettings, dispatch } = useAppState(); - const { width, height, negative_prompt } = imageGenerationSettings; + const { width, height, negative_prompt, sampler_name } = imageGenerationSettings; const [widthDraft, setWidthDraft] = useInputState(String(width)); const [heightDraft, setHeightDraft] = useInputState(String(height)); @@ -15,14 +16,24 @@ export const ImageSettings = () => { const commitWidth = () => { const parsed = parseInt(widthDraft, 10); if (!isNaN(parsed) && parsed > 0) { - dispatch({ type: 'SET_IMAGE_GENERATION_SETTINGS', settings: { width: parsed } }); + const snapped = Math.max(64, Math.round(parsed / 64) * 64); + dispatch({ + type: 'SET_IMAGE_GENERATION_SETTINGS', + settings: { width: snapped } + }); + setWidthDraft(String(snapped)); } }; const commitHeight = () => { const parsed = parseInt(heightDraft, 10); if (!isNaN(parsed) && parsed > 0) { - dispatch({ type: 'SET_IMAGE_GENERATION_SETTINGS', settings: { height: parsed } }); + const snapped = Math.max(64, Math.round(parsed / 64) * 64); + dispatch({ + type: 'SET_IMAGE_GENERATION_SETTINGS', + settings: { height: snapped } + }); + setHeightDraft(String(snapped)); } }; @@ -30,8 +41,18 @@ export const ImageSettings = () => { dispatch({ type: 'SET_IMAGE_GENERATION_SETTINGS', settings: { negative_prompt: value } }); }, []); + const handleSamplerChange = useInputCallback((value) => { + dispatch({ + type: 'SET_IMAGE_GENERATION_SETTINGS', + settings: { sampler_name: value as LLM.ImageSamplerName }, + }); + }, []); + const handleReset = () => { - dispatch({ type: 'SET_IMAGE_GENERATION_SETTINGS', settings: DEFAULT_IMAGE_GENERATION_SETTINGS }); + dispatch({ + type: 'SET_IMAGE_GENERATION_SETTINGS', + settings: DEFAULT_IMAGE_GENERATION_SETTINGS, + }); setWidthDraft(String(DEFAULT_IMAGE_GENERATION_SETTINGS.width)); setHeightDraft(String(DEFAULT_IMAGE_GENERATION_SETTINGS.height)); }; @@ -70,6 +91,18 @@ export const ImageSettings = () => { onKeyDown={(e) => e.key === 'Enter' && commitHeight()} /> +
+ + +