fix: hochgeladene Logos auf Anzeigegroesse zuschneiden

Ein hochgeladenes Logo erschien auf der Willkommensseite deutlich
kleiner als ein automatisch gefundenes. Ursache ist nicht die CSS -
beide nutzen dieselbe Klasse - sondern der Bildinhalt: nach dem
Freistellen ist der Rand zwar durchsichtig, zaehlt aber weiter zur
Bildflaeche. .customer-logo skaliert mit object-fit: contain auf 120px
Hoehe, ein Logo mit breitem Rand erscheint dadurch nur einen Bruchteil
davon gross (gemessen: 30px statt 120px). Brandfetch-Logos sind bereits
eng beschnitten und fuellen den Kasten aus.

trim_transparent_border() schneidet die durchsichtigen Raender nach dem
Freistellen weg. Greift auch bei bereits transparenten PNGs; bei
abgewaehltem Freistellen passiert nichts, da es dort keinen
transparenten Rand gibt.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Erik Thiele
2026-09-02 15:06:20 +02:00
parent 9dae841461
commit 8de8a116bb
4 changed files with 27 additions and 1 deletions

View File

@@ -300,7 +300,7 @@ Maximal 3 Kunden eingeben → Logos werden via OpenAI + Brandfetch gesucht → `
**Logo-Upload:** Findet die automatische Suche kein Logo (oder passt es nicht), kann pro Kunde eine Bilddatei hochgeladen werden. Ein Upload hat Vorrang vor der Suche. Die Datei wird als `media/<site>/logos/logo_<slot>.png` abgelegt und über `/media/<site>/logos/<datei>` ausgeliefert.
**Freistellen:** Beim Upload wird der Hintergrund automatisch entfernt, damit das Logo nicht in einem weissen Kasten auf dem Hintergrundbild steht. Verfahren: Flood Fill von den Bildrändern her (bewusst kein globaler Farbvergleich – so bleibt Weiss *innerhalb* des Logos erhalten), weiche Kante gegen Treppeneffekte, Speicherung immer als PNG. Bereits transparente Bilder werden unverändert übernommen; ist der Bildrand nicht einfarbig, bleibt das Bild unangetastet und die Oberfläche weist darauf hin. Mit der Checkbox „Hintergrund behalten" lässt sich das Freistellen pro Kunde abschalten. Umgesetzt mit Pillow – bewusst ohne ML-Modell, da der Container mit read-only Root-FS läuft und kein Modell-Cache zur Verfügung steht.
**Freistellen und Zuschneiden:** Beim Upload wird der Hintergrund automatisch entfernt, damit das Logo nicht in einem weissen Kasten auf dem Hintergrundbild steht. Anschliessend werden die durchsichtigen Ränder weggeschnitten (`trim_transparent_border`). Ohne diesen Schnitt erscheint ein hochgeladenes Logo kleiner als ein automatisch gefundenes: die Willkommensseite skaliert mit `object-fit: contain` auf eine feste Höhe von 120px, und ein breiter Rand zählt dabei mit – Brandfetch-Logos sind bereits eng beschnitten. Verfahren: Flood Fill von den Bildrändern her (bewusst kein globaler Farbvergleich – so bleibt Weiss *innerhalb* des Logos erhalten), weiche Kante gegen Treppeneffekte, Speicherung immer als PNG. Bereits transparente Bilder werden unverändert übernommen; ist der Bildrand nicht einfarbig, bleibt das Bild unangetastet und die Oberfläche weist darauf hin. Mit der Checkbox „Hintergrund behalten" lässt sich das Freistellen pro Kunde abschalten. Umgesetzt mit Pillow – bewusst ohne ML-Modell, da der Container mit read-only Root-FS läuft und kein Modell-Cache zur Verfügung steht.
**Anzeigen bis:** Optionales Datum im Formular. Ist es gesetzt, bekommt der Eintrag eine Zeitsteuerung (`daily 00:00–23:59` mit `valid_until`) und verschwindet danach auf allen Screens von selbst.
@@ -511,6 +511,7 @@ Optional pro Eintrag. Ohne `schedule` läuft der Eintrag immer (sofern `enabled`
- `welcome_target_screens(config, site)` – Zielscreens der Willkommensseite (Fallback `lobby`)
- `save_uploaded_logo(file, site, slot, freistellen=True)` – hochgeladenes Logo freistellen und als PNG ablegen
- `remove_logo_background(image)` – Hintergrund per Flood Fill entfernen, gibt `(bild, hinweis)` zurück
- `trim_transparent_border(img)` – durchsichtige Ränder wegschneiden, damit das Logo den Anzeigebereich ausfüllt
- `sync_welcome_for_screen(config, site, screen, enabled)` – Willkommensseite beim Umlegen des Schalters platzieren bzw. entfernen
- `find_welcome_source(site, config)` – vorhandene `welcome.html` als Kopiervorlage finden
- `prio_redirect(site)` – Redirect-Pfad zur Priority-Seite