@tailwind base; @tailwind components; @tailwind utilities; /* * Surfaces and neutrals. * * Accent variables are NOT defined here — they are written onto the root * element at runtime from the palette in @pig/core, so there is exactly one * definition of each colour and the CSS cannot drift from the TypeScript. */ :root { --bg: 0 0% 100%; --surface: 0 0% 100%; --surface-2: 240 5% 97%; --border: 240 6% 90%; --fg: 240 10% 4%; --muted: 240 4% 46%; --positive: 160 84% 32%; --warning: 32 95% 44%; --danger: 0 72% 45%; --info: 201 90% 40%; /* Safe-area insets, so layout can reference them even at zero. */ --safe-top: env(safe-area-inset-top, 0px); --safe-bottom: env(safe-area-inset-bottom, 0px); --safe-left: env(safe-area-inset-left, 0px); --safe-right: env(safe-area-inset-right, 0px); } :root[data-theme='dark'] { --bg: 240 10% 4%; --surface: 240 8% 7%; --surface-2: 240 6% 11%; --border: 240 5% 18%; --fg: 0 0% 98%; --muted: 240 5% 60%; --positive: 158 64% 52%; --warning: 38 92% 60%; --danger: 0 84% 65%; --info: 199 89% 60%; } @layer base { * { border-color: hsl(var(--border)); } html { /* Prevents iOS from silently enlarging text in landscape. */ -webkit-text-size-adjust: 100%; /* Keeps the background painted behind the rubber-band overscroll area. */ background-color: hsl(var(--bg)); } body { @apply bg-bg text-fg antialiased; font-feature-settings: 'cv02', 'cv03', 'cv04', 'cv11'; /* Stops the whole page bouncing on iOS while inner panes still scroll. */ overscroll-behavior-y: none; } /* * Mobile Safari zooms the viewport when a focused input has a font size * below 16px, and never zooms back out. This is the fix — not * user-scalable=no, which breaks pinch-zoom for everyone. */ input, select, textarea { font-size: max(16px, 1rem); } /* A visible, consistent focus ring — keyboard users need it, and the default varies wildly between browsers. */ :focus-visible { @apply outline-none ring-2 ring-accent ring-offset-2 ring-offset-bg; } /* Respect a reduced-motion preference rather than animating regardless. */ @media (prefers-reduced-motion: reduce) { *, *::before, *::after { animation-duration: 0.01ms !important; animation-iteration-count: 1 !important; transition-duration: 0.01ms !important; scroll-behavior: auto !important; } } } @layer components { /* Horizontal scrollers (pipeline boards, wide tables) get momentum scrolling and snap on touch, without hijacking the page. */ .scroll-x { @apply overflow-x-auto; -webkit-overflow-scrolling: touch; scrollbar-width: thin; overscroll-behavior-x: contain; } .scroll-x::-webkit-scrollbar { height: 6px; } .scroll-x::-webkit-scrollbar-thumb { background-color: hsl(var(--border)); border-radius: 3px; } /* Touch targets. 44px is the documented iOS minimum and the difference between a usable and a frustrating phone experience. */ .tap { @apply min-h-[44px] min-w-[44px]; } .card { @apply rounded-xl border border-border bg-surface; } /* Tabular figures keep money and percentages from jittering as they update, which matters on a dashboard that refreshes. */ .nums { font-variant-numeric: tabular-nums; font-feature-settings: 'tnum'; } }