import { api, escapeAttr, escapeHtml } from "../core.js"; import { widgetAnmelden, widgetsLaden, widgetsZeichnen } from "./rahmen.js"; /* ── Das Bild ────────────────────────────────────────────────────────────── * * Genau **ein** Bild je Nutzer, hochgeladen oder verlinkt. Ein neues ersetzt * das alte, ohne Verwaltung und ohne Liste — das ist der ganze Reiz: Es ist * das erste Widget, das nichts abfragt, sondern etwas *ist*. * * Hochgeladen wird zum eigenen Server; verlinkt wird auf eine fremde Adresse. * Der Unterschied ist keiner der Bequemlichkeit: Ein Link holt bei jedem * Aufbau des Schreibtischs etwas von woanders, ein Upload nie. */ const LEER = "Kein Bild — hochladen oder Adresse einfügen."; let art = ""; // "datei" | "link" | "" let quelle = ""; let stand = ""; // Meldung unter dem Bild let linkAuf = false; widgetAnmelden({ id: "bild", titel: "bild", // Hält ein Dateifeld und ein Eingabefeld: Der Rahmen darf den Inhalt nicht // unter den Fingern austauschen. stabil: true, async laden() { const d = await api("/api/image/info"); art = (d && d.art) || ""; quelle = (d && d.url) || ""; }, inhalt() { const bild = quelle ? `` : `

${LEER}

`; return `
${bild}
${ linkAuf ? `
` : "" }
${escapeHtml(stand)} ${quelle ? `` : ""}
`; }, montiert(el) { const datei = el.querySelector(".bildw-datei"); el.querySelector(".bildw-waehlen").addEventListener("click", () => datei.click()); datei.addEventListener("change", () => datei.files[0] && hochladen(datei.files[0])); el.querySelector(".bildw-link").addEventListener("click", () => { linkAuf = !linkAuf; neu(); }); const url = el.querySelector(".bildw-url"); if (url) { url.focus(); const setzen = () => linkSetzen(url.value.trim()); el.querySelector(".bildw-uebernehmen").addEventListener("click", setzen); url.addEventListener("keydown", (e) => { if (e.key === "Enter") { e.preventDefault(); setzen(); } }); } const weg = el.querySelector(".bildw-weg"); if (weg) weg.addEventListener("click", () => linkSetzen("")); // Ein Bild, das nicht kommt, soll es sagen — bei einem Link ist das der // Normalfall des Tages, an dem die fremde Seite umzieht. const img = el.querySelector(".bildw-bild"); if (img) { img.addEventListener("error", () => { melden(art === "link" ? "Adresse liefert kein Bild" : "Bild nicht lesbar"); }); } }, }); async function hochladen(file) { melden("lädt hoch …"); try { await api("/api/image", { method: "POST", body: file, headers: { "Content-Type": file.type || "application/octet-stream" } }); linkAuf = false; await widgetsLaden("bild"); melden(""); } catch (e) { melden(e.message); } } async function linkSetzen(adresse) { melden(adresse ? "übernehme …" : "entferne …"); try { await api("/api/image", { method: "PUT", body: JSON.stringify({ url: adresse }) }); linkAuf = false; await widgetsLaden("bild"); melden(""); } catch (e) { melden(e.message); } } function melden(s) { stand = s; document.querySelectorAll('[data-widget="bild"] .zettel-stand').forEach((el) => { el.textContent = s; }); } /** Neu zeichnen — stabile Widgets lässt der Rahmen sonst in Ruhe. */ function neu() { document.querySelectorAll('[data-widget="bild"]').forEach((el) => delete el.dataset.zustand); widgetsZeichnen(); }