From 5af6ccdcdf4d5af2c417d043d548a40fe5189663 Mon Sep 17 00:00:00 2001 From: huyan Date: Fri, 14 Aug 2026 01:01:56 +0800 Subject: [PATCH 1/2] feat(quick-start): redesign character creation entry The previous entry mixed decorative copy with a tall form and unclear role examples. Introduce a bottom composer, style starters, rotating role ideas, and layered character motion. Creation services, routes, export behavior, and error handling remain unchanged. --- frontend/src/pages/quick-start/index.tsx | 236 ++++++++++-------- frontend/src/shared/ui/index.ts | 2 + frontend/src/shared/ui/kinetic-copy-cycle.css | 164 ++++++++++++ frontend/src/shared/ui/kinetic-copy-cycle.tsx | 164 ++++++++++++ 4 files changed, 458 insertions(+), 108 deletions(-) create mode 100644 frontend/src/shared/ui/kinetic-copy-cycle.css create mode 100644 frontend/src/shared/ui/kinetic-copy-cycle.tsx diff --git a/frontend/src/pages/quick-start/index.tsx b/frontend/src/pages/quick-start/index.tsx index a4517396..1c7447f0 100644 --- a/frontend/src/pages/quick-start/index.tsx +++ b/frontend/src/pages/quick-start/index.tsx @@ -7,6 +7,7 @@ import { type ChangeEvent, type FormEvent, } from 'react' +import { ArrowUp, ImageSquare, X } from '@phosphor-icons/react' import { Link, useNavigate, useParams, useSearchParams } from 'react-router' import { @@ -17,6 +18,7 @@ import { type WorkflowNodeType, } from '@/entities' import { ExportButton, type ExportPackageModel } from '@/features/export-package' +import { KineticCopyCycle, type KineticCopyMessage } from '@/shared/ui' import { quickStartService, type QuickStartEntryService, @@ -40,17 +42,50 @@ const STEP_LABELS: Record = { review: '审核', } -const EXAMPLES = [ +const STYLE_PROMPTS = [ { - label: '像素守夜人', - prompt: '一位提着风灯、披深色斗篷的像素守夜人', + title: '16-bit 日式 RPG', + detail: '清晰轮廓 · 明亮配色', + prompt: '16-bit 日式 RPG 像素风,清晰轮廓,明亮配色', }, { - label: '轻装信使', - prompt: '轻装信使,侧视像素风,轮廓清晰,动作轻快', + title: '暗黑哥特像素', + detail: '低饱和 · 强烈明暗', + prompt: '暗黑哥特像素风,低饱和配色,强烈明暗对比', }, + { + title: '温暖手绘像素', + detail: '柔和色彩 · 纸张质感', + prompt: '温暖手绘像素风,柔和配色,细腻纸张质感', + }, +] as const + +const ROLE_IDEAS = [ + '银色卷发、戴星形单片眼镜的裁缝', + '长着鹿角、披苔藓斗篷的邮差', + '戴透明水母帽、穿蓝色雨衣的药剂师', + '蓬松白胡子、背黄铜工具箱的机械师', + '紫色短发、戴猫耳耳机的情报员', + '披白羽斗篷、戴月牙面具的占星师', + '红色双辫、穿宽大飞行夹克的小飞行员', + '黑色卷发、戴珊瑚项链的海洋祭司', ] as const +const ROLE_IDEA_MESSAGES: readonly KineticCopyMessage[] = [ + { lines: ['想做一个什么角色?'], className: 'text-app-ink' }, + ...ROLE_IDEAS.map((idea) => ({ + prefix: '试试', + prefixClassName: + 'mr-3 font-mono text-[10px] font-bold tracking-[0.14em] text-app-faint sm:text-[11px]', + lines: [idea], + className: 'text-app-accent', + })), +] + +const ROLE_DEFAULT_MESSAGE: readonly KineticCopyMessage[] = [ + { lines: ['用文字塑造你的角色……'], className: 'text-app-ink' }, +] + function playtestPath(characterId: string, outfitId: string, actionId?: string): string { const path = `/playtest/${encodeURIComponent(characterId)}/${encodeURIComponent(outfitId)}` return actionId ? `${path}?${new URLSearchParams({ actionId })}` : path @@ -181,6 +216,8 @@ function QuickStartInput({ const fileInput = useRef(null) const submitAbortController = useRef(null) const unavailableReason = service.unavailableReason + const hasPrompt = Boolean(prompt.trim()) + const showStylePrompts = !hasPrompt && !templateFile useEffect( () => () => { @@ -232,140 +269,123 @@ function QuickStartInput({ } return ( -
+
-
-
-
-

- QUICK START / CREATE CHARACTER -

-

- 用一句角色设定, -
- 开始一条可追踪的制作流程。 -

-
- - AI 快捷创作 - -
- -
- +
+
+ -
- -
-
- {EXAMPLES.slice(1).map((example) => ( + {STYLE_PROMPTS.map((stylePrompt) => ( ))}
+
+
void submit(event)} - className="grid gap-3 rounded-[1.4rem] border border-app-line-strong bg-app-surface-raised p-4 shadow-app-panel sm:grid-cols-[1fr_auto]" + className="grid items-center gap-1.5 rounded-xl border border-app-line-strong bg-app-surface-raised p-1.5 shadow-app-panel transition-shadow focus-within:border-app-accent focus-within:shadow-[0_18px_48px_rgb(29_37_31/14%)] sm:grid-cols-[1fr_auto_auto]" > -