style(design): migrate to DESIGN.md system

Full visual migration: Space Grotesk + DM Sans + JetBrains Mono fonts,
warm amber two-accent system (amber=state, blue=action), dark mode with
CSS vars + localStorage + FOUC prevention, mobile bottom nav (5 tabs),
full-width tables, error/skipped dot glow, ~13 hardcoded hex replaced
with CSS vars in 4 JS files, 5 new E2E tests.

Files: style.css (full rewrite), base.html (fonts, theme script, dark
toggle, bottom nav), settings.html (dark toggle card), dashboard.js,
logs.js, mappings.js, settings.js (color vars), 5 templates (bnav
active blocks), test_design_system_e2e.py (NEW).

Cache-bust: style.css?v=18, shared.js?v=14, dashboard.js?v=27,
logs.js?v=13, mappings.js?v=12, settings.js?v=8

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Claude Agent
2026-03-27 11:36:07 +00:00
parent c5757b8322
commit a8292c2ef2
13 changed files with 550 additions and 183 deletions

View File

@@ -1,16 +1,28 @@
<!DOCTYPE html>
<html lang="ro" style="color-scheme: light">
<html lang="ro">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>{% block title %}GoMag Import Manager{% endblock %}</title>
<!-- FOUC prevention: apply saved theme before any rendering -->
<script>
try {
var t = localStorage.getItem('theme');
if (!t) t = window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light';
if (t === 'dark') document.documentElement.setAttribute('data-theme', 'dark');
} catch(e) {}
</script>
<!-- Fonts (DESIGN.md) -->
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=DM+Sans:ital,opsz,wght@0,9..40,300;0,9..40,400;0,9..40,500;0,9..40,600;0,9..40,700;1,9..40,400&family=JetBrains+Mono:wght@400;500;600&family=Space+Grotesk:wght@400;500;600;700&display=swap" rel="stylesheet">
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.2/dist/css/bootstrap.min.css" rel="stylesheet">
<link href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.11.2/font/bootstrap-icons.css" rel="stylesheet">
{% set rp = request.scope.get('root_path', '') %}
<link href="{{ rp }}/static/css/style.css?v=17" rel="stylesheet">
<link href="{{ rp }}/static/css/style.css?v=18" rel="stylesheet">
</head>
<body>
<!-- Top Navbar -->
<!-- Top Navbar (hidden on mobile via CSS) -->
<nav class="top-navbar">
<div class="navbar-brand">GoMag Import</div>
<div class="navbar-links">
@@ -20,10 +32,22 @@
<a href="{{ rp }}/logs" class="nav-tab {% block nav_logs %}{% endblock %}"><span class="d-none d-md-inline">Jurnale Import</span><span class="d-md-none">Jurnale</span></a>
<a href="{{ rp }}/settings" class="nav-tab {% block nav_settings %}{% endblock %}"><span class="d-none d-md-inline">Setari</span><span class="d-md-none">Setari</span></a>
</div>
<button class="dark-toggle" onclick="toggleDarkMode()" title="Comuta tema" aria-label="Comuta tema intunecata">
<i class="bi bi-sun-fill"></i>
</button>
</nav>
<!-- Bottom Nav (mobile only, shown via CSS) -->
<nav class="bottom-nav">
<a href="{{ rp }}/" class="bottom-nav-item {% block bnav_dashboard %}{% endblock %}"><i class="bi bi-speedometer2"></i><span>Dashboard</span></a>
<a href="{{ rp }}/mappings" class="bottom-nav-item {% block bnav_mappings %}{% endblock %}"><i class="bi bi-arrow-left-right"></i><span>Mapari</span></a>
<a href="{{ rp }}/missing-skus" class="bottom-nav-item {% block bnav_missing %}{% endblock %}"><i class="bi bi-exclamation-triangle"></i><span>Lipsa</span></a>
<a href="{{ rp }}/logs" class="bottom-nav-item {% block bnav_logs %}{% endblock %}"><i class="bi bi-journal-text"></i><span>Jurnale</span></a>
<a href="{{ rp }}/settings" class="bottom-nav-item {% block bnav_settings %}{% endblock %}"><i class="bi bi-gear"></i><span>Setari</span></a>
</nav>
<!-- Main content -->
<main class="main-content">
<main class="main-content {% block main_class %}{% endblock %}">
{% block content %}{% endblock %}
</main>
@@ -39,7 +63,7 @@
<div style="margin-bottom:8px; font-size:0.85rem">
<small class="text-muted">Produs:</small> <strong id="qmProductName"></strong>
</div>
<div class="qm-row" style="font-size:0.7rem; color:#9ca3af; padding:0 0 2px">
<div class="qm-row" style="font-size:0.7rem; color:var(--text-muted); padding:0 0 2px">
<span style="flex:1">CODMAT</span>
<span style="width:70px">Cant.</span>
<span style="width:30px"></span>
@@ -116,7 +140,27 @@
<script>window.ROOT_PATH = "{{ rp }}";</script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.2/dist/js/bootstrap.bundle.min.js"></script>
<script src="{{ rp }}/static/js/shared.js?v=13"></script>
<script src="{{ rp }}/static/js/shared.js?v=14"></script>
<script>
// Dark mode toggle
function toggleDarkMode() {
var isDark = document.documentElement.getAttribute('data-theme') === 'dark';
var newTheme = isDark ? 'light' : 'dark';
document.documentElement.setAttribute('data-theme', newTheme);
try { localStorage.setItem('theme', newTheme); } catch(e) {}
updateDarkToggleIcon();
// Sync settings page toggle if present
var settToggle = document.getElementById('settDarkMode');
if (settToggle) settToggle.checked = (newTheme === 'dark');
}
function updateDarkToggleIcon() {
var isDark = document.documentElement.getAttribute('data-theme') === 'dark';
document.querySelectorAll('.dark-toggle i').forEach(function(el) {
el.className = isDark ? 'bi bi-moon-fill' : 'bi bi-sun-fill';
});
}
updateDarkToggleIcon();
</script>
{% block scripts %}{% endblock %}
</body>
</html>

View File

@@ -1,6 +1,7 @@
{% extends "base.html" %}
{% block title %}Dashboard - GoMag Import{% endblock %}
{% block nav_dashboard %}active{% endblock %}
{% block bnav_dashboard %}active{% endblock %}
{% block content %}
<h4 class="mb-4">Panou de Comanda</h4>
@@ -112,5 +113,5 @@
{% endblock %}
{% block scripts %}
<script src="{{ request.scope.get('root_path', '') }}/static/js/dashboard.js?v=26"></script>
<script src="{{ request.scope.get('root_path', '') }}/static/js/dashboard.js?v=27"></script>
{% endblock %}

View File

@@ -1,6 +1,7 @@
{% extends "base.html" %}
{% block title %}Jurnale Import - GoMag Import{% endblock %}
{% block nav_logs %}active{% endblock %}
{% block bnav_logs %}active{% endblock %}
{% block content %}
<h4 class="mb-4">Jurnale Import</h4>
@@ -101,5 +102,5 @@
{% endblock %}
{% block scripts %}
<script src="{{ request.scope.get('root_path', '') }}/static/js/logs.js?v=12"></script>
<script src="{{ request.scope.get('root_path', '') }}/static/js/logs.js?v=13"></script>
{% endblock %}

View File

@@ -1,6 +1,7 @@
{% extends "base.html" %}
{% block title %}Mapari SKU - GoMag Import{% endblock %}
{% block nav_mappings %}active{% endblock %}
{% block bnav_mappings %}active{% endblock %}
{% block content %}
<div class="d-flex justify-content-between align-items-center mb-4">
@@ -150,5 +151,5 @@
{% endblock %}
{% block scripts %}
<script src="{{ request.scope.get('root_path', '') }}/static/js/mappings.js?v=11"></script>
<script src="{{ request.scope.get('root_path', '') }}/static/js/mappings.js?v=12"></script>
{% endblock %}

View File

@@ -1,6 +1,7 @@
{% extends "base.html" %}
{% block title %}SKU-uri Lipsa - GoMag Import{% endblock %}
{% block nav_missing %}active{% endblock %}
{% block bnav_missing %}active{% endblock %}
{% block content %}
<div class="d-flex justify-content-between align-items-center mb-4">

View File

@@ -1,10 +1,23 @@
{% extends "base.html" %}
{% block title %}Setari - GoMag Import{% endblock %}
{% block nav_settings %}active{% endblock %}
{% block bnav_settings %}active{% endblock %}
{% block main_class %}constrained{% endblock %}
{% block content %}
<h4 class="mb-3">Setari</h4>
<!-- Dark mode toggle -->
<div class="theme-toggle-card">
<div>
<i class="bi bi-moon-fill me-2"></i>
<label for="settDarkMode">Mod intunecat</label>
</div>
<div class="form-check form-switch mb-0">
<input class="form-check-input" type="checkbox" role="switch" id="settDarkMode" style="width:2.5rem;height:1.25rem">
</div>
</div>
<div class="row g-3 mb-3">
<!-- GoMag API card -->
<div class="col-md-6">
@@ -233,5 +246,5 @@
{% endblock %}
{% block scripts %}
<script src="{{ request.scope.get('root_path', '') }}/static/js/settings.js?v=7"></script>
<script src="{{ request.scope.get('root_path', '') }}/static/js/settings.js?v=8"></script>
{% endblock %}