diff --git a/src/app/page.tsx b/src/app/page.tsx index b640db1..05a054c 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -57,7 +57,7 @@ const palette72Keys = ["A3", "A4", "A6", "A7", "A10", "A11", "A13", "B3", "B5", // const palette24Keys = [...]; const paletteOptions = { - 'all': { name: `221全实色`, keys: allPaletteKeys }, + 'all': { name: `全色系291色`, keys: allPaletteKeys }, '168': { name: '168色', keys: palette168Keys }, '144': { name: '144色', keys: palette144Keys }, '120': { name: '120色', keys: palette120Keys }, @@ -155,6 +155,7 @@ interface MappedPixel { export default function Home() { const [originalImageSrc, setOriginalImageSrc] = useState(null); const [granularity, setGranularity] = useState(50); // Example default + const [granularityInput, setGranularityInput] = useState("50"); // ++ 新增:输入框状态 ++ const [similarityThreshold, setSimilarityThreshold] = useState(30); // Example default for merging const [selectedPaletteKeySet, setSelectedPaletteKeySet] = useState('all'); // Use 'all' or another valid key const [activeBeadPalette, setActiveBeadPalette] = useState(() => { @@ -195,6 +196,10 @@ export default function Home() { setActiveBeadPalette(newActiveBeadPalette); }, [selectedPaletteKeySet, excludedColorKeys, remapTrigger]); // ++ 添加 remapTrigger 依赖 ++ + // ++ 添加:当granularity状态改变时同步更新输入框的值 ++ + useEffect(() => { + setGranularityInput(granularity.toString()); + }, [granularity]); // ++ Calculate unique colors currently on the grid for the palette ++ const currentGridColors = useMemo(() => { @@ -250,6 +255,10 @@ export default function Home() { setColorCounts(null); setTotalBeadCount(0); setInitialGridColorKeys(null); // ++ 重置初始键 ++ + // ++ 重置横轴格子数量为默认值 ++ + const defaultGranularity = 50; + setGranularity(defaultGranularity); + setGranularityInput(defaultGranularity.toString()); setRemapTrigger(prev => prev + 1); // Trigger full remap for new image }; reader.onerror = () => { @@ -263,13 +272,35 @@ export default function Home() { setSelectedColor(null); }; - const handleGranularityChange = (event: ChangeEvent) => { - const newGranularity = parseInt(event.target.value, 10); - setGranularity(newGranularity); - setRemapTrigger(prev => prev + 1); // Trigger full remap - // ++ Exit manual coloring mode if parameters change ++ - setIsManualColoringMode(false); - setSelectedColor(null); + // ++ 新增:处理输入框变化的函数 ++ + const handleGranularityInputChange = (event: ChangeEvent) => { + setGranularityInput(event.target.value); + }; + + // ++ 新增:处理确认按钮点击的函数 ++ + const handleConfirmGranularity = () => { + const minGranularity = 10; + const maxGranularity = 100; + let newGranularity = parseInt(granularityInput, 10); + + if (isNaN(newGranularity) || newGranularity < minGranularity) { + newGranularity = minGranularity; + } else if (newGranularity > maxGranularity) { + newGranularity = maxGranularity; + } + + // 只有在值确实改变时才触发更新 + if (newGranularity !== granularity) { + console.log(`Confirming new granularity: ${newGranularity}`); + setGranularity(newGranularity); // 更新主状态 + setRemapTrigger(prev => prev + 1); // 触发重映射 + // ++ Exit manual coloring mode if parameters change ++ + setIsManualColoringMode(false); + setSelectedColor(null); + } + + // 总是将输入框的值同步为验证后的值(避免显示非法值) + setGranularityInput(newGranularity.toString()); }; const handlePaletteChange = (event: ChangeEvent) => { @@ -297,7 +328,7 @@ export default function Home() { // Core function: Pixelate the image const pixelateImage = (imageSrc: string, detailLevel: number, threshold: number, currentPalette: PaletteColor[]) => { - console.log(`Attempting to pixelate with threshold: ${threshold}`); + console.log(`Attempting to pixelate with detail: ${detailLevel}, threshold: ${threshold}`); // ++ 修改日志,添加detail参数 ++ const originalCanvas = originalCanvasRef.current; const pixelatedCanvas = pixelatedCanvasRef.current; @@ -1202,14 +1233,31 @@ export default function Home() { {/* ++ HIDE Control Row in manual mode ++ */} {!isManualColoringMode && (
- {/* Granularity Slider */} + {/* ++ 修改:Granularity 输入框和按钮 ++ */}
- - -
-
+ +
+ e.key === 'Enter' && handleConfirmGranularity()} + className="w-full p-1.5 border border-gray-300 rounded-md text-sm focus:ring-blue-500 focus:border-blue-500 h-9" + /> + +
+
{/* Similarity Threshold Slider */}