"use client"; import { useEffect, useState } from "react"; import Image from "next/image"; import { api } from "./StartGame"; import type { DatasetManifest } from "@/shared/protocol"; type Draft = { id: string; name: string; description: string; state: string; source: string; map: string | null; manifest: DatasetManifest; previews: { id: string; image: string | null }[]; }; export function DraftEditor({ id }: { id: string }) { const [draft, setDraft] = useState(null), [name, setName] = useState(""), [description, setDescription] = useState(""), [selected, setSelected] = useState([]), [error, setError] = useState(""), [message, setMessage] = useState(""), [busy, setBusy] = useState(false); useEffect(() => { api("datasets/" + id) .then((d) => { setDraft(d); setName(d.name); setDescription(d.description); setSelected(d.manifest.viewpoints.map((p) => p.id)); }) .catch((e) => setError(e.message)); }, [id]); async function save(submit = false) { setBusy(true); setError(""); try { await api( "datasets/" + id, { name, description, selectedIds: selected }, "PATCH", ); if (submit) { await api("datasets/" + id + "/submit", {}); setDraft((d) => (d ? { ...d, state: "review" } : d)); setMessage("Submitted for moderator review."); } else setMessage("Draft saved."); } catch (e) { setError((e as Error).message); } finally { setBusy(false); } } async function cancel() { setBusy(true); try { await api("datasets/" + id + "/cancel", {}); setMessage("Processing cancelled."); } catch (e) { setError((e as Error).message); } finally { setBusy(false); } } if (!draft) return (

{error || "Loading your draft…"}

); const editable = ["draft", "rejected"].includes(draft.state); return ( <> {draft.state}

{draft.source === "plugin" ? "Server-generated views use vanilla terrain and simplified lighting. Entities, shaders, custom packs and dynamic sign text are omitted." : "Player captures show the terrain received by the client. Unexplored map coverage remains blank."}

{draft.map && (
Draft surface map
)}