From a94626c192d436d0356581dfe112b2b2a3d6eb39 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=BE=90=E6=B6=9B?= Date: Tue, 7 Jan 2025 13:51:32 +0800 Subject: [PATCH] =?UTF-8?q?=E5=AE=8C=E6=88=90Mixer=E5=8A=9F=E8=83=BD?= =?UTF-8?q?=E7=9A=84=E8=AE=BE=E8=AE=A1=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 2 + src/pages/Mixer.module.css | 34 ++++++++++++++++ src/pages/Mixer.tsx | 79 ++++++++++++++++++++++++++++++++++++++ 3 files changed, 115 insertions(+) create mode 100644 src/pages/Mixer.module.css create mode 100644 src/pages/Mixer.tsx diff --git a/src/App.tsx b/src/App.tsx index 83384b1..e0d4022 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -5,6 +5,7 @@ import { Harmonies } from './pages/Harmonies'; import { Home } from './pages/Home'; import { LightenDarken } from './pages/LightenDarken'; import { MainLayout } from './pages/MainLayout'; +import { Mixer } from './pages/Mixer'; import { NewScheme } from './pages/NewScheme'; import { SchemeDetail } from './pages/SchemeDetail'; import { SchemeNotFound } from './pages/SchemeNotFound'; @@ -33,6 +34,7 @@ const routes = createBrowserRouter([ { path: 'tones', element: }, { path: 'tints-shades', element: }, { path: 'lighten-darken', element: }, + { path: 'mixer', element: }, ], }, ]); diff --git a/src/pages/Mixer.module.css b/src/pages/Mixer.module.css new file mode 100644 index 0000000..4c1f217 --- /dev/null +++ b/src/pages/Mixer.module.css @@ -0,0 +1,34 @@ +@layer pages { + .mixer_workspace { + flex-direction: column; + } + .mixer_content { + width: 100%; + display: flex; + flex-direction: row; + justify-content: space-around; + align-items: flex-start; + gap: var(--spacing-m); + .mixer_column { + display: flex; + flex-direction: column; + gap: var(--spacing-s); + font-size: var(--font-size-s); + .color_value_mode { + display: flex; + flex-direction: row; + align-items: center; + gap: var(--spacing-s); + font-size: var(--font-size-s); + } + .colors_booth { + display: flex; + flex-direction: row; + justify-content: center; + align-items: stretch; + gap: var(--spacing-xs); + min-height: 12em; + } + } + } +} diff --git a/src/pages/Mixer.tsx b/src/pages/Mixer.tsx new file mode 100644 index 0000000..bb8f65d --- /dev/null +++ b/src/pages/Mixer.tsx @@ -0,0 +1,79 @@ +import cx from 'clsx'; +import { useMemo, useState } from 'react'; +import { useColorFunction } from '../ColorFunctionContext'; +import { ColorPicker } from '../components/ColorPicker'; +import { FlexColorStand } from '../components/FlexColorStand'; +import { HSegmentedControl } from '../components/HSegmentedControl'; +import { LabeledPicker } from '../components/LabeledPicker'; +import { ScrollArea } from '../components/ScrollArea'; +import styles from './Mixer.module.css'; + +export function Mixer() { + const { colorFn } = useColorFunction(); + const [basicColor, setBasicColor] = useState('000000'); + const [mixColor, setMixColor] = useState('000000'); + const [mixRatio, setMixRatio] = useState(0); + const [mode, setMode] = useState<'hex' | 'rgb' | 'hsl' | 'lab' | 'oklch'>('hex'); + const mixedColor = useMemo(() => { + try { + if (!colorFn) { + return '000000'; + } + const mixed = colorFn.mix(basicColor, mixColor, mixRatio / 100); + return mixed; + } catch (e) { + console.error('[Mix Color]', e); + } + return '000000'; + }, [basicColor, mixColor, mixRatio]); + + return ( +
+
+

Color Mixer

+

Make a new color by mixing two colors.

+
+ +
+
+
Basic Color
+ +
+
+
Mix Color
+ + +
+
+
Mix Result
+
+ +
+
+ + +
+
+
+
+
+ ); +}