feat(theme): Theme "Mobile" - kompakte Darstellung fuers Handy

Perinco-Farben, aber rund 16 % dichter: --spacing 0.21rem statt 0.25rem,
kleinere Ueberschriften (lg bis 5xl), Kopfleiste 3.5rem, flachere Schatten.
text-sm/base bleiben, damit iOS beim Tippen in Felder nicht zoomt.
Dunkel mit echtem Schwarz fuer OLED.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
schakal00783
2026-09-23 10:47:26 +02:00
co-authored by Claude Opus 5.5
parent 2f9c58f202
commit bea758e651
6 changed files with 69 additions and 7 deletions
+6 -3
View File
@@ -212,9 +212,12 @@ Modell mit einer echten Anfrage.
## Themes
Sieben Farbwelten, jede in hell und dunkel, gespeichert am Benutzer
Acht Farbwelten, jede in hell und dunkel, gespeichert am Benutzer
(`pulse_users.theme`, `theme_mode`) und vor dem ersten Bild gesetzt (Inline-Skript
in `index.html`). Sie kommen 1:1 aus dem perinco CRM; vier bringen Bewegung mit:
in `index.html`). Sieben kommen 1:1 aus dem perinco CRM. Das achte, **Mobile**, gibt es nur
in Pulse: perinco-Farben, aber fürs Handy rund 16 % dichter (kleineres `--spacing`,
kleinere Überschriften, niedrigere Kopfleiste), dunkel mit echtem Schwarz für OLED.
Vier Themes bringen Bewegung mit:
| Theme | Bewegung | Wo |
| --- | --- | --- |
@@ -312,7 +315,7 @@ Aus Auftrag und Call-Mitschrift.
| Einstellungen (nur Admin): SSO-Credentials, Userverwaltung, Kopf/Fuß der Exporte | ✅ inkl. PDF-/Excel-Vorschau | Einstellungen |
| Arbeitsstunden pro Woche (40) | ✅ | Einstellungen → Allgemein |
| Projektbezeichnungen nach Muster | ✅ | Einstellungen → Allgemein |
| Themes wie CRM (perinco, Pixel Art, Outdoor, Cyberpunk, Rainy, Snow, Aura – jeweils hell/dunkel, am Benutzer gespeichert) | ✅ | Kopfleiste |
| Themes wie CRM (perinco, Pixel Art, Outdoor, Cyberpunk, Rainy, Snow, Aura, Mobile – jeweils hell/dunkel, am Benutzer gespeichert) | ✅ | Kopfleiste |
| Lokaler Admin mit vorgegebenem Passwort, später änderbar | ✅ | Mein Konto |
| Mobil: eigene Ansicht bei Handy | ✅ untere Navigation, Tagesstreifen, Bottom-Sheets, schwebender Plus-Knopf | |
| SSO, anfangs normaler Login; AD-User auslesen, Rollen intern | ✅ vorbereitet, noch nicht gegen echten Tenant getestet | Einstellungen → SSO |
+1 -1
View File
@@ -40,7 +40,7 @@
var palette = localStorage.getItem('pulse_palette');
// Whitelist, damit ein manipulierter Eintrag keine Klasse setzt.
if (['pixel', 'outdoor', 'cyberpunk', 'rainy', 'snow', 'aura'].indexOf(palette) !== -1) {
if (['pixel', 'outdoor', 'cyberpunk', 'rainy', 'snow', 'aura', 'mobile'].indexOf(palette) !== -1) {
document.documentElement.classList.add('theme-' + palette);
}
} catch (e) {
+1 -1
View File
@@ -76,7 +76,7 @@ router.patch('/me', requireAuth, async (req, res, next) => {
const updates = {};
if (req.body?.theme !== undefined) {
const theme = req.body.theme;
if (theme !== null && !['perinco', 'pixel', 'outdoor', 'cyberpunk', 'rainy', 'snow', 'aura'].includes(theme)) {
if (theme !== null && !['perinco', 'pixel', 'outdoor', 'cyberpunk', 'rainy', 'snow', 'aura', 'mobile'].includes(theme)) {
return res.status(400).json({ error: 'Unbekanntes Design.' });
}
updates.theme = theme === 'perinco' ? null : theme;
+58
View File
@@ -997,6 +997,64 @@ html.theme-aura.dark {
--shadow-lift: 0 0 0 1px rgb(170 178 240 / 0.12), 0 14px 36px rgb(0 0 0 / 0.45);
}
/* ===========================================================================
* Mobile
*
* Kein eigenes Motiv, sondern mehr Inhalt auf dem Handybildschirm. Farben und
* Gruen bleiben perinco; anders ist die Dichte.
*
* Tailwind v4 rechnet jeden Abstand, jede feste Hoehe und Breite aus
* --spacing (p-4 = 4 * --spacing). Den Grundwert von 0.25rem auf 0.21rem zu
* setzen, zieht also die ganze Oberflaeche um rund 16 % zusammen, ohne dass
* eine Komponente angefasst wird. Weiter nicht: ein h-10-Knopf hat dann noch
* knapp 34 px und laesst sich mit dem Daumen sicher treffen.
*
* Verkleinert werden nur die grossen Schriften (lg bis 5xl), also Ueberschriften
* und Kennzahlen. text-sm und text-base bleiben: darunter wird es auf dem Handy
* schwer lesbar, und iOS zoomt beim Tippen in jedes Feld unter 16 px.
*
* Hell ist reines Weiss auf hellgrauem Grund, dunkel echtes Schwarz - auf
* OLED-Displays schont das den Akku. Schatten fast flach: auf kleiner Flaeche
* trennen Rahmen ruhiger als Tiefe.
* =========================================================================== */
html.theme-mobile {
--spacing: 0.21rem;
--app-bar-height: 3.5rem;
--text-lg: 1.0625rem;
--text-xl: 1.1875rem;
--text-2xl: 1.375rem;
--text-3xl: 1.625rem;
--text-4xl: 2rem;
--text-5xl: 2.5rem;
--radius-sm: 0.2rem;
--radius-md: 0.3rem;
--radius-lg: 0.45rem;
--radius-xl: 0.6rem;
--radius-2xl: 0.8rem;
}
html.theme-mobile:not(.dark) {
--color-canvas: #f2f2f2;
--color-surface: #ffffff;
--shadow-card: 0 1px 2px rgb(31 31 31 / 0.05);
--shadow-lift: 0 6px 18px rgb(31 31 31 / 0.12);
}
html.theme-mobile.dark {
--color-canvas: #000000;
--color-surface: #121212;
--color-ink-50: #1a1a1a;
--color-ink-100: #242424;
--color-ink-200: #333333;
--shadow-card: 0 0 0 1px rgb(255 255 255 / 0.04);
--shadow-lift: 0 0 0 1px rgb(255 255 255 / 0.08), 0 10px 28px rgb(0 0 0 / 0.6);
}
@layer base {
:root {
/*
+1 -1
View File
@@ -18,7 +18,7 @@ import { PixelRunner } from '../components/layout/PixelRunner';
/*
* Darstellung der Oberflaeche. Sie hat zwei unabhaengige Achsen:
*
* Farbwelt (palette) perinco | pixel | outdoor | cyberpunk | rainy | snow | aura
* Farbwelt (palette) perinco | pixel | outdoor | cyberpunk | rainy | snow | aura | mobile
* -> Klasse theme-* am <html>
* Modus (mode) hell | dunkel -> Klasse dark am <html>
*
+2 -1
View File
@@ -1,4 +1,4 @@
export const THEME_PALETTES = ['perinco', 'pixel', 'outdoor', 'cyberpunk', 'rainy', 'snow', 'aura'] as const;
export const THEME_PALETTES = ['perinco', 'pixel', 'outdoor', 'cyberpunk', 'rainy', 'snow', 'aura', 'mobile'] as const;
export type ThemePalette = (typeof THEME_PALETTES)[number];
export const THEME_PALETTE_LABELS: Record<ThemePalette, { name: string; hint: string }> = {
@@ -9,6 +9,7 @@ export const THEME_PALETTE_LABELS: Record<ThemePalette, { name: string; hint: st
rainy: { name: 'Rainy', hint: 'Regenwetter: Nieselregen, Wolken mit Wetterleuchten, Schieferblau' },
snow: { name: 'Snow', hint: 'Winter: Schneefall, der sich unten sammelt, Eisblau' },
aura: { name: 'Aura', hint: 'Hell Sunshine mit Sonnenstrahlen, dunkel Mond mit Sternen - ziehende Wolken' },
mobile: { name: 'Mobile', hint: 'Fürs Handy: kompakter, mehr Inhalt pro Bildschirm, dunkel echtes Schwarz' },
};
export type Role = 'user' | 'external' | 'lead' | 'management' | 'admin';