feat(miniapp): lock to variant A; green active dot; tighter spacing in menu and profile card

This commit is contained in:
wasrusgen 2026-05-09 12:25:19 +03:00
parent 7e0d2b98b0
commit ce91c0283b
3 changed files with 30 additions and 58 deletions

View File

@ -11,10 +11,8 @@ const app = document.getElementById("app");
function setupTelegram() { function setupTelegram() {
const scheme = tg?.colorScheme || (window.matchMedia?.("(prefers-color-scheme: dark)").matches ? "dark" : "light"); const scheme = tg?.colorScheme || (window.matchMedia?.("(prefers-color-scheme: dark)").matches ? "dark" : "light");
document.documentElement.setAttribute("data-theme", scheme); document.documentElement.setAttribute("data-theme", scheme);
// Зафиксирован вариант A — Editorial Calm
// Дизайн-вариант: brand (default) / a / c — сохраняется в localStorage. document.documentElement.setAttribute("data-variant", "a");
const savedVariant = (typeof localStorage !== "undefined" && localStorage.getItem("zov_variant")) || "brand";
document.documentElement.setAttribute("data-variant", savedVariant);
if (!tg) return; if (!tg) return;
try { try {
@ -27,31 +25,6 @@ function setupTelegram() {
} catch (e) { console.warn(e); } } catch (e) { console.warn(e); }
} }
function setVariant(variant) {
document.documentElement.setAttribute("data-variant", variant);
try { localStorage.setItem("zov_variant", variant); } catch (e) {}
// Перерисовать активную кнопку в свитчере
document.querySelectorAll(".theme-switch button").forEach(b => {
b.classList.toggle("active", b.dataset.variant === variant);
});
haptic();
}
function buildThemeSwitch() {
const current = document.documentElement.getAttribute("data-variant") || "brand";
const node = el(`
<div class="theme-switch" role="tablist" aria-label="Дизайн-вариант">
<button data-variant="brand" class="${current === "brand" ? "active" : ""}">Brand · ZOV</button>
<button data-variant="a" class="${current === "a" ? "active" : ""}">A · Editorial</button>
<button data-variant="c" class="${current === "c" ? "active" : ""}">C · Architect</button>
</div>
`);
node.querySelectorAll("button").forEach(btn => {
btn.addEventListener("click", () => setVariant(btn.dataset.variant));
});
return node;
}
function haptic(type = "selection") { function haptic(type = "selection") {
try { try {
if (!tg?.HapticFeedback) return; if (!tg?.HapticFeedback) return;
@ -118,7 +91,6 @@ function renderManager(me) {
const tgId = me.user?.tg_id ? `ID ${me.user.tg_id}` : ""; const tgId = me.user?.tg_id ? `ID ${me.user.tg_id}` : "";
app.innerHTML = ""; app.innerHTML = "";
app.appendChild(buildThemeSwitch());
app.appendChild(el(` app.appendChild(el(`
<header class="profile-card"> <header class="profile-card">
@ -180,7 +152,6 @@ function renderClient(me) {
const greetName = me.user?.full_name || "Здравствуйте"; const greetName = me.user?.full_name || "Здравствуйте";
app.innerHTML = ""; app.innerHTML = "";
app.appendChild(buildThemeSwitch());
app.appendChild(el(` app.appendChild(el(`
<header class="profile-card"> <header class="profile-card">

View File

@ -72,9 +72,10 @@ html[data-variant="a"] {
--accent-1: #3C5278; /* editorial blue */ --accent-1: #3C5278; /* editorial blue */
--accent-2: #6B4A2B; /* walnut */ --accent-2: #6B4A2B; /* walnut */
--accent-3: #B85A2D; /* terracotta */ --accent-3: #B85A2D; /* terracotta */
--status-active: #B85A2D; /* Active = зелёный сигнал (бренд ЗОВ); lapsed/grace остаются в палитре A */
--status-active: #76BD22;
--status-lapsed: #B85A2D; --status-lapsed: #B85A2D;
--status-grace: #B85A2D; --status-grace: #6B4A2B;
--r-card: 0; --r-card: 0;
--r-btn: 0; --r-btn: 0;
@ -149,7 +150,7 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
#app { #app {
max-width: 560px; max-width: 560px;
margin: 0 auto; margin: 0 auto;
padding: var(--s4) var(--s4) calc(var(--s8) + env(safe-area-inset-bottom)); padding: var(--s3) var(--s4) calc(var(--s7) + env(safe-area-inset-bottom));
min-height: 100vh; min-height: 100vh;
} }
@ -213,8 +214,8 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
background: var(--card); background: var(--card);
border: 1px solid var(--line-strong); border: 1px solid var(--line-strong);
border-radius: var(--r-card); border-radius: var(--r-card);
padding: var(--s6) var(--s5) var(--s5); padding: var(--s5) var(--s4) var(--s4);
margin-bottom: var(--s7); margin-bottom: var(--s5);
position: relative; position: relative;
overflow: hidden; overflow: hidden;
} }
@ -234,7 +235,7 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
letter-spacing: 0.12em; letter-spacing: 0.12em;
text-transform: uppercase; text-transform: uppercase;
color: var(--muted); color: var(--muted);
margin-bottom: var(--s3); margin-bottom: var(--s2);
display: inline-flex; display: inline-flex;
align-items: center; align-items: center;
gap: var(--s2); gap: var(--s2);
@ -252,7 +253,7 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
display: flex; display: flex;
align-items: flex-start; align-items: flex-start;
gap: var(--s4); gap: var(--s4);
margin-bottom: var(--s4); margin-bottom: var(--s3);
} }
.profile-card .info { flex: 1; min-width: 0; } .profile-card .info { flex: 1; min-width: 0; }
@ -260,12 +261,12 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
.profile-card .name { .profile-card .name {
font-family: var(--font-display); font-family: var(--font-display);
font-style: italic; font-style: italic;
font-size: 30px; font-size: 26px;
font-weight: 400; font-weight: 400;
line-height: 1.05; line-height: 1.05;
letter-spacing: -0.02em; letter-spacing: -0.02em;
color: var(--ink); color: var(--ink);
margin-bottom: var(--s2); margin-bottom: var(--s1);
word-break: break-word; word-break: break-word;
} }
@ -275,8 +276,8 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
} }
.profile-card .avatar { .profile-card .avatar {
width: 52px; width: 44px;
height: 52px; height: 44px;
border-radius: var(--r-pill); border-radius: var(--r-pill);
background: var(--paper-2); background: var(--paper-2);
display: grid; display: grid;
@ -284,7 +285,7 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
flex-shrink: 0; flex-shrink: 0;
font-family: var(--font-display); font-family: var(--font-display);
font-style: italic; font-style: italic;
font-size: 26px; font-size: 22px;
font-weight: 400; font-weight: 400;
color: var(--accent-1); color: var(--accent-1);
border: 1px solid var(--line-strong); border: 1px solid var(--line-strong);
@ -301,8 +302,8 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
letter-spacing: 0.08em; letter-spacing: 0.08em;
text-transform: uppercase; text-transform: uppercase;
color: var(--muted); color: var(--muted);
margin-top: var(--s4); margin-top: var(--s3);
padding-top: var(--s4); padding-top: var(--s3);
border-top: 1px solid var(--line); border-top: 1px solid var(--line);
} }
@ -350,7 +351,7 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
letter-spacing: 0.14em; letter-spacing: 0.14em;
color: var(--muted); color: var(--muted);
padding: 0 var(--s4); padding: 0 var(--s4);
margin: var(--s7) 0 var(--s3); margin: var(--s5) 0 var(--s2);
display: flex; display: flex;
align-items: center; align-items: center;
gap: var(--s3); gap: var(--s3);
@ -378,9 +379,9 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
.menu-item { .menu-item {
display: flex; display: flex;
align-items: center; align-items: center;
gap: var(--s4); gap: var(--s3);
padding: var(--s4) var(--s5); padding: var(--s3) var(--s4);
min-height: 64px; min-height: 52px;
color: var(--ink); color: var(--ink);
cursor: pointer; cursor: pointer;
transition: background 0.12s; transition: background 0.12s;
@ -391,7 +392,7 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
content: ""; content: "";
position: absolute; position: absolute;
top: 0; top: 0;
left: var(--s5); left: var(--s4);
right: 0; right: 0;
height: 1px; height: 1px;
background: var(--line); background: var(--line);
@ -400,8 +401,8 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
.menu-item:active { background: var(--paper-2); } .menu-item:active { background: var(--paper-2); }
.menu-item .icon { .menu-item .icon {
width: 32px; width: 28px;
height: 32px; height: 28px;
display: grid; display: grid;
place-items: center; place-items: center;
flex-shrink: 0; flex-shrink: 0;
@ -409,8 +410,8 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
} }
.menu-item .icon svg { .menu-item .icon svg {
width: 22px; width: 20px;
height: 22px; height: 20px;
stroke-width: 1.6; stroke-width: 1.6;
} }
@ -422,7 +423,7 @@ button { font: inherit; cursor: pointer; border: none; background: none; color:
.menu-item .label { .menu-item .label {
font-family: var(--font-ui); font-family: var(--font-ui);
font-size: 15px; font-size: 14.5px;
font-weight: 500; font-weight: 500;
letter-spacing: -0.01em; letter-spacing: -0.01em;
display: flex; display: flex;

View File

@ -12,7 +12,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin> <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&family=Geist:wght@400;500;600&family=Newsreader:ital,wght@0,400..600;1,400..600&family=Instrument+Serif:ital@0;1&family=JetBrains+Mono:wght@400;500&display=swap"> <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&family=Geist:wght@400;500;600&family=Newsreader:ital,wght@0,400..600;1,400..600&family=Instrument+Serif:ital@0;1&family=JetBrains+Mono:wght@400;500&display=swap">
<script src="https://telegram.org/js/telegram-web-app.js"></script> <script src="https://telegram.org/js/telegram-web-app.js"></script>
<link rel="stylesheet" href="assets/styles.css?v=20260509e"> <link rel="stylesheet" href="assets/styles.css?v=20260509f">
</head> </head>
<body> <body>
<main id="app"> <main id="app">
@ -20,7 +20,7 @@
<div class="spinner"></div> <div class="spinner"></div>
</div> </div>
</main> </main>
<script src="assets/icons.js?v=20260509e"></script> <script src="assets/icons.js?v=20260509f"></script>
<script src="assets/app.js?v=20260509e"></script> <script src="assets/app.js?v=20260509f"></script>
</body> </body>
</html> </html>