---
import Icon from './Icon.astro';
import { getChangelog, type ChangelogTag } from '../lib/changelog';

/**
 * ChangelogShowcase - landing-page changelog. Copy and CTA on the left; on
 * the right a plinth artifact holds the release feed as compact cards on a
 * rail, newest emphasized, older entries dissolving off the bottom edge.
 * Content is the same build-time data that powers /changelog/ (real merged
 * pull requests), so the section never drifts from the actual history.
 */

interface Release {
  date: string;
  category: 'New' | 'Improved' | 'Fixed';
  title: string;
  url: string;
  summary: string;
}

const categoryByTag: Record<ChangelogTag, Release['category']> = {
  shipped: 'New',
  changed: 'Improved',
  fixed: 'Fixed',
};

// Five latest entries; the plinth crops the tail so the feed reads as ongoing.
const releases: Release[] = (await getChangelog()).slice(0, 5).map((e) => ({
  date: e.date,
  category: categoryByTag[e.tag],
  title: e.title,
  url: e.url,
  summary: e.bullets.length ? e.bullets[0] : e.body,
}));

const styleFor = (c: Release['category']) =>
  c === 'New' ? { chip: 'bg-sky-50 text-sky-700 ring-sky-200', dot: 'bg-sky-500' }
  : c === 'Improved' ? { chip: 'bg-emerald-50 text-emerald-700 ring-emerald-200', dot: 'bg-emerald-500' }
  : { chip: 'bg-amber-50 text-amber-700 ring-amber-200', dot: 'bg-amber-500' };
---
<section class="clg container-page py-20 md:py-28">
  <div class="grid lg:grid-cols-12 gap-10 lg:gap-14 items-center">
    <!-- ── Copy ──────────────────────────────────────────────────── -->
    <!-- Copy sits right on lg (artifact left), mirroring the open-source
         section below so two artifact-and-copy splits do not stack the
         same way. Mobile keeps copy first. -->
    <div class="lg:col-span-5 lg:order-2">
      <div class="flex items-center gap-2.5 mb-4">
        <span class="text-[11px] uppercase tracking-[0.16em] text-[color:var(--brand)] font-semibold">Changelog</span>
        <span class="w-1 h-1 rounded-full bg-[color:var(--border-strong)]"></span>
        <span class="inline-flex items-center gap-1.5 text-[11px] uppercase tracking-[0.14em] text-muted-foreground font-mono">
          <span class="clg-live w-1.5 h-1.5 rounded-full bg-emerald-500"></span>
          Shipping continuously
        </span>
      </div>
      <h2 class="text-[32px] md:text-[48px] font-semibold tracking-[-0.03em] leading-[1.04] text-heading">
        The latest from Warmbly.
      </h2>
      <p class="mt-4 text-foreground/75 leading-relaxed max-w-xl">
        New features, changes and fixes in the order they reached production. Every entry links to its pull request.
      </p>
      <a
        href="/changelog/"
        class="group mt-7 inline-flex items-center gap-1.5 h-11 px-5 rounded-[10px] text-[14px] font-medium text-heading bg-white ring-1 ring-[color:var(--border)] hover:ring-[color:var(--border-strong)] transition-colors"
      >
        View full changelog
        <Icon name="arrowUpRight" size={13} class="text-muted-foreground group-hover:text-heading transition-colors" />
      </a>
    </div>

    <!-- ── Artifact: the release feed ────────────────────────────── -->
    <div class="lg:col-span-7 lg:order-1">
      <div class="clg-stage relative overflow-hidden h-[420px] rounded-[18px]"
           style="background: linear-gradient(175deg, #fbfcfe 0%, var(--surface-2) 100%); box-shadow: inset 0 0 0 1px var(--border);">
        <span class="clg-texture absolute inset-0 pointer-events-none"></span>
        <!-- rail -->
        <span class="absolute left-[34px] top-8 bottom-0 w-px bg-slate-200"></span>

        <div class="clg-fade absolute left-12 right-6 top-7 bottom-0">
          {releases.map((r, i) => {
            const s = styleFor(r.category);
            return (
              <div class="clg-card relative mb-3" style={`--i:${i}`}>
                <span class="absolute -left-[21px] top-[18px] w-[13px] h-[13px] rounded-full bg-white ring-1 ring-slate-200 grid place-items-center">
                  <span class={`w-1.5 h-1.5 rounded-full ${s.dot}`}></span>
                </span>
                <a
                  href={r.url}
                  target="_blank"
                  rel="noopener noreferrer"
                  class:list={[
                    'block rounded-[11px] bg-white ring-1 ring-slate-200 px-4 py-3 transition-shadow',
                    i === 0
                      ? 'shadow-[0_22px_50px_-18px_rgb(15_23_42_/_0.28)]'
                      : 'shadow-[0_10px_30px_-20px_rgb(15_23_42_/_0.25)]',
                  ]}
                >
                  <div class="flex items-center gap-2.5">
                    <span class={`shrink-0 inline-flex items-center h-5 px-1.5 rounded text-[9.5px] font-semibold uppercase tracking-[0.08em] ring-1 ${s.chip}`}>{r.category}</span>
                    <span class="text-[12.5px] font-semibold text-slate-900 truncate">{r.title}</span>
                    <span class="ml-auto shrink-0 text-[10px] font-mono text-slate-400 tabular-nums">{r.date}</span>
                  </div>
                  {r.summary && (
                    <p class="mt-1.5 text-[11.5px] text-slate-500 leading-snug line-clamp-1">{r.summary}</p>
                  )}
                </a>
              </div>
            );
          })}
        </div>
      </div>
    </div>
  </div>
</section>

<style>
  .clg-texture {
    background-image: radial-gradient(circle, rgb(15 23 42 / 0.07) 1px, transparent 1.2px);
    background-size: 14px 14px;
    -webkit-mask-image: radial-gradient(ellipse at 50% 40%, #000 30%, transparent 78%);
    mask-image: radial-gradient(ellipse at 50% 40%, #000 30%, transparent 78%);
  }
  /* Older entries dissolve off the bottom: the feed continues past the card. */
  .clg-fade {
    -webkit-mask-image: linear-gradient(to bottom, #000 58%, transparent 96%);
    mask-image: linear-gradient(to bottom, #000 58%, transparent 96%);
  }

  /* Motion gated on .is-live so nothing runs off screen. */
  @media (prefers-reduced-motion: no-preference) {
    .clg.js-ready .clg-card { opacity: 0; }
    .clg.is-live .clg-card {
      animation: clg-rise 520ms cubic-bezier(0.22, 1, 0.36, 1) both;
      animation-delay: calc(var(--i) * 110ms);
    }
    .clg.is-live .clg-live { animation: clg-pulse 2.4s ease-in-out infinite; }
  }
  @keyframes clg-rise {
    from { opacity: 0; transform: translateY(12px); }
    to   { opacity: 1; transform: none; }
  }
  @keyframes clg-pulse { 0%, 100% { opacity: 1; } 50% { opacity: 0.35; } }
</style>

<script is:inline>
  // Arm hidden start states only when JS runs, so a script failure leaves
  // the section fully visible.
  document.querySelectorAll('.clg').forEach((el) => el.classList.add('js-ready'));
</script>

<script>
  const clg = document.querySelector('.clg');
  if (clg) {
    new IntersectionObserver(
      (entries) => entries.forEach((e) => clg.classList.toggle('is-live', e.isIntersecting)),
      { threshold: 0.2 },
    ).observe(clg);
  }
</script>
