"use client" import { getProjectAdminList, projectConfig, } from "@/components/label/api/project" import { ProjectDetail } from "@/components/label/api/project/typing" import { useAllUserStore } from "@/components/label/store/auth" import { ActionIcon, Collapse, Group, Paper, ScrollArea, SimpleGrid, Stack, Switch, Text, } from "@mantine/core" import { notifications } from "@mantine/notifications" import { IconCheck, IconChevronDown, IconChevronRight, IconEdit, IconX, } from "@tabler/icons-react" import { useCallback, useEffect, useMemo, useState } from "react" import AdminUserModal from "./components/AdminUserModal" import LabelSchemeContainer from "./components/LabelSchemeContainer" import NoteRulesTable from "./components/NoteRulesTable" import SamplingPlanContainer from "./components/SamplingPlanContainer" import TaskStageTabsContainer from "./components/TaskStageTabsContainer" export default function InfoSettingContainer(props: { info: ProjectDetail.DataProps | undefined userEnums: { allEnum: Map labelEnum: Map review1Enum: Map review2Enum: Map } updateAction: () => void }) { const { info, userEnums, updateAction } = props const projectId = info?.id ?? -1 const { userOpts } = useAllUserStore() const fallbackUserOptions = useMemo(() => { return userOpts.map((o) => ({ label: o.label, value: String(o.value) })) }, [userOpts]) const [adminOptions, setAdminOptions] = useState< Array<{ label: string; value: string }> >([]) const [adminModalOpen, setAdminModalOpen] = useState(false) const [lockingValue, setLockingValue] = useState( !!info?.is_lock_object ) const [lockingEditValue, setLockingEditValue] = useState( !!info?.is_lock_object ) const [isLockingEdit, setIsLockingEdit] = useState(false) const [savingLock, setSavingLock] = useState(false) const [show, setShow] = useState({ process: true, scheme: true, sampling: true, note: true, }) useEffect(() => { const v = !!info?.is_lock_object setLockingValue(v) setLockingEditValue(v) setIsLockingEdit(false) }, [info?.is_lock_object]) const loadAdminOptions = useCallback(async () => { try { const res = await getProjectAdminList() const opts = (res ?? []).map((item) => ({ label: item.label, value: String(item.value), })) setAdminOptions(opts) } catch { setAdminOptions([]) } }, []) useEffect(() => { queueMicrotask(loadAdminOptions) }, [loadAdminOptions]) const adminText = useMemo(() => { const adminUids = info?.admin_user ?? [] const names = adminUids.map((uid) => { const opt = userOpts.find((o) => o.value === uid) return opt?.label ?? String(uid) }) return names.length ? names.join("、") : "-" }, [info?.admin_user, userOpts]) const saveLock = async () => { if (projectId === -1) return setSavingLock(true) try { await projectConfig({ project_id: projectId, is_lock_object: lockingEditValue, }) notifications.show({ color: "green", title: "操作成功", message: "已保存配置", }) setLockingValue(lockingEditValue) setIsLockingEdit(false) updateAction() } catch (e) { notifications.show({ color: "red", title: "操作失败", message: e instanceof Error ? e.message : "请求失败", }) } finally { setSavingLock(false) } } const sectionTitle = ( key: keyof typeof show, title: string, color: "blue" | "orange" | "teal" | "grape" ) => { const opened = show[key] return (
{title} setShow((s) => ({ ...s, [key]: !opened }))}> {opened ? ( ) : ( )} ) } const finalAdminOptions = adminOptions.length > 0 ? adminOptions : fallbackUserOptions return ( <> 项目配置 项目管理员 {adminText} { setAdminModalOpen(true) if (adminOptions.length === 0) { queueMicrotask(loadAdminOptions) } }}> 图片对象锁定 开启后对象可被锁定,避免多人同时标注冲突 {isLockingEdit ? ( setLockingEditValue(e.currentTarget.checked) } /> { setLockingEditValue(lockingValue) setIsLockingEdit(false) }}> ) : ( setIsLockingEdit(true)}> )} 刷新项目详情 {sectionTitle("process", "任务流程", "blue")} {sectionTitle("scheme", "标注方案", "orange")} {sectionTitle("sampling", "抽检方案", "teal")} {sectionTitle("note", "批注规则", "grape")} { setAdminModalOpen(false) if (!next || projectId === -1) return try { await projectConfig({ project_id: projectId, admin_user: next }) notifications.show({ color: "green", title: "操作成功", message: "已保存项目管理员", }) updateAction() } catch (e) { notifications.show({ color: "red", title: "操作失败", message: e instanceof Error ? e.message : "请求失败", }) } }} /> ) }