Files
nutriscan/app/globals.css
T

530 lines
17 KiB
CSS
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
@tailwind base;
@tailwind components;
@tailwind utilities;
/* Fonts are self-hosted through next/font. */
/* ─── Design Tokens ───────────────────────────────────────────────────── */
@layer base {
:root {
/* Warm neutral palette */
--bg-base: #f9f6f0;
--bg-surface: #f4f0e8;
--bg-elevated: #ffffff;
--fg-primary: #1e1810;
--fg-secondary: #5e4e3c;
--fg-muted: #9a8870;
--fg-faint: #b8a88a;
--border-subtle: #e8e0d0;
--border-strong: #d4c8b0;
/* Single accent: editorial green */
--accent: oklch(52% 0.11 155);
--accent-light: oklch(72% 0.10 155);
--accent-dark: oklch(38% 0.10 155);
--accent-muted: oklch(92% 0.04 155);
/* Nutri-Score grade colors */
--score-a: #1a7a4a;
--score-b: #5da832;
--score-c: #e8c110;
--score-d: #e07820;
--score-e: #c0201a;
/* Spacing primitives */
--section-gap: 7rem;
--container: 1120px;
--radius: 0.375rem;
/* shadcn/ui required tokens → warm neutral mapped */
--background: 36 30% 96%;
--foreground: 24 20% 10%;
--card: 36 30% 98%;
--card-foreground: 24 20% 10%;
--popover: 36 30% 98%;
--popover-foreground: 24 20% 10%;
--primary: 155 40% 32%; /* accent green */
--primary-foreground: 0 0% 100%;
--secondary: 36 22% 90%;
--secondary-foreground: 24 20% 20%;
--muted: 36 20% 92%;
--muted-foreground: 24 15% 46%;
--destructive: 0 72% 44%;
--destructive-foreground: 0 0% 100%;
--border: 36 20% 86%;
--input: 36 20% 86%;
--ring: 155 40% 32%;
--chart-1: oklch(52% 0.11 155);
--chart-2: oklch(62% 0.14 200);
--chart-3: oklch(70% 0.16 60);
--chart-4: oklch(56% 0.18 30);
--chart-5: oklch(52% 0.15 340);
}
.dark {
--bg-base: #110e09;
--bg-surface: #1a1610;
--bg-elevated: #231e17;
--fg-primary: #f4f0e8;
--fg-secondary: #c8b898;
--fg-muted: #8a7860;
--fg-faint: #5e4e3c;
--border-subtle: #2e2618;
--border-strong: #3e3228;
--accent: oklch(62% 0.12 155);
--accent-light: oklch(75% 0.10 155);
--accent-dark: oklch(44% 0.10 155);
--accent-muted: oklch(20% 0.06 155);
--background: 24 20% 8%;
--foreground: 36 30% 94%;
--card: 24 20% 10%;
--card-foreground: 36 30% 94%;
--popover: 24 20% 10%;
--popover-foreground: 36 30% 94%;
--primary: 155 38% 48%;
--primary-foreground: 0 0% 100%;
--secondary: 24 18% 18%;
--secondary-foreground: 36 28% 88%;
--muted: 24 16% 16%;
--muted-foreground: 36 20% 58%;
--destructive: 0 62% 42%;
--destructive-foreground: 0 0% 100%;
--border: 24 18% 18%;
--input: 24 18% 18%;
--ring: 155 38% 48%;
}
/* ── Base resets & typography ───────────────────────────────────────── */
* {
@apply border-border;
}
html {
font-feature-settings: "kern" 1, "liga" 1, "calt" 1, "ss01" 1;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-rendering: optimizeLegibility;
}
body {
background-color: var(--bg-base);
color: var(--fg-primary);
font-family: var(--font-inter), system-ui, sans-serif;
font-size: 1rem;
line-height: 1.72;
transition: background-color 0.4s ease, color 0.4s ease;
}
/* Headings use the active display font. */
h1, h2, h3, h4 {
font-family: var(--font-display), Georgia, serif;
font-weight: 400;
font-style: normal;
}
/* Hairline horizontal rule */
hr {
border: none;
border-top: 1px solid var(--border-subtle);
}
}
/* ─── Utility layer ───────────────────────────────────────────────────── */
@layer utilities {
/* Scrollbar */
.scrollbar-hide { -ms-overflow-style: none; scrollbar-width: none; }
.scrollbar-hide::-webkit-scrollbar { display: none; }
/* Editorial typography helpers */
.font-display { font-family: var(--font-display), Georgia, serif; }
.font-display-i { font-family: var(--font-display), Georgia, serif; font-style: italic; }
/* Container max-width */
.container-editorial {
width: 100%;
max-width: var(--container);
margin-inline: auto;
padding-inline: clamp(1.25rem, 5vw, 3rem);
}
/* Hairline divider */
.hairline {
border: none;
border-top: 1px solid var(--border-subtle);
}
.hairline-v {
border: none;
border-left: 1px solid var(--border-subtle);
}
/* Section vertical rhythm */
.section-py { padding-top: var(--section-gap); padding-bottom: var(--section-gap); }
.section-pt { padding-top: var(--section-gap); }
.section-pb { padding-bottom: var(--section-gap); }
/* Warm surface tokens */
.bg-base { background-color: var(--bg-base); }
.bg-surface { background-color: var(--bg-surface); }
.bg-elevated { background-color: var(--bg-elevated); }
.text-primary { color: var(--fg-primary); }
.text-secondary{ color: var(--fg-secondary); }
.text-muted { color: var(--fg-muted); }
.text-faint { color: var(--fg-faint); }
/* Accent utilities */
.text-accent { color: var(--accent); }
.bg-accent { background-color: var(--accent); }
.bg-accent-muted { background-color: var(--accent-muted); }
.border-accent { border-color: var(--accent); }
/* Label caps */
.label {
font-size: 0.6875rem;
font-weight: 600;
letter-spacing: 0.12em;
text-transform: uppercase;
font-family: var(--font-inter), system-ui, sans-serif;
}
.label-lg {
font-size: 0.75rem;
font-weight: 600;
letter-spacing: 0.10em;
text-transform: uppercase;
font-family: var(--font-inter), system-ui, sans-serif;
}
/* Product grid performance */
.product-grid { contain: layout style; }
.product-card { will-change: transform; backface-visibility: hidden; }
/* Stagger animation helpers */
.anim-delay-1 { animation-delay: 0.1s; }
.anim-delay-2 { animation-delay: 0.2s; }
.anim-delay-3 { animation-delay: 0.3s; }
.anim-delay-4 { animation-delay: 0.4s; }
.anim-delay-5 { animation-delay: 0.5s; }
/* Nutri-Score grade pills */
.grade-a { background: var(--score-a); color: #fff; }
.grade-b { background: var(--score-b); color: #fff; }
.grade-c { background: var(--score-c); color: #1e1810; }
.grade-d { background: var(--score-d); color: #fff; }
.grade-e { background: var(--score-e); color: #fff; }
/* Thin top-border accent card */
.card-accent-top {
border-top: 2px solid var(--accent);
}
/* Hover lift */
.hover-lift {
transition: transform 0.3s cubic-bezier(0.16, 1, 0.3, 1),
box-shadow 0.3s cubic-bezier(0.16, 1, 0.3, 1);
}
.hover-lift:hover {
transform: translateY(-3px);
box-shadow: 0 12px 40px -8px rgba(30, 24, 16, 0.12);
}
/* Monochrome icon filter for editorial look */
.icon-mono {
filter: grayscale(1);
opacity: 0.7;
}
}
/* ─── Component layer ─────────────────────────────────────────────────── */
@layer components {
/* ── Editorial Section Header ────────────────────────────────────────── */
.section-header {
@apply mb-16;
}
.section-header .eyebrow {
@apply label text-accent mb-4 block;
}
.section-header h2 {
@apply font-display text-display-lg text-[var(--fg-primary)] mb-5;
}
.section-header p {
@apply text-[var(--fg-secondary)] text-lg leading-relaxed max-w-[65ch];
}
/* ── Warm Card ───────────────────────────────────────────────────────── */
.card-warm {
background-color: var(--bg-elevated);
border: 1px solid var(--border-subtle);
border-radius: 0.75rem;
transition: border-color 0.25s ease, box-shadow 0.25s ease;
}
.card-warm:hover {
border-color: var(--border-strong);
box-shadow: 0 8px 32px -8px rgba(30, 24, 16, 0.10);
}
/* ── Accent Button ───────────────────────────────────────────────────── */
.btn-accent {
display: inline-flex;
align-items: center;
gap: 0.5rem;
padding: 0.75rem 1.5rem;
background-color: var(--accent);
color: #fff;
border-radius: 0.375rem;
font-size: 0.875rem;
font-weight: 600;
letter-spacing: 0.02em;
font-family: var(--font-inter), sans-serif;
transition: background-color 0.2s ease, transform 0.15s ease;
cursor: pointer;
border: none;
}
.btn-accent:hover {
background-color: var(--accent-dark);
transform: translateY(-1px);
}
.btn-accent:active { transform: translateY(0); }
.btn-accent:focus-visible,
.btn-ghost:focus-visible {
outline: 2px solid var(--accent);
outline-offset: 3px;
}
/* ── Ghost Button ────────────────────────────────────────────────────── */
.btn-ghost {
display: inline-flex;
align-items: center;
gap: 0.5rem;
padding: 0.6875rem 1.375rem;
background: transparent;
color: var(--fg-primary);
border: 1px solid var(--border-strong);
border-radius: 0.375rem;
font-size: 0.875rem;
font-weight: 500;
font-family: var(--font-inter), sans-serif;
transition: background-color 0.2s ease, border-color 0.2s ease;
cursor: pointer;
}
.btn-ghost:hover {
background-color: var(--bg-surface);
border-color: var(--fg-muted);
}
/* ── Stat Cell (Hero metrics) ────────────────────────────────────────── */
.stat-cell {
@apply flex flex-col items-center gap-1;
}
.stat-cell .stat-value {
font-family: var(--font-display), Georgia, serif;
font-size: 2rem;
line-height: 1;
color: var(--fg-primary);
}
.stat-cell .stat-label {
@apply label text-[var(--fg-muted)];
}
/* ── Step number (How It Works) ──────────────────────────────────────── */
.step-number {
font-family: var(--font-display), Georgia, serif;
font-size: 3.5rem;
line-height: 1;
color: var(--border-strong);
}
/* ── Nutri-Score Hero metric ─────────────────────────────────────────── */
.nutriscore-hero {
display: inline-flex;
align-items: center;
justify-content: center;
width: 5rem;
height: 5rem;
border-radius: 50%;
font-family: var(--font-display), Georgia, serif;
font-size: 2.25rem;
animation: score-reveal 0.6s cubic-bezier(0.34, 1.56, 0.64, 1) forwards;
}
/* ── Search input editorial ──────────────────────────────────────────── */
.search-editorial {
width: 100%;
background: var(--bg-elevated);
border: 1px solid var(--border-subtle);
border-radius: 0.5rem;
display: flex;
align-items: center;
gap: 0.75rem;
padding: 0 1.25rem;
transition: border-color 0.2s ease, box-shadow 0.2s ease;
}
.search-editorial:focus-within {
border-color: var(--accent);
box-shadow: 0 0 0 3px oklch(52% 0.11 155 / 0.12);
}
.search-editorial input {
flex: 1;
background: transparent;
border: none;
outline: none;
padding: 1.125rem 0;
font-family: var(--font-inter), sans-serif;
font-size: 1rem;
color: var(--fg-primary);
}
.search-editorial input::placeholder {
color: var(--fg-faint);
}
}
/* ─── Keyframe animations ─────────────────────────────────────────────── */
@keyframes fade-up {
from { opacity: 0; transform: translateY(1.5rem); }
to { opacity: 1; transform: translateY(0); }
}
@keyframes fade-in {
from { opacity: 0; }
to { opacity: 1; }
}
@keyframes stagger-in {
from { opacity: 0; transform: translateY(0.75rem); }
to { opacity: 1; transform: translateY(0); }
}
@keyframes line-grow {
from { transform: scaleX(0); transform-origin: left; }
to { transform: scaleX(1); transform-origin: left; }
}
@keyframes score-reveal {
from { transform: scale(0.6); opacity: 0; }
to { transform: scale(1); opacity: 1; }
}
@keyframes fadeInUp {
from { opacity: 0; transform: translateY(1rem); }
to { opacity: 1; transform: translateY(0); }
}
/* ─── Legacy animation class aliases (keep compatibility) ─────────────── */
.animate-in { animation: fadeInUp 0.6s ease-out forwards; }
.fade-in-0 { opacity: 0; }
.slide-in-from-bottom-4 { transform: translateY(1rem); }
.animate-fade-up { animation: fade-up 0.7s cubic-bezier(0.16, 1, 0.3, 1) forwards; }
.animate-fade-in { animation: fade-in 0.5s ease forwards; }
.animate-stagger-in { animation: stagger-in 0.5s cubic-bezier(0.16, 1, 0.3, 1) forwards; }
.animate-pulse-slow { animation: pulse 3s cubic-bezier(0.4, 0, 0.6, 1) infinite; }
/* ─── Redesign: ink palette tokens (mirror the HTML spec) ────────────── */
:root {
--ink-900: #141312;
--ink-800: #26231f;
--ink-700: #3d3934;
--ink-600: #595149;
--ink-500: #7a7269;
--ink-400: #a39c93;
--ink-300: #c9c3ba;
--ink-200: #e4dfd7;
--ink-150: #ece7de;
--ink-100: #f3efe7;
--ink-50: #f9f6f0;
--ink-0: #fdfbf5;
--nutri-a: #038141;
--nutri-b: #85bb2f;
--nutri-c: #fecb02;
--nutri-d: #ee8100;
--nutri-e: #e63e11;
--accent-soft: oklch(94% 0.04 155);
--accent-ink: oklch(28% 0.06 155);
--warn: #b45309;
--warn-soft: #fef3c7;
--font-display: var(--font-instrument-serif);
--font-serif: var(--font-display), 'Iowan Old Style', Georgia, serif;
--font-mono: 'JetBrains Mono', 'Fira Code', ui-monospace, Menlo, monospace;
}
.landing-font {
--font-display: var(--font-newsreader);
}
/* ─── Redesign: nutri-letter hero circle ─────────────────────────────── */
.nutri-letter {
display: inline-flex;
align-items: center;
justify-content: center;
border-radius: 50%;
font-family: var(--font-display), Georgia, serif;
color: #fff;
font-weight: 400;
letter-spacing: -0.03em;
line-height: 1;
box-shadow: inset 0 -3px 0 rgba(0,0,0,0.15), 0 8px 24px -8px rgba(0,0,0,0.2);
}
.nutri-letter.grade-a, .nutri-letter.a { background: var(--nutri-a); }
.nutri-letter.grade-b, .nutri-letter.b { background: var(--nutri-b); }
.nutri-letter.grade-c, .nutri-letter.c { background: var(--nutri-c); color: #3a2a00; }
.nutri-letter.grade-d, .nutri-letter.d { background: var(--nutri-d); }
.nutri-letter.grade-e, .nutri-letter.e { background: var(--nutri-e); }
/* ─── Redesign: nutri-scale badge (full A–E row) ─────────────────────── */
.nutri-badge {
display: inline-flex;
align-items: center;
font-family: var(--font-inter), sans-serif;
font-weight: 800;
border-radius: 999px;
overflow: hidden;
background: var(--ink-100);
padding: 3px;
gap: 2px;
}
.nutri-badge .seg {
border-radius: 999px;
display: flex;
align-items: center;
justify-content: center;
color: #fff;
letter-spacing: -0.02em;
transition: transform 0.25s;
opacity: 0.35;
filter: saturate(0.3);
}
.nutri-badge .seg.active { opacity: 1; filter: none; transform: scale(1.15); box-shadow: 0 2px 8px rgba(0,0,0,0.15); }
.nutri-badge .seg.a { background: var(--nutri-a); }
.nutri-badge .seg.b { background: var(--nutri-b); }
.nutri-badge .seg.c { background: var(--nutri-c); color: #3a2a00; }
.nutri-badge .seg.d { background: var(--nutri-d); }
.nutri-badge .seg.e { background: var(--nutri-e); }
/* ─── Redesign: eyebrow mono label ──────────────────────────────────── */
.eyebrow-mono {
font-family: var(--font-mono, ui-monospace, monospace);
font-size: 11px;
letter-spacing: 0.12em;
text-transform: uppercase;
color: var(--ink-500);
font-weight: 500;
}
/* ─── Redesign: product card chip ─────────────────────────────────── */
.rd-chip {
display: inline-flex;
align-items: center;
gap: 6px;
padding: 4px 10px;
border-radius: 999px;
font-size: 12px;
font-weight: 500;
background: var(--ink-100, #f3efe7);
color: var(--ink-700, #3d3934);
border: 1px solid var(--ink-200, #e4dfd7);
}
.rd-chip.warn {
background: var(--warn-soft, #fef3c7);
color: var(--warn, #b45309);
border-color: #fcd34d;
}