import { $, api, esc, showError, renderHeader, renderFooter, isAdmin, prepareImage } from './common.js'; renderHeader('kooperationen'); renderFooter(); let coops = []; let admin = false; // nur der Admin-Zugang darf anlegen, ändern, löschen let editingId = null; let imageData = null; // data:-URL des neu gewählten Titelbildes const imgUrl = (c) => `/koop-img/${encodeURIComponent(c.image)}`; // ---------- Soziale Medien ---------- const SOCIALS = [ { key: 'website', label: 'Website', icon: '' }, { key: 'instagram', label: 'Instagram', icon: '' }, { key: 'youtube', label: 'YouTube', icon: '' }, { key: 'tiktok', label: 'TikTok', icon: '' }, { key: 'facebook', label: 'Facebook', icon: '' }, { key: 'discord', label: 'Discord', icon: '' }, ]; const icon = (s) => ``; function socialsHtml(c) { const links = SOCIALS.filter((s) => c.socials?.[s.key]); return links.length ? links.map((s) => `${icon(s)}${s.label}`).join('') : '

Keine Links eingetragen.

'; } // Ohne Titelbild: Anfangsbuchstaben auf Flaggenblau const initials = (name) => name.split(/\s+/).filter(Boolean).slice(0, 2).map((w) => w[0]).join('').toUpperCase(); // ---------- Übersicht ---------- function renderOverview() { $('#coop-empty').hidden = coops.length > 0; $('#coop-empty-hint').textContent = admin ? 'Trag über „Kooperation hinzufügen“ die erste Gruppe ein.' : 'Sobald der Admin eine Kooperation einträgt, erscheint sie hier.'; $('#coop-grid').innerHTML = coops.map((c) => `
${c.image ? `` : `${esc(initials(c.name))}`}

${esc(c.name)}

${c.leader ? `

Anführer: ${esc(c.leader)}

` : ''} Ansehen
`).join(''); } // ---------- Einzelansicht (#id) ---------- function renderDetail(c) { document.title = `${c.name} – Kooperationen – HCRB`; $('#detail-name').textContent = c.name; const img = $('#detail-img'); img.hidden = !c.image; if (c.image) img.src = imgUrl(c); $('#detail-hero').classList.toggle('no-image', !c.image); $('#detail-hero').dataset.initials = initials(c.name); $('#detail-description').textContent = c.description || 'Noch keine Beschreibung.'; $('#detail-leader').textContent = c.leader || 'Nicht angegeben'; $('#detail-socials').innerHTML = socialsHtml(c); $('#detail-admin').hidden = !admin; } function route() { const id = location.hash.slice(1); const coop = coops.find((c) => c.id === id); $('#overview').hidden = !!coop; $('#detail').hidden = !coop; if (coop) { renderDetail(coop); scrollTo(0, 0); } else { document.title = 'Kooperationen – HCRB'; renderOverview(); } } addEventListener('hashchange', () => { closeForm(); route(); }); $('#back-link').addEventListener('click', (e) => { e.preventDefault(); history.pushState(null, '', location.pathname); route(); }); // ---------- Formular ---------- function showPreview(src) { $('#coop-preview').hidden = !src; if (src) $('#coop-preview').src = src; $('#drop-text').innerHTML = src ? 'Anderes Titelbild wählen' : 'Titelbild auswählen
oder hierher ziehen · am besten ein breites Foto (Querformat)'; } function openForm(coop) { editingId = coop?.id ?? null; imageData = null; $('#coop-form').reset(); $('#coop-error').hidden = true; $('#coop-form-title').textContent = coop ? 'Kooperation bearbeiten' : 'Kooperation hinzufügen'; $('#coop-name').value = coop?.name ?? ''; $('#coop-leader').value = coop?.leader ?? ''; $('#coop-description').value = coop?.description ?? ''; for (const s of SOCIALS) $(`#social-${s.key}`).value = coop?.socials?.[s.key] ?? ''; $('#remove-image-wrap').hidden = !coop?.image; showPreview(coop?.image ? imgUrl(coop) : null); $('#coop-form-card').hidden = false; $('#coop-form-card').scrollIntoView({ behavior: 'smooth', block: 'start' }); $('#coop-name').focus({ preventScroll: true }); } function closeForm() { $('#coop-form-card').hidden = true; editingId = null; imageData = null; } async function pickFile(file) { if (!file) return; $('#coop-error').hidden = true; try { imageData = await prepareImage(file, 2000); showPreview(imageData); $('#coop-remove-image').checked = false; } catch (err) { imageData = null; $('#coop-error').textContent = err.message || 'Das Bild konnte nicht gelesen werden.'; $('#coop-error').hidden = false; } } $('#coop-file').addEventListener('change', (e) => pickFile(e.target.files[0])); const drop = $('#dropzone'); drop.addEventListener('dragover', (e) => { e.preventDefault(); drop.classList.add('over'); }); drop.addEventListener('dragleave', () => drop.classList.remove('over')); drop.addEventListener('drop', (e) => { e.preventDefault(); drop.classList.remove('over'); pickFile(e.dataTransfer.files[0]); }); $('#add-btn').addEventListener('click', () => openForm(null)); $('#coop-cancel').addEventListener('click', closeForm); $('#detail-edit').addEventListener('click', () => openForm(coops.find((c) => c.id === location.hash.slice(1)))); $('#detail-delete').addEventListener('click', async () => { const c = coops.find((x) => x.id === location.hash.slice(1)); if (!c || !confirm(`Kooperation „${c.name}“ wirklich löschen?`)) return; try { await api('DELETE', `/kooperationen/${c.id}`); history.pushState(null, '', location.pathname); await load(); } catch (err) { showError(err); } }); $('#coop-form').addEventListener('submit', async (e) => { e.preventDefault(); const error = $('#coop-error'); error.hidden = true; const button = $('#coop-submit'); button.disabled = true; try { const body = { name: $('#coop-name').value, leader: $('#coop-leader').value, description: $('#coop-description').value, socials: Object.fromEntries(SOCIALS.map((s) => [s.key, $(`#social-${s.key}`).value])), }; if (imageData) body.image = imageData; else if ($('#coop-remove-image').checked) body.removeImage = true; const saved = editingId ? await api('PUT', `/kooperationen/${editingId}`, body) : await api('POST', '/kooperationen', body); closeForm(); coops = await api('GET', '/kooperationen'); // Nach dem Speichern die Seite der Kooperation zeigen if (location.hash.slice(1) === saved.id) route(); else location.hash = saved.id; } catch (err) { error.textContent = err.message; error.hidden = false; } finally { button.disabled = false; } }); // ---------- Laden ---------- async function load() { coops = await api('GET', '/kooperationen'); route(); } admin = await isAdmin(); $('#add-btn').hidden = !admin; showPreview(null); await load().catch(showError);