'use client'; // TextCandidateCard — 文案候选卡,AI评委7维分 + 总评 + 违禁状态 + 导入角标 import { useState } from 'react'; import { TextCandidate } from '@/types/index'; import { ScoreDimBars } from './ScoreDimBars'; import { clsx } from 'clsx' ; interface TextCandidateCardProps { candidate: TextCandidate; selected: boolean; onToggle: (id: number) => void; onSaveEdit?: (id: number, content: string) => Promise; } const BANNED_STATUS_STYLES = { pass: null, auto_fixed: 'bg-green-50 border-brand-green text-brand-green-dark text-xs px-2 py-0.5 rounded-full', soft_warn: 'bg-yellow-50 border-yellow-400 text-yellow-700 text-xs px-2 py-0.5 rounded-full', hard_block: 'bg-red-50 border-red-400 text-status-error text-xs px-2 py-0.5 rounded-full', }; const VERDICT_STYLES: Record = { '优秀': 'text-status-success font-medium', '合格': 'text-text-secondary', '不合格':'text-status-error', }; export function TextCandidateCard({ candidate, selected, onToggle, onSaveEdit }: TextCandidateCardProps) { const [expanded, setExpanded] = useState(false); const [editing, setEditing] = useState(false); const [draft, setDraft] = useState(candidate.content); const [saving, setSaving] = useState(false); const [justSaved, setJustSaved] = useState(false); async function handleSave(e: React.MouseEvent) { e.stopPropagation(); if (!onSaveEdit || saving || draft.trim() === '') return; setSaving(true); try { await onSaveEdit(candidate.candidate_id, draft); setEditing(false); setJustSaved(true); // 飞轮节点反馈:改稿=最强信号已喂回 setTimeout(() => setJustSaved(false), 4000); } finally { setSaving(false); } } return (
onToggle(candidate.candidate_id)} aria-selected={selected} aria-label={`文案:${candidate.angle_label},总分${candidate.score.total},${selected ? '已选中' : '未选中'}`} className={clsx( 'relative border rounded-xl p-4 cursor-pointer transition-all', selected ? 'border-brand-orange bg-brand-cream shadow-sm' : 'border-border-default bg-surface-primary hover:border-brand-orange/50' )} > {/* 角标:导入来源 */} {candidate.source === 'import' && ( 导入 )} {/* 选中勾 */} {selected && ( )}
{candidate.angle_label} {(candidate.edited || justSaved) && ( 已改稿 )} {editing ? (