@import './tokens.css';
@import './fonts.css';

*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  color-scheme: dark;
}

body {
  margin: 0;
  background: var(--color-bg);
  color: var(--color-text);
  font-family: var(--font-body);
  -webkit-font-smoothing: antialiased;
}

a {
  color: inherit;
}
/* Shared blog UI (React BlogPage/BlogPostPage + backend live HTML).
   Stable BEM class names — keep in sync with public/blog-ui/blog.css. */

:root {
  /* Covers are authored at 1200x630 - the size the bot asks for, and the size
     Open Graph wants. The box carries the same ratio so the art fills it edge
     to edge: nothing cropped, no letterbox bars, and every card the same
     height whatever is inside it. */
  --blog-cover-ratio: 1200 / 630;
}

/* The filter script drives visibility through the hidden attribute, and a
   class that sets display beats the attribute’s own rule — so an element got
   hidden="" and stayed on screen. Two elements had a [hidden] rule of their
   own and the featured card did not, which is exactly the kind of thing that
   is remembered once and then forgotten. Stated once for the whole page
   instead: inside the blog, hidden means hidden. */
.blog-page [hidden],
.blog-post [hidden] {
  display: none !important;
}

.blog-sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0, 0, 0, 0);
  white-space: nowrap;
  border: 0;
}

.blog-shell {
  width: 100%;
  overflow-x: clip;
  background: var(--color-bg);
  color: var(--color-text);
  min-height: 100vh;
  display: flex;
  flex-direction: column;
}

.blog-shell-main {
  flex: 1;
}

.blog-container {
  max-width: var(--content-max);
  margin: 0 auto;
  position: relative;
  z-index: 2;
}

/* —— Chrome: nav + footer (server HTML) —— */

.blog-nav {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-6);
  padding: 0 var(--nav-pad-x);
  height: var(--nav-height);
  border-bottom: 1px solid var(--color-border);
}

.blog-nav-brand {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  color: var(--color-text-strong);
  text-decoration: none;
}

/* The same lockup the SPA renders through its Logo component, from the same two
   assets — drawn as text here, the blog header read as a different brand. Sizes
   mirror Logo.module.css: 28/21 in the header, 24/19 in the footer. */
.blog-brand-mark {
  display: block;
  height: 28px;
  width: auto;
  flex-shrink: 0;
}

.blog-brand-wordmark {
  display: block;
  height: 21px;
  width: auto;
  max-width: 108px;
  flex-shrink: 0;
}

.blog-nav-brand[data-size='sm'] .blog-brand-mark {
  height: 24px;
}

.blog-nav-brand[data-size='sm'] .blog-brand-wordmark {
  height: 19px;
  max-width: 92px;
}

@media (max-width: 768px) {
  .blog-brand-mark {
    height: 26px;
  }

  .blog-brand-wordmark {
    height: 19px;
    max-width: 96px;
  }
}

/* Below this the wordmark would crowd the CTA, exactly as on the rest of the site. */
@media (max-width: 520px) {
  .blog-brand-wordmark {
    display: none;
  }
}

.blog-nav-links {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--space-5);
}

.blog-nav-links a {
  color: var(--color-text-soft);
  text-decoration: none;
  font-size: 14px;
  font-weight: 500;
}

.blog-nav-links a:hover,
.blog-nav-links a[aria-current='page'] {
  color: var(--color-text-strong);
}

/* Header actions, in the site's order: a quiet log-in beside the one solid CTA. */
.blog-nav-actions {
  display: inline-flex;
  align-items: center;
  gap: var(--space-5);
}

.blog-nav-login {
  color: var(--color-text-muted);
  font-size: 15.5px;
  text-decoration: none;
}

.blog-nav-login:hover {
  color: var(--color-text);
}

.blog-nav-cta {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: var(--space-3) var(--space-5);
  border-radius: var(--radius-md);
  background: var(--color-text);
  color: var(--color-bg);
  font-size: 14px;
  font-weight: 600;
  text-decoration: none;
}

.blog-nav-cta:hover {
  background: var(--color-text-strong);
  color: var(--color-bg);
}

.blog-site-footer {
  margin-top: auto;
  padding: var(--space-12) var(--section-pad-x) var(--space-8);
  border-top: 1px solid var(--color-border);
  background: var(--color-bg);
}

.blog-site-footer-grid {
  max-width: var(--content-max);
  margin: 0 auto;
  display: grid;
  grid-template-columns: minmax(0, 1.2fr) minmax(0, 2fr);
  gap: var(--space-10);
}

.blog-site-footer-tagline {
  margin: var(--space-3) 0 0;
  color: var(--color-text-muted);
  font-size: 14px;
}

.blog-site-footer-columns {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: var(--space-6);
}

.blog-site-footer-columns h2 {
  margin: 0 0 var(--space-3);
  font-family: var(--font-mono);
  font-size: 11px;
  letter-spacing: 0.14em;
  color: var(--color-text-dim);
}

.blog-site-footer-columns a {
  display: block;
  margin-bottom: var(--space-2);
  color: var(--color-text-soft);
  text-decoration: none;
  font-size: 14px;
}

.blog-site-footer-columns a:hover {
  color: var(--color-text-strong);
}

.blog-site-footer-bottom {
  max-width: var(--content-max);
  margin: var(--space-10) auto 0;
  padding-top: var(--space-6);
  border-top: 1px solid var(--color-border-soft);
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: var(--space-4);
  font-size: 13px;
  color: var(--color-text-dim);
}

.blog-site-footer-social {
  display: flex;
  gap: var(--space-4);
}

.blog-site-footer-social a {
  color: var(--color-text-soft);
  text-decoration: none;
}

.blog-site-footer-social a:hover {
  color: var(--color-text-strong);
}

/* —— Index page —— */

.blog-page {
  position: relative;
  padding: 40px var(--section-pad-x) 96px;
}

.blog-featured {
  display: grid;
  grid-template-columns: minmax(0, 1.05fr) minmax(0, 0.95fr);
  gap: var(--space-8);
  align-items: stretch;
  padding: var(--space-8);
  border: 1px solid var(--color-border-panel);
  border-radius: var(--radius-3xl);
  background: var(--color-surface-raised);
  text-decoration: none;
  color: inherit;
  transition:
    border-color 0.18s ease,
    background 0.18s ease;
}

.blog-featured:hover {
  border-color: var(--color-border-hover);
  background: var(--color-surface-6);
}

.blog-featured:focus-visible {
  outline: 2px solid var(--color-accent-soft);
  outline-offset: 3px;
}

.blog-featured-copy {
  display: flex;
  flex-direction: column;
  justify-content: center;
  min-width: 0;
  padding: var(--space-4);
}

.blog-featured-tag {
  align-self: flex-start;
  padding: 5px 10px;
  border: 1px solid var(--color-border-pill);
  border-radius: var(--radius-pill);
  font-family: var(--font-mono);
  font-size: 11px;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--color-text-soft);
}

.blog-featured-date {
  margin-top: var(--space-4);
  font-family: var(--font-mono);
  font-size: 12px;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--color-text-dim);
}

.blog-featured-title {
  margin: var(--space-4) 0 0;
  font-family: var(--font-display);
  font-weight: 600;
  font-size: clamp(28px, 3.2vw, 40px);
  line-height: 1.12;
  letter-spacing: -0.025em;
  color: var(--color-text-strong);
}

.blog-featured-lead {
  margin: var(--space-4) 0 0;
  max-width: 46ch;
  font-size: 16px;
  line-height: 1.65;
  color: var(--color-text-muted);
}

.blog-featured-author {
  display: inline-flex;
  align-items: center;
  gap: var(--space-3);
  margin-top: var(--space-6);
  font-size: 14px;
  color: var(--color-text-soft);
}

.blog-author-mark {
  width: 28px;
  height: 28px;
  border-radius: 50%;
  border: 1px solid var(--color-border-strong);
  background:
    radial-gradient(circle at 35% 30%, rgba(183, 196, 211, 0.45), transparent 55%),
    var(--color-surface-3);
}

.blog-controls {
  margin-top: var(--space-10);
  display: flex;
  flex-direction: column;
  gap: var(--space-5);
}

.blog-search {
  position: relative;
  display: block;
}

.blog-search-icon {
  position: absolute;
  left: 16px;
  top: 50%;
  transform: translateY(-50%);
  color: var(--color-text-dim);
  pointer-events: none;
}

.blog-search input {
  width: 100%;
  box-sizing: border-box;
  padding: 14px 16px 14px 44px;
  border: 1px solid var(--color-border-input);
  border-radius: var(--radius-xl);
  background: var(--color-surface-3);
  color: var(--color-text);
  font-family: var(--font-body);
  font-size: 15px;
}

.blog-search input::placeholder {
  color: var(--color-text-fainter);
}

.blog-search input:focus {
  outline: none;
  border-color: var(--color-border-hover-strong);
}

.blog-search input:focus-visible {
  outline: 2px solid var(--color-accent-soft);
  outline-offset: 2px;
}

.blog-filters {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2);
}

.blog-filter {
  padding: 8px 14px;
  border: 1px solid var(--color-border-strong);
  border-radius: var(--radius-pill);
  background: transparent;
  color: var(--color-text-soft);
  font-family: var(--font-body);
  font-size: 13px;
  font-weight: 500;
  cursor: pointer;
  transition:
    background 0.15s ease,
    border-color 0.15s ease,
    color 0.15s ease;
}

.blog-filter:hover {
  border-color: var(--color-border-hover-strong);
  color: var(--color-text-strong);
}

.blog-filter[data-active='true'] {
  border-color: var(--color-text);
  background: var(--color-text);
  color: var(--color-bg);
}

.blog-filter:focus-visible {
  outline: 2px solid var(--color-accent-soft);
  outline-offset: 2px;
}

.blog-grid {
  margin-top: var(--space-8);
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--space-6);
}

.blog-card {
  display: flex;
  flex-direction: column;
  gap: var(--space-4);
  text-decoration: none;
  color: inherit;
  min-width: 0;
}

.blog-card:focus-visible {
  outline: 2px solid var(--color-accent-soft);
  outline-offset: 4px;
  border-radius: var(--radius-xl);
}

.blog-card:hover .blog-card-title {
  color: var(--color-text-strong);
}

.blog-card-title {
  margin: 0;
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 18px;
  line-height: 1.35;
  letter-spacing: -0.015em;
  color: var(--color-text);
  display: -webkit-box;
  -webkit-line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
}

.blog-cover {
  position: relative;
  aspect-ratio: var(--blog-cover-ratio);
  border-radius: var(--radius-2xl);
  overflow: hidden;
  border: 1px solid var(--color-border-soft);
  background: var(--color-surface-4);
}

.blog-cover-image {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  /* contain, not cover: an upload that is not 1200x630 loses a strip of itself
     to a crop, and the strip is usually the part with the wordmark in it. */
  object-fit: contain;
}

.blog-cover--featured {
  /* Same ratio as every other cover; centred beside the copy rather than
     stretched to its height, which is what used to crop it. */
  align-self: center;
}

.blog-cover-glow {
  position: absolute;
  inset: -20%;
  background:
    radial-gradient(circle at 70% 30%, rgba(183, 196, 211, 0.22), transparent 45%),
    radial-gradient(circle at 20% 80%, rgba(203, 180, 138, 0.12), transparent 40%);
  pointer-events: none;
}

.blog-cover[data-tone='violet'] .blog-cover-glow {
  background:
    radial-gradient(circle at 65% 25%, rgba(157, 134, 201, 0.35), transparent 48%),
    radial-gradient(circle at 15% 85%, rgba(183, 196, 211, 0.12), transparent 42%);
}

.blog-cover[data-tone='gold'] .blog-cover-glow {
  background:
    radial-gradient(circle at 70% 20%, rgba(203, 180, 138, 0.4), transparent 46%),
    radial-gradient(circle at 20% 90%, rgba(183, 196, 211, 0.1), transparent 40%);
}

.blog-cover[data-tone='ember'] .blog-cover-glow {
  background:
    radial-gradient(circle at 75% 30%, rgba(201, 139, 139, 0.35), transparent 48%),
    radial-gradient(circle at 10% 80%, rgba(183, 196, 211, 0.1), transparent 40%);
}

.blog-cover[data-tone='mint'] .blog-cover-glow {
  background:
    radial-gradient(circle at 60% 25%, rgba(159, 180, 201, 0.35), transparent 48%),
    radial-gradient(circle at 25% 85%, rgba(203, 180, 138, 0.1), transparent 40%);
}

.blog-cover[data-tone='slate'] .blog-cover-glow {
  background:
    radial-gradient(circle at 50% 40%, rgba(245, 245, 242, 0.1), transparent 50%),
    radial-gradient(circle at 80% 80%, rgba(183, 196, 211, 0.16), transparent 42%);
}

.blog-cover-label {
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: var(--space-6);
  text-align: center;
  font-family: var(--font-display);
  font-weight: 600;
  font-size: clamp(18px, 2vw, 26px);
  line-height: 1.2;
  letter-spacing: -0.02em;
  color: var(--color-text-strong);
  text-shadow: 0 1px 18px rgba(0, 0, 0, 0.55);
}

.blog-cover-meta {
  position: absolute;
  left: 12px;
  right: 12px;
  bottom: 12px;
  z-index: 1;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-3);
  font-family: var(--font-mono);
  font-size: 10px;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--color-text-soft);
}

.blog-cover-tag {
  padding: 4px 8px;
  border-radius: var(--radius-sm);
  background: rgba(0, 0, 0, 0.45);
  border: 1px solid rgba(255, 255, 255, 0.08);
}

.blog-cover-meta time {
  padding: 4px 8px;
  border-radius: var(--radius-sm);
  background: rgba(0, 0, 0, 0.45);
  border: 1px solid rgba(255, 255, 255, 0.08);
}

.blog-empty {
  margin: var(--space-10) 0 0;
  color: var(--color-text-muted);
  font-size: 15px;
}

/* —— Article page —— */

.blog-post {
  padding: 48px var(--section-pad-x) 96px;
  position: relative;
}

.blog-post-sheet {
  max-width: 760px;
  margin: 0 auto;
  color: var(--color-text-soft);
}

.blog-post-crumb {
  margin: 0 0 var(--space-6);
  font-size: 13px;
  line-height: 1.5;
  color: var(--color-text-dim);
}

.blog-post-crumb a {
  color: var(--color-text-muted);
  text-decoration: none;
}

.blog-post-crumb a:hover {
  color: var(--color-text-strong);
}

.blog-post-meta {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--space-3);
  margin-bottom: var(--space-2);
}

.blog-post-tag {
  padding: 4px 10px;
  border: 1px solid var(--color-border-pill);
  border-radius: var(--radius-pill);
  font-family: var(--font-mono);
  font-size: 11px;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--color-text-soft);
}

.blog-post-date {
  font-family: var(--font-mono);
  font-size: 12px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--color-text-dim);
}

.blog-post-title {
  margin: var(--space-3) 0 0;
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 40px;
  line-height: 1.15;
  letter-spacing: -0.025em;
  color: var(--color-text-strong);
}

.blog-post-dek {
  margin: var(--space-5) 0 0;
  font-size: 18px;
  line-height: 1.6;
  color: var(--color-text-muted);
}

.blog-post-cover {
  display: block;
  width: 100%;
  aspect-ratio: var(--blog-cover-ratio);
  object-fit: contain;
  border-radius: var(--radius-2xl);
  border: 1px solid var(--color-border-soft);
  margin: var(--space-8) 0 0;
}

.blog-post-body {
  margin-top: var(--space-10);
  font-size: 16px;
  line-height: 1.75;
}

.blog-post-body h2 {
  margin: 44px 0 14px;
  padding-top: 26px;
  border-top: 1px solid var(--color-border-soft);
  font-family: var(--font-display);
  font-size: 24px;
  font-weight: 600;
  line-height: 1.3;
  letter-spacing: -0.02em;
  color: var(--color-text-strong);
}

.blog-post-body p {
  margin: 0 0 16px;
}

.blog-post-body ul {
  margin: 0 0 16px;
  padding-left: 22px;
}

.blog-post-body li {
  margin-bottom: 8px;
}

.blog-post-body a {
  color: var(--color-accent-soft);
  text-decoration: underline;
  text-underline-offset: 2px;
}

.blog-post-body a:hover {
  color: var(--color-text-strong);
}

.blog-post-footer {
  margin-top: var(--space-12);
  padding-top: var(--space-8);
  border-top: 1px solid var(--color-border-soft);
}

.blog-post-product,
.blog-post-related {
  margin-top: var(--space-10);
  padding-top: var(--space-6);
  border-top: 1px solid var(--color-border-soft);
}

.blog-post-related-heading {
  margin: 0 0 var(--space-3);
  font-family: var(--font-mono);
  font-size: 11px;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--color-text-dim);
}

.blog-post-link-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: var(--space-2);
}

.blog-post-link {
  color: var(--color-accent-soft);
  text-decoration: none;
  font-size: 15px;
  line-height: 1.45;
}

.blog-post-link:hover {
  color: var(--color-text-strong);
}

.blog-post-footer-lead {
  margin: 0 0 var(--space-5);
  font-size: 16px;
  line-height: 1.6;
  color: var(--color-text-muted);
}

.blog-post-ctas {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-3);
}

.blog-cta {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: var(--space-4) var(--space-6);
  border: 1px solid transparent;
  border-radius: var(--radius-md);
  font-size: 16px;
  font-weight: 600;
  text-decoration: none;
  white-space: nowrap;
}

.blog-cta--primary {
  background: var(--color-text);
  color: var(--color-bg);
}

.blog-cta--primary:hover {
  background: var(--color-text-strong);
  color: var(--color-bg);
}

.blog-cta--secondary {
  border-color: var(--color-border-strong);
  background: rgba(255, 255, 255, 0.02);
  color: var(--color-text);
  font-weight: 500;
}

.blog-cta--secondary:hover {
  border-color: var(--color-border-hover-strong);
  background: rgba(255, 255, 255, 0.05);
}

@media (max-width: 1024px) {
  .blog-grid {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }

  .blog-site-footer-grid {
    grid-template-columns: 1fr;
  }

  .blog-site-footer-columns {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }

  /* Not hidden: the blog has its own header with no menu button, so hiding these
     left a reader no way out of an article but the logo. They still fit beside
     the brand and the CTA at this width; the narrow breakpoint gives them a row. */
  .blog-nav {
    flex-wrap: wrap;
  }
}

@media (max-width: 768px) {
  .blog-nav {
    height: auto;
    padding-top: var(--space-3);
    padding-bottom: var(--space-3);
    row-gap: var(--space-3);
  }

  .blog-nav-links {
    order: 3;
    width: 100%;
    gap: var(--space-4);
  }
  .blog-page {
    padding-top: 24px;
  }

  .blog-featured {
    grid-template-columns: 1fr;
    padding: var(--space-5);
    gap: var(--space-5);
  }

  .blog-featured-copy {
    padding: var(--space-2);
    order: 2;
  }

  .blog-cover--featured {
    order: 1;
  }

  .blog-grid {
    grid-template-columns: 1fr;
  }

  .blog-featured-title {
    font-size: 26px;
  }

  .blog-post-title {
    font-size: 30px;
  }

  .blog-post-dek {
    font-size: 16.5px;
  }

  .blog-post-body h2 {
    font-size: 20px;
  }
}
