Admin-CMS für VanVan optisch und strukturell deutlich aufgewertet

- Farbschema/Schriftart der Website übernommen (Sveltias eigenes CSS-Variablen-
  Theming-System genutzt: --sui-base-hue, --sui-primary-accent-color* auf den
  Türkis-Akzent + Lila-Grundton der Seite gesetzt, Inter-Schriftart)
- Eigenes Logo + Seitentitel "Van's Shop – Adminbereich" auf dem Login-Bildschirm
- Icons pro Bereich in der Seitenleiste (Produkte/Kategorien/Versandkosten)
- Zahlenfelder ohne die klobigen Browser-Spinner-Pfeile
- Produktformular neu geordnet nach natürlichem Ablauf: Fotos → Name →
  Beschreibung → Preis/Bestand (mit klareren Erklärtexten) → Kategorie →
  Auszeichnungen → weitere Detailangaben → Versand → interner Code
This commit is contained in:
qcigano
2026-08-02 18:35:05 +02:00
parent a45f536fbb
commit 0f93ab73c3
2 changed files with 104 additions and 45 deletions
+61 -45
View File
@@ -4,6 +4,11 @@ backend:
branch: main
base_url: https://vans-diy-bastelbedarf-cms-auth.dogfather1608.workers.dev
logo:
src: /logo.png
app_title: "Van's Shop Adminbereich"
# Bilder, die VanVan hier hochlädt, landen automatisch hier im Projekt und sind danach
# unter /img/products/<dateiname> auf der Website erreichbar.
media_folder: "public/img/products"
@@ -13,6 +18,7 @@ collections:
- name: products
label: Produkte
label_singular: Produkt
icon: shopping_bag
folder: src/content/products
create: true
delete: true
@@ -22,15 +28,11 @@ collections:
format: json
summary: "{{name.de}} — {{preis}} €"
fields:
- label: "Interner Code (URL) — nach Veröffentlichung nicht mehr ändern!"
name: slug
widget: string
hint: "Nur Kleinbuchstaben, Zahlen und Bindestriche, z.B. wolke-plushie-lavendel"
- label: "📷 Fotos"
name: bilder
widget: list
required: false
hint: "Hier Fotos hochladen oder per Drag & Drop reinziehen. Das erste Foto ist das Hauptbild."
hint: "Hier Fotos hochladen oder per Drag & Drop reinziehen. Das erste Foto ist das Hauptbild, das überall zuerst angezeigt wird."
field: { label: Foto, name: bild, widget: image }
- label: Name
name: name
@@ -40,10 +42,32 @@ collections:
- { label: Englisch, name: en, widget: string }
- { label: "Schweizerdeutsch", name: ch, widget: string }
- { label: Französisch, name: fr, widget: string }
- label: Artikelnummer
name: artikelnummer
widget: string
- label: Beschreibung
name: beschreibung
widget: object
fields:
- { label: Deutsch, name: de, widget: text }
- { label: Englisch, name: en, widget: text }
- { label: "Schweizerdeutsch", name: ch, widget: text }
- { label: Französisch, name: fr, widget: text }
- label: "Preis (€)"
name: preis
widget: number
value_type: float
step: 0.01
hint: "Der ganz normale Verkaufspreis, z.B. 19.99"
- label: "Reduzierter Preis? (nur ausfüllen, wenn im Sale)"
name: preisAlt
widget: number
value_type: float
step: 0.01
required: false
hint: "Hier den ALTEN, höheren Preis eintragen — er wird dann durchgestrichen neben dem neuen Preis angezeigt. Leer lassen, wenn kein Sale."
- label: "Auf Lager"
name: bestand
widget: number
value_type: int
hint: "Wie viele Stück hast du vorrätig? 0 = ausverkauft (Artikel bleibt trotzdem sichtbar)."
- label: Kategorie
name: kategorie
widget: relation
@@ -55,23 +79,19 @@ collections:
name: unterkategorie
widget: string
required: false
hint: "Interner Code der Unterkategorie eintragen, z.B. kuh-frieda (siehe Kategorien-Bereich)"
- { label: "Preis (in Euro)", name: preis, widget: number, value_type: float, step: 0.01 }
- label: "Alter Preis (nur ausfüllen, wenn im Sale)"
name: preisAlt
widget: number
value_type: float
step: 0.01
hint: "Interner Code der Unterkategorie eintragen, z.B. kuh-frieda (siehe Bereich Kategorien)"
- label: Auszeichnungen
name: badges
widget: select
multiple: true
required: false
- { label: "Bestand (Anzahl auf Lager)", name: bestand, widget: number, value_type: int }
- label: Beschreibung
name: beschreibung
widget: object
fields:
- { label: Deutsch, name: de, widget: text }
- { label: Englisch, name: en, widget: text }
- { label: "Schweizerdeutsch", name: ch, widget: text }
- { label: Französisch, name: fr, widget: text }
hint: "Erscheinen als kleine Sticker auf dem Produktbild"
options:
- { label: "✨ Neu", value: neu }
- { label: "🔥 Bestseller", value: bestseller }
- { label: "🏷️ Im Sale", value: sale }
- { label: "🧶 Handgemacht", value: handgemacht }
- { label: Artikelnummer, name: artikelnummer, widget: string, required: false }
- { label: Material, name: material, widget: string, required: false }
- { label: "Größe / Maße", name: groesse, widget: string, required: false }
- label: Farben
@@ -82,30 +102,25 @@ collections:
- { label: Lieferumfang, name: lieferumfang, widget: string, required: false }
- { label: Pflegehinweise, name: pflegehinweise, widget: string, required: false }
- { label: Lieferzeit, name: lieferzeit, widget: string, required: false }
- label: Auszeichnungen
name: badges
widget: select
multiple: true
required: false
options:
- { label: Neu, value: neu }
- { label: Bestseller, value: bestseller }
- { label: "Im Sale", value: sale }
- { label: Handgemacht, value: handgemacht }
- label: "🚚 Eigene Versandkosten (nur für Einzelkauf dieses Produkts)"
name: versand
widget: object
required: false
hint: "Gilt NUR, wenn jemand genau 1 Stück von genau diesem Produkt kauft. Bei mehreren Produkten/Stück im Warenkorb gilt automatisch die allgemeine Versandkosten-Staffel (siehe eigener Bereich 'Versandkosten-Staffel' im Menü links). Leer lassen = Staffel gilt auch beim Einzelkauf."
hint: "Gilt NUR, wenn jemand genau 1 Stück von genau diesem Produkt kauft. Bei mehreren Produkten/Stück im Warenkorb gilt automatisch die allgemeine Versandkosten-Staffel (siehe Bereich 'Versandkosten-Staffel'). Leer lassen = Staffel gilt auch beim Einzelkauf."
fields:
- { label: "Deutschland (€)", name: de, widget: number, value_type: float, step: 0.01, required: false }
- { label: "Österreich (€)", name: at, widget: number, value_type: float, step: 0.01, required: false }
- { label: "Schweiz (€)", name: ch, widget: number, value_type: float, step: 0.01, required: false }
- { label: "Luxemburg (€)", name: lu, widget: number, value_type: float, step: 0.01, required: false }
- label: "Interner Code (URL) — nach Veröffentlichung nicht mehr ändern!"
name: slug
widget: string
hint: "Nur Kleinbuchstaben, Zahlen und Bindestriche, z.B. wolke-plushie-lavendel"
- name: categories
label: Kategorien
label_singular: Kategorie
icon: category
folder: src/content/categories
create: true
delete: false
@@ -115,13 +130,10 @@ collections:
format: json
summary: "{{name.de}}"
fields:
- label: "Interner Code (URL) — nach Veröffentlichung nicht mehr ändern!"
name: slug
- label: "Icon (Emoji)"
name: icon
widget: string
- label: "Reihenfolge (0 = zuerst)"
name: order
widget: number
value_type: int
hint: "z.B. 🧸"
- label: Name
name: name
widget: object
@@ -138,10 +150,6 @@ collections:
- { label: Englisch, name: en, widget: text }
- { label: "Schweizerdeutsch", name: ch, widget: text }
- { label: Französisch, name: fr, widget: text }
- label: "Icon (Emoji)"
name: icon
widget: string
hint: "z.B. 🧸"
- label: Unterkategorien
name: subcategories
widget: list
@@ -157,9 +165,17 @@ collections:
- { label: Englisch, name: en, widget: string }
- { label: "Schweizerdeutsch", name: ch, widget: string }
- { label: Französisch, name: fr, widget: string }
- label: "Reihenfolge (0 = zuerst)"
name: order
widget: number
value_type: int
- label: "Interner Code (URL) — nach Veröffentlichung nicht mehr ändern!"
name: slug
widget: string
- name: versandkosten
label: "🚚 Versandkosten-Staffel"
icon: local_shipping
files:
- name: staffel
label: "Versandkosten-Staffel nach Warenwert"
+43
View File
@@ -6,6 +6,49 @@
<meta name="robots" content="noindex" />
<title>Van's DIY & Bastelbedarf Admin</title>
<link rel="icon" href="/favicon.svg" />
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap" rel="stylesheet" />
<style>
/* Sveltia CMS optisch an die eigentliche Website angepasst — nutzt Sveltias eigenes
CSS-Variablen-Theming-System (--sui-*, "Sveltia UI"), keine geratenen internen
Klassennamen. Das ist zwar nirgends offiziell als öffentliche Theming-API dokumentiert,
aber es sind echte, durchgängig im ganzen Sveltia-Interface verwendete Design-Tokens —
deutlich robuster als CSS gegen zufällige Klassennamen zu schreiben. Falls ein
künftiges Sveltia-Update diese Variablennamen ändert, fällt die Oberfläche einfach
wieder auf ihr Standard-Blau zurück statt kaputtzugehen.
*/
/* !important nötig: Sveltia hängt sein eigenes Stylesheet erst NACH dieser Seite ein,
gewinnt also bei gleicher Spezifität normalerweise die Kaskade. Mit !important setzt
sich unsere Optik trotzdem zuverlässig durch, unabhängig von der Ladereihenfolge. */
:root {
/* Schiebt alle neutralen Grautöne/Ränder der Oberfläche Richtung Lila — wie der
Rest der Seite (statt Sveltias Standard-Blaugrau). */
--sui-base-hue: 248 !important;
/* Türkiser Akzent der Website statt Sveltias Standard-Blau. */
--sui-primary-accent-color: #5fd3ec !important;
--sui-primary-accent-color-light: #7fdcf0 !important;
--sui-primary-accent-color-dark: #3ca9c2 !important;
--sui-primary-accent-color-text: #5fd3ec !important;
--sui-primary-accent-color-inverted: #0a0910 !important;
--sui-primary-accent-color-translucent: rgba(95, 211, 236, 0.5) !important;
--sui-primary-accent-color-translucent-light: rgba(95, 211, 236, 0.3) !important;
/* Gleiche Schriftart wie der Rest der Seite statt Sveltias Standardschrift. */
--sui-font-family-default: "Inter", system-ui, sans-serif !important;
}
/* Zahlenfelder ohne die klobigen Auf/Ab-Pfeile — dezenter, aufgeräumter. */
input[type="number"]::-webkit-outer-spin-button,
input[type="number"]::-webkit-inner-spin-button {
-webkit-appearance: none;
margin: 0;
}
input[type="number"] {
-moz-appearance: textfield;
}
</style>
</head>
<body>
<!-- Sveltia CMS: quelloffen (MIT), läuft komplett im Browser, bearbeitet die Inhalte