feat: picdrop delivery — worker delivers on job completion, /api/deliver for manual, gallery default 'POSTER LEA', library bulk send + status badges
This commit is contained in:
@@ -28,6 +28,11 @@ export default function LibraryApp() {
|
||||
};
|
||||
const del = async (id: string) => { await fetch(`/api/items/${id}`, { method: 'DELETE' }); setItems((x) => x.filter((y) => y.id !== id)); };
|
||||
const delSelected = async () => { for (const id of sel) await fetch(`/api/items/${id}`, { method: 'DELETE' }); setSel(new Set()); load(); notify('Gelöscht.'); };
|
||||
const deliverSelected = async () => {
|
||||
notify('Sende an Picdrop …');
|
||||
const r = await fetch('/api/deliver', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ itemIds: [...sel] }) }).then((x) => x.json());
|
||||
setSel(new Set()); load(); notify(`${r.delivered}/${r.total} nach Picdrop ausgeliefert.`);
|
||||
};
|
||||
const toggle = (id: string) => setSel((s) => { const n = new Set(s); n.has(id) ? n.delete(id) : n.add(id); return n; });
|
||||
|
||||
const newFolder = async () => {
|
||||
@@ -43,7 +48,7 @@ export default function LibraryApp() {
|
||||
<div className="reihe">
|
||||
{sel.size > 0 && <>
|
||||
<span className="fein">{sel.size} gewählt</span>
|
||||
{[...sel].map((id) => <a key={id} className="hidden" />)}
|
||||
<button className="mini stark" onClick={deliverSelected}>Nach Picdrop</button>
|
||||
<button className="mini" onClick={delSelected}>Löschen</button>
|
||||
</>}
|
||||
<button className="mini" onClick={newFolder}>Neuer Ordner</button>
|
||||
@@ -62,7 +67,11 @@ export default function LibraryApp() {
|
||||
<span className="haken">{sel.has(v.id) ? '✓' : ''}</span>
|
||||
</div>
|
||||
<input className="name" defaultValue={v.filename || ''} onBlur={(e) => rename(v.id, e.target.value)} />
|
||||
<div className="meta">{(v.tasks || []).join(' · ')}{v.output_px ? ` · ${v.output_px}px` : ''}{v.has_alpha ? ' · transparent' : ''}</div>
|
||||
<div className="meta">{(v.tasks || []).join(' · ')}{v.output_px ? ` · ${v.output_px}px` : ''}{v.has_alpha ? ' · transparent' : ''}
|
||||
{v.delivery_status === 'delivered' && <span className="dbadge ok">Picdrop ✓</span>}
|
||||
{v.delivery_status === 'pending' && <span className="dbadge">Picdrop …</span>}
|
||||
{v.delivery_status === 'failed' && <span className="dbadge err">Picdrop ✕</span>}
|
||||
</div>
|
||||
<div className="reihe knapp">
|
||||
<button className="mini" onClick={() => setCompare(v)}>Vorher/Nachher</button>
|
||||
<a className="mini" href={`/api/items/${v.id}/file?download=1`}>Laden</a>
|
||||
@@ -112,6 +121,10 @@ function LibStyles() {
|
||||
.kachel.gewaehlt .haken{background:var(--accent);}
|
||||
.name{margin-top:8px;width:100%;font-size:12.5px;padding:6px 8px;font-family:var(--font-mono);border:1px solid var(--line);border-radius:3px;background:#fff;}
|
||||
.meta{font-size:11px;color:var(--soft);margin-top:5px;}
|
||||
.mini.stark{background:var(--accent);border-color:var(--accent);color:#fff;font-weight:600;}
|
||||
.dbadge{display:inline-block;margin-left:6px;font-family:var(--font-mono);font-size:9px;letter-spacing:.08em;text-transform:uppercase;background:var(--paper);color:var(--soft);padding:1px 6px;border-radius:20px;}
|
||||
.dbadge.ok{background:var(--accent-bg);color:var(--accent);}
|
||||
.dbadge.err{color:var(--err);}
|
||||
.mini-select{border:1px solid var(--line);border-radius:3px;padding:5px 7px;font-family:inherit;font-size:12px;background:#fff;}
|
||||
.lupe{position:fixed;inset:0;background:rgba(22,21,15,.85);display:flex;flex-direction:column;align-items:center;justify-content:center;gap:14px;padding:26px;z-index:50;}
|
||||
.vergleich{position:relative;max-width:90vw;max-height:76vh;}
|
||||
|
||||
Reference in New Issue
Block a user