fix(web): 审稿面板去重标题/去英文 slug + 伏笔待登记数实时递减 + 移动端决策栏 + 对比度修复

This commit is contained in:
Yaojia Wang
2026-06-30 08:56:23 +02:00
parent 69030eacc3
commit f0f925b195
6 changed files with 114 additions and 40 deletions

View File

@@ -6,6 +6,9 @@ import { useRouter } from "next/navigation";
import {
AlertTriangle,
CheckCircle2,
ChevronDown,
ClipboardCheck,
LocateFixed,
RotateCcw,
Square,
} from "lucide-react";
@@ -101,6 +104,11 @@ export function ReviewReport({
const editorRef = useRef<HTMLTextAreaElement>(null);
// 回炉中漂移段在终稿里定位到的原文null=未打开 RefineView。内容锚定位非位置 idx。
const [refineText, setRefineText] = useState<string | null>(null);
// 伏笔「仍待处理」数:由 ForeshadowSuggestions 上抛(已登记/已回收的已扣除)。
// null=尚未上报,回退到原始建议数,避免首帧闪「无建议」。
const [foreshadowRemaining, setForeshadowRemaining] = useState<number | null>(
null,
);
const seededRef = useRef(false);
// 进页一次性把历史留痕(冲突 + 伏笔建议 + 节奏)种入流状态(无需重审即可裁决/查看)。
@@ -143,6 +151,8 @@ export function ReviewReport({
const foreshadow = review.state.foreshadow;
const pace = review.state.pace;
const style = review.state.style;
// 伏笔徽标/验收预览统一用「仍待处理数」(随登记/回收递减);未上报前回退原始建议数。
const foreshadowOpen = foreshadowRemaining ?? foreshadow.length;
const sectionStatus = (name: string): string | undefined =>
review.state.sections.find((s) => s.name === name)?.status;
@@ -469,6 +479,8 @@ export function ReviewReport({
conflicts={conflicts}
focusedIndex={focusedIndex}
onAnchorClick={focusRegion}
projectId={project.id}
chapterNo={chapterNo}
editorRef={editorRef}
/>
</div>
@@ -490,7 +502,6 @@ export function ReviewReport({
<div className="space-y-3">
<ReviewSectionPanel
title="一致性"
subtitle="continuity"
statusLabel={
reviewing
? "审稿中"
@@ -537,7 +548,7 @@ export function ReviewReport({
<details
key={group.type}
open={unresolvedInGroup > 0}
className="rounded border border-line/70 bg-bg/35 p-2"
className="group rounded border border-line/70 bg-bg/35 p-2"
>
<summary className="flex cursor-pointer list-none items-center justify-between gap-2 text-xs font-semibold text-ink">
<span className="flex items-center gap-2">
@@ -550,10 +561,16 @@ export function ReviewReport({
{group.items.length}
</Badge>
</span>
<span className="font-mono text-[11px] text-ink-soft">
{unresolvedInGroup > 0
? `${unresolvedInGroup} 未裁决`
: "已处理"}
<span className="flex items-center gap-1.5">
<span className="font-mono text-2xs text-ink-soft">
{unresolvedInGroup > 0
? `${unresolvedInGroup} 未裁决`
: "已处理"}
</span>
<ChevronDown
className="h-4 w-4 text-ink-soft transition-transform group-open:rotate-180"
aria-hidden="true"
/>
</span>
</summary>
<ul className="mt-3 space-y-3">
@@ -583,18 +600,17 @@ export function ReviewReport({
<ReviewSectionPanel
title="伏笔"
subtitle="foreshadow-analyst"
statusLabel={
sectionStatus("foreshadow") === "incomplete"
? "未完成"
: foreshadow.length > 0
? `${foreshadow.length} 建议`
: foreshadowOpen > 0
? `${foreshadowOpen} 待登记`
: "无建议"
}
statusVariant={
sectionStatus("foreshadow") === "incomplete"
? "warning"
: foreshadow.length > 0
: foreshadowOpen > 0
? "accent"
: "success"
}
@@ -605,11 +621,11 @@ export function ReviewReport({
incomplete={sectionStatus("foreshadow") === "incomplete"}
projectId={project.id}
chapterNo={chapterNo}
onRemainingChange={setForeshadowRemaining}
/>
</ReviewSectionPanel>
<ReviewSectionPanel
title="节奏"
subtitle="pace-checker"
statusLabel={
sectionStatus("pace") === "incomplete"
? "未完成"
@@ -633,7 +649,6 @@ export function ReviewReport({
</ReviewSectionPanel>
<ReviewSectionPanel
title="文风"
subtitle="style"
statusLabel={
sectionStatus("style") === "incomplete"
? "未完成"
@@ -667,20 +682,52 @@ export function ReviewReport({
) : null}
</div>
<section className="mt-4">
<section id="accept-panel" className="mt-4 scroll-mt-4">
<AcceptPanel
projectId={project.id}
chapterNo={chapterNo}
reviewed={initialReview !== undefined || review.state.phase === "done"}
conflictCount={conflictCount}
unresolvedCount={resolved ? 0 : unresolved}
foreshadowCount={foreshadow.length}
foreshadowCount={foreshadowOpen}
accepting={accept.status === "accepting"}
result={accept.result}
onAccept={() => void onAccept()}
/>
</section>
</aside>
{/* 移动端(<lg 单列)快捷条:编辑器在上、审稿/验收在下,滚一整屏才够得着——
固定底栏直接「跳到未裁决」或「去验收」,免去长滚。桌面端隐藏(右栏常驻可见)。 */}
{hasReport && !accept.result ? (
<div className="fixed inset-x-0 bottom-0 z-30 flex items-center gap-2 border-t border-line bg-panel/95 px-4 py-2 backdrop-blur supports-[backdrop-filter]:bg-panel/80 lg:hidden">
<span className="flex-1 truncate text-xs text-ink-soft">
{unresolved > 0 ? `${unresolved} 项冲突待裁决` : "可验收本章"}
</span>
{unresolved > 0 ? (
<Button
onClick={jumpToNextUnresolved}
variant="secondary"
size="sm"
>
<LocateFixed className="h-4 w-4" aria-hidden="true" />
</Button>
) : null}
<Button
onClick={() =>
document
.getElementById("accept-panel")
?.scrollIntoView({ behavior: "smooth", block: "center" })
}
variant="primary"
size="sm"
>
<ClipboardCheck className="h-4 w-4" aria-hidden="true" />
</Button>
</div>
) : null}
</div>
</AppShell>
);