import React, { useEffect, useRef, useState } from 'react'
import { Link, router, usePage } from '@inertiajs/react'
import SeoHead from '../../components/seo/SeoHead'
import { postAcademyAction, trackAcademyEvent, trackUpgradeClick, useAcademyPageAnalytics } from '../../lib/academyAnalytics'

function academyHref(section, slug) {
  return `/academy/${section}/${encodeURIComponent(slug)}`
}

function AcademyBreadcrumbs({ items = [] }) {
  if (!items.length) return null

  return (
    <nav aria-label="Breadcrumb" className="flex flex-wrap items-center gap-2 text-sm text-slate-400">
      {items.map((item, index) => {
        const isLast = index === items.length - 1

        return (
          <React.Fragment key={`${item.label}-${index}`}>
            {index > 0 ? <span className="text-slate-600">/</span> : null}
            {isLast ? (
              <span className="font-medium text-slate-200">{item.label}</span>
            ) : (
              <Link href={item.href} className="transition hover:text-white">
                {item.label}
              </Link>
            )}
          </React.Fragment>
        )
      })}
    </nav>
  )
}

function slugifyHeading(value, fallback = 'section') {
  const normalized = String(value || '')
    .toLowerCase()
    .trim()
    .replace(/[^a-z0-9\s-]/g, '')
    .replace(/\s+/g, '-')
    .replace(/-+/g, '-')
    .replace(/^-|-$/g, '')

  return normalized || fallback
}

function formatLessonDate(value) {
  if (!value) return 'Recently updated'

  const date = new Date(value)

  if (Number.isNaN(date.getTime())) return 'Recently updated'

  return new Intl.DateTimeFormat('en', { month: 'short', day: 'numeric', year: 'numeric' }).format(date)
}

function formatLessonMinutes(minutes) {
  const value = Number(minutes || 0)

  return value > 0 ? `${value} min read` : 'Quick read'
}

function normalizePromptAccessLevel(accessLevel) {
  const value = String(accessLevel || 'free').trim().toLowerCase()
  return value === 'creator' || value === 'pro' ? value : 'free'
}

function promptRequirementText(accessLevel) {
  const level = normalizePromptAccessLevel(accessLevel)

  if (level === 'pro') return 'Requires Pro access.'
  if (level === 'creator') return 'Requires Creator or Pro access.'

  return null
}

function promptUnlockHeading(accessLevel) {
  const level = normalizePromptAccessLevel(accessLevel)

  if (level === 'pro') return 'Unlock the full Pro prompt.'
  if (level === 'creator') return 'Unlock the full Creator prompt.'

  return 'Unlock the full prompt.'
}

function promptUnlockDescription(accessLevel) {
  const level = normalizePromptAccessLevel(accessLevel)

  if (level === 'pro') {
    return 'Get the complete reusable prompt, negative prompt, workflow notes, model settings, and variation strategy.'
  }

  if (level === 'creator') {
    return 'Get the complete reusable prompt, negative prompt, workflow notes, and creative workflow.'
  }

  return 'Get the complete reusable prompt and workflow notes.'
}

function promptInlineImage(url, thumbUrl) {
  return thumbUrl || url || ''
}

function formatMetaDisplay(value) {
  const normalized = String(value || '').trim()
  if (!normalized) return ''

  return normalized
    .replace(/[_-]+/g, ' ')
    .replace(/\b\w/g, (character) => character.toUpperCase())
}

function StatPill({ label, value, icon, accentClassName = 'border-white/10 bg-white/[0.04] text-slate-300', valueClassName = 'text-white' }) {
  return (
    <div className="rounded-[24px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.04),rgba(15,23,42,0.18))] p-4 shadow-[inset_0_1px_0_rgba(255,255,255,0.03)]">
      <div className="flex items-start gap-3">
        <div className="min-w-0 flex-1">
          <p className="text-[10px] font-semibold uppercase tracking-[0.22em] text-slate-400">{label}</p>
          <p className={`mt-3 text-[clamp(1.35rem,2.2vw,2rem)] font-semibold tracking-[-0.04em] ${valueClassName}`}>{value}</p>
        </div>
        {icon ? (
          <span className={`mt-1 inline-flex h-9 w-9 shrink-0 items-center justify-center rounded-[18px] border ${accentClassName}`} aria-hidden="true">
            <i className={`fa-solid ${icon} text-xs`} />
          </span>
        ) : null}
      </div>
    </div>
  )
}

function PromptHeaderStat({ label, value, icon, accentClassName = 'border-white/10 bg-white/[0.04] text-slate-300', valueClassName = 'text-white' }) {
  return (
    <div className="rounded-[24px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.04),rgba(15,23,42,0.16))] px-4 py-4 shadow-[inset_0_1px_0_rgba(255,255,255,0.03)]">
      <div className="flex items-start justify-between gap-3">
        <div className="min-w-0 flex-1">
          <p className="text-[9px] font-semibold uppercase tracking-[0.2em] text-slate-400">{label}</p>
          <p className={`mt-2 break-words text-[clamp(0.75rem,0.95vw,0.95rem)] font-semibold leading-[1.25] tracking-[-0.03em] ${valueClassName}`}>{value}</p>
        </div>
        {icon ? (
          <span className={`inline-flex h-7 w-7 shrink-0 items-center justify-center rounded-[14px] border ${accentClassName}`} aria-hidden="true">
            <i className={`fa-solid ${icon} text-[10px]`} />
          </span>
        ) : null}
      </div>
    </div>
  )
}

function LessonInfoRow({ label, value }) {
  return (
    <div className="flex items-center justify-between gap-4 rounded-2xl border border-white/10 bg-black/20 px-4 py-3">
      <span className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">{label}</span>
      <span className="text-sm font-semibold text-white">{value}</span>
    </div>
  )
}

function LessonNavCard({ direction, lesson }) {
  if (!lesson) return null

  const eyebrow = direction === 'previous' ? 'Previous lesson' : 'Next lesson'
  const alignClass = direction === 'previous' ? 'items-start text-left' : 'items-end text-right'
  const href = lesson.course_url || `/academy/lessons/${lesson.slug}`

  return (
    <Link
      href={href}
      aria-label={`${eyebrow}: ${lesson.title}`}
      className={`group flex min-h-full flex-col justify-between rounded-[28px] border border-white/10 bg-black/20 p-5 transition hover:border-sky-300/25 hover:bg-white/[0.06] ${alignClass}`}
    >
      <div>
        <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">{eyebrow}</p>
        {lesson.lesson_label ? <p className="mt-3 text-xs font-semibold uppercase tracking-[0.2em] text-amber-100">{lesson.lesson_label}</p> : null}
        <h3 className="mt-3 text-2xl font-semibold tracking-[-0.04em] text-white transition group-hover:text-sky-100">{lesson.title}</h3>
      </div>
      <p className="mt-4 text-sm leading-7 text-slate-300">{lesson.excerpt || lesson.content_preview || 'Open the next step in this Academy sequence.'}</p>
    </Link>
  )
}

function LockedPanel({ pricingUrl, label, accessLevel, onUpgrade }) {
  const isPrompt = label === 'prompt'
  const requirement = promptRequirementText(accessLevel)

  return (
    <div className="rounded-[28px] border border-amber-300/20 bg-amber-300/10 p-6 text-amber-50">
      <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-amber-100/80">Premium content</p>
      <h2 className="mt-3 text-2xl font-semibold tracking-[-0.04em]">{isPrompt ? promptUnlockHeading(accessLevel) : `Unlock the full ${label}.`}</h2>
      <p className="mt-3 text-sm leading-7 text-amber-50/90">{isPrompt ? promptUnlockDescription(accessLevel) : 'This preview is visible, but the full Academy content stays server-side until your account has the required access.'}</p>
      {requirement ? <p className="mt-3 text-xs font-semibold uppercase tracking-[0.18em] text-amber-100">{requirement}</p> : null}
      <Link href={pricingUrl} onClick={onUpgrade} className="mt-5 inline-flex rounded-full border border-amber-200/25 bg-white/10 px-5 py-3 text-sm font-semibold text-white">See Academy plans</Link>
    </div>
  )
}

function copyTextToClipboard(text) {
  const source = String(text || '')
  if (!source) return Promise.reject(new Error('Nothing to copy'))

  if (navigator.clipboard && typeof navigator.clipboard.writeText === 'function') {
    return navigator.clipboard.writeText(source)
  }

  const textarea = document.createElement('textarea')
  textarea.value = source
  textarea.setAttribute('readonly', 'true')
  textarea.style.position = 'fixed'
  textarea.style.top = '-1000px'
  textarea.style.left = '-1000px'
  document.body.appendChild(textarea)
  textarea.select()

  try {
    if (document.execCommand('copy')) {
      return Promise.resolve()
    }
  } finally {
    document.body.removeChild(textarea)
  }

  return Promise.reject(new Error('Clipboard unavailable'))
}

function PromptCopyButton({ prompt, label = 'Copy prompt', analytics = null, contentId = null, eventType = 'academy_prompt_copy', metadata = {} }) {
  const [status, setStatus] = useState('idle')
  const resetTimerRef = useRef(0)

  return (
    <button
      type="button"
      onClick={() => {
        copyTextToClipboard(prompt)
          .then(() => {
            setStatus('copied')
            void trackAcademyEvent(eventType, analytics?.contentType || null, contentId || analytics?.contentId || null, metadata, {
              url: analytics?.eventUrl,
              pageName: analytics?.pageName,
              useBeacon: false,
            })
          })
          .catch(() => setStatus('failed'))
          .finally(() => {
            window.clearTimeout(resetTimerRef.current)
            resetTimerRef.current = window.setTimeout(() => setStatus('idle'), 1800)
          })
      }}
      className="inline-flex items-center gap-2 rounded-full border border-[#ffb9ab]/20 bg-[#ffb9ab]/10 px-4 py-2 text-sm font-semibold text-[#ffe2dc] transition hover:border-[#ffb9ab]/35 hover:bg-[#ffb9ab]/16"
      aria-label="Copy prompt"
    >
      <i className={`fa-solid ${status === 'copied' ? 'fa-check' : status === 'failed' ? 'fa-triangle-exclamation' : 'fa-copy'}`} />
      <span>{status === 'copied' ? 'Copied' : status === 'failed' ? 'Copy failed' : label}</span>
    </button>
  )
}

function ImageLightbox({ gallery, onClose, onNavigate }) {
  useEffect(() => {
    if (!gallery?.images?.length) return undefined

    const handleEscape = (event) => {
      if (event.key === 'Escape') {
        onClose()
        return
      }

      if (event.key === 'ArrowLeft') {
        onNavigate(-1)
        return
      }

      if (event.key === 'ArrowRight') {
        onNavigate(1)
      }
    }

    document.body.style.overflow = 'hidden'
    window.addEventListener('keydown', handleEscape)

    return () => {
      document.body.style.overflow = ''
      window.removeEventListener('keydown', handleEscape)
    }
  }, [gallery, onClose, onNavigate])

  const images = Array.isArray(gallery?.images) ? gallery.images : []
  const currentIndex = Math.max(0, Math.min(images.length - 1, Number(gallery?.index || 0)))
  const currentImage = images[currentIndex]

  if (!currentImage?.src) return null

  return (
    <div className="fixed inset-0 z-[120] flex items-center justify-center bg-[#020611e6] p-4 backdrop-blur-md" onClick={onClose} role="dialog" aria-modal="true" aria-label={currentImage.alt || 'Image preview'}>
      <button type="button" onClick={onClose} className="absolute right-4 top-4 inline-flex h-11 w-11 items-center justify-center rounded-full border border-white/10 bg-black/35 text-white transition hover:border-white/25 hover:bg-white/10" aria-label="Close image preview">
        <i className="fa-solid fa-xmark text-lg" />
      </button>
      {images.length > 1 ? (
        <button type="button" onClick={(event) => { event.stopPropagation(); onNavigate(-1) }} className="absolute left-4 top-1/2 inline-flex h-12 w-12 -translate-y-1/2 items-center justify-center rounded-full border border-white/10 bg-black/35 text-white transition hover:border-white/25 hover:bg-white/10" aria-label="Previous image">
          <i className="fa-solid fa-chevron-left" />
        </button>
      ) : null}
      {images.length > 1 ? (
        <button type="button" onClick={(event) => { event.stopPropagation(); onNavigate(1) }} className="absolute right-4 top-1/2 inline-flex h-12 w-12 -translate-y-1/2 items-center justify-center rounded-full border border-white/10 bg-black/35 text-white transition hover:border-white/25 hover:bg-white/10" aria-label="Next image">
          <i className="fa-solid fa-chevron-right" />
        </button>
      ) : null}
      <div className="max-h-[92vh] max-w-[min(1400px,96vw)] overflow-hidden rounded-[30px] border border-white/10 bg-black/30 shadow-[0_30px_120px_rgba(0,0,0,0.5)]" onClick={(event) => event.stopPropagation()}>
        <img src={currentImage.src} alt={currentImage.alt || ''} className="max-h-[92vh] w-full object-contain" />
        {images.length > 1 ? (
          <div className="flex items-center justify-between gap-4 border-t border-white/10 bg-black/35 px-5 py-3 text-sm text-slate-200">
            <div>
              <p className="font-semibold text-white">{currentImage.alt || `Image ${currentIndex + 1}`}</p>
              <p className="text-xs uppercase tracking-[0.18em] text-slate-400">{`Image ${currentIndex + 1} of ${images.length}`}</p>
            </div>
            <div className="flex gap-2">
              {images.map((image, index) => (
                <button
                  key={`${image.src}-${index}`}
                  type="button"
                  onClick={() => onNavigate(index - currentIndex)}
                  className={`h-2.5 w-2.5 rounded-full transition ${index === currentIndex ? 'bg-white' : 'bg-white/25 hover:bg-white/45'}`}
                  aria-label={`Go to image ${index + 1}`}
                />
              ))}
            </div>
          </div>
        ) : null}
      </div>
    </div>
  )
}

function PromptToolNoteCard({ note, index, galleryIndex, onOpenImage }) {
  if (!note || typeof note !== 'object') return null

  const displayType = String(note.display_type || '').trim()
  const eyebrowLabel = displayType || 'AI comparison'
  const title = note.model_name || note.provider || `${displayType || 'Comparison'} ${String(index + 1).padStart(2, '0')}`
  const subtitle = [note.provider, note.model_name].filter(Boolean).join(' · ')
  const previewUrl = promptInlineImage(note.image_url, note.thumb_url)
  const hasContent = Boolean(displayType || note.notes || note.strengths || note.weaknesses || note.best_for || note.settings || previewUrl || note.score || subtitle)

  if (!hasContent) return null

  return (
    <article className="rounded-[28px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.05),rgba(15,23,42,0.22))] p-5 shadow-[0_16px_40px_rgba(2,6,23,0.16)]">
      {previewUrl ? (
        <button
          type="button"
          onClick={() => onOpenImage?.(galleryIndex)}
          className="group mb-5 block w-full overflow-hidden rounded-[24px] border border-white/10 bg-slate-950 text-left transition hover:border-sky-300/25 focus:outline-none focus:ring-2 focus:ring-sky-300/35"
          aria-label={`Open comparison image for ${title}`}
        >
          <div className="relative">
            <img src={previewUrl} srcSet={note.image_srcset || undefined} sizes="(max-width: 767px) calc(100vw - 4rem), (max-width: 1535px) calc(50vw - 3rem), 560px" alt={title} loading="lazy" className="aspect-[4/3] w-full object-cover transition duration-500 group-hover:scale-[1.03]" />
            <div className="absolute inset-x-0 bottom-0 flex items-center justify-between gap-3 bg-[linear-gradient(180deg,transparent,rgba(2,6,23,0.72))] px-4 py-3">
              <span className="text-[10px] font-semibold uppercase tracking-[0.2em] text-slate-100/90">Click to zoom</span>
              <span className="inline-flex h-9 w-9 items-center justify-center rounded-full border border-white/10 bg-black/25 text-white">
                <i className="fa-solid fa-expand" />
              </span>
            </div>
          </div>
        </button>
      ) : null}

      <div className="flex items-start justify-between gap-4">
        <div>
          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-[#ffcfbf]">{eyebrowLabel}</p>
          <h3 className="mt-2 text-xl font-semibold tracking-[-0.03em] text-white">{title}</h3>
          {subtitle ? <p className="mt-1 text-sm text-slate-400">{subtitle}</p> : null}
        </div>
        <div className="flex flex-col items-end gap-2">
          <span className="rounded-full border border-white/10 bg-white/[0.04] px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-300">{String(index + 1).padStart(2, '0')}</span>
          {note.score ? <span className="rounded-full border border-[#ffcfbf]/20 bg-[#ffcfbf]/10 px-3 py-1 text-xs font-semibold text-[#fff0ea]">{`Score ${note.score}/10`}</span> : null}
        </div>
      </div>

      <div className="mt-5 space-y-4">
        {note.settings ? (
          <div className="rounded-[22px] border border-white/10 bg-black/25 p-4">
            <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-slate-400">Generated in</p>
            <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-200">{note.settings}</p>
          </div>
        ) : null}

        {note.notes ? (
          <div>
            <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-slate-400">Overall notes</p>
            <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-200">{note.notes}</p>
          </div>
        ) : null}

        {note.best_for ? (
          <div className="rounded-[22px] border border-sky-300/15 bg-sky-300/10 p-4">
            <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-sky-100">Best for</p>
            <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-100">{note.best_for}</p>
          </div>
        ) : null}

        <div className="grid gap-4 md:grid-cols-2">
          {note.strengths ? (
            <div className="rounded-[22px] border border-emerald-300/15 bg-emerald-300/10 p-4">
              <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-emerald-100">Strengths</p>
              <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-100">{note.strengths}</p>
            </div>
          ) : null}

          {note.weaknesses ? (
            <div className="rounded-[22px] border border-amber-300/15 bg-amber-300/10 p-4">
              <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-amber-100">Weaknesses</p>
              <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-100">{note.weaknesses}</p>
            </div>
          ) : null}
        </div>
      </div>
    </article>
  )
}

function normalizePromptDocumentation(documentation) {
  const source = documentation && typeof documentation === 'object' && !Array.isArray(documentation) ? documentation : {}
  const list = (key) => (Array.isArray(source[key]) ? source[key] : [])
    .map((item) => String(item || '').trim())
    .filter(Boolean)

  return {
    summary: String(source.summary || '').trim(),
    best_for: list('best_for'),
    how_to_use: list('how_to_use'),
    required_inputs: list('required_inputs'),
    workflow: list('workflow'),
    tips: list('tips'),
    common_mistakes: list('common_mistakes'),
    data_accuracy_notes: list('data_accuracy_notes'),
    display_notes: String(source.display_notes || '').trim(),
  }
}

function PromptDocumentationPanel({ documentation }) {
  const hasContent = Boolean(
    documentation.summary
    || documentation.display_notes
    || documentation.best_for.length
    || documentation.how_to_use.length
    || documentation.required_inputs.length
    || documentation.workflow.length
    || documentation.tips.length
    || documentation.common_mistakes.length
    || documentation.data_accuracy_notes.length,
  )

  if (!hasContent) return null

  return (
    <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)] md:p-8">
      <div className="max-w-3xl">
        <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">How to use</p>
        <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Prompt documentation</h2>
        {documentation.summary ? <p className="mt-3 text-sm leading-7 text-slate-300 md:text-base">{documentation.summary}</p> : null}
      </div>

      {documentation.best_for.length ? (
        <div className="mt-6">
          <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Best for</p>
          <div className="mt-3 flex flex-wrap gap-2">
            {documentation.best_for.map((item) => (
              <span key={item} className="rounded-full border border-sky-300/20 bg-sky-300/10 px-3 py-1.5 text-xs font-semibold uppercase tracking-[0.18em] text-sky-100">{item}</span>
            ))}
          </div>
        </div>
      ) : null}

      <div className="mt-6 grid gap-5 xl:grid-cols-2">
        {documentation.how_to_use.length ? (
          <div className="rounded-[26px] border border-white/10 bg-black/20 p-5">
            <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-[#ffd8cd]">How to use</p>
            <ol className="mt-3 space-y-3 text-sm leading-7 text-slate-200">
              {documentation.how_to_use.map((step, index) => (
                <li key={`${step}-${index}`} className="flex gap-3">
                  <span className="mt-0.5 inline-flex h-6 w-6 shrink-0 items-center justify-center rounded-full border border-white/10 bg-white/[0.04] text-[11px] font-semibold text-white">{index + 1}</span>
                  <span>{step}</span>
                </li>
              ))}
            </ol>
          </div>
        ) : null}

        {documentation.workflow.length ? (
          <div className="rounded-[26px] border border-white/10 bg-black/20 p-5">
            <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-emerald-200/75">Workflow</p>
            <ol className="mt-3 space-y-3 text-sm leading-7 text-slate-200">
              {documentation.workflow.map((step, index) => (
                <li key={`${step}-${index}`} className="flex gap-3">
                  <span className="mt-0.5 inline-flex h-6 w-6 shrink-0 items-center justify-center rounded-full border border-emerald-300/15 bg-emerald-300/10 text-[11px] font-semibold text-emerald-100">{index + 1}</span>
                  <span>{step}</span>
                </li>
              ))}
            </ol>
          </div>
        ) : null}
      </div>

      <div className="mt-5 grid gap-5 xl:grid-cols-3">
        {documentation.required_inputs.length ? (
          <div className="rounded-[26px] border border-white/10 bg-black/20 p-5">
            <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-slate-400">Required inputs</p>
            <ul className="mt-3 space-y-2 text-sm leading-7 text-slate-200">
              {documentation.required_inputs.map((item) => <li key={item}>{item}</li>)}
            </ul>
          </div>
        ) : null}

        {documentation.tips.length ? (
          <div className="rounded-[26px] border border-emerald-300/15 bg-emerald-300/10 p-5">
            <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-emerald-100">Tips</p>
            <ul className="mt-3 space-y-2 text-sm leading-7 text-slate-100">
              {documentation.tips.map((item) => <li key={item}>{item}</li>)}
            </ul>
          </div>
        ) : null}

        {documentation.common_mistakes.length ? (
          <div className="rounded-[26px] border border-amber-300/15 bg-amber-300/10 p-5">
            <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-amber-100">Common mistakes</p>
            <ul className="mt-3 space-y-2 text-sm leading-7 text-slate-100">
              {documentation.common_mistakes.map((item) => <li key={item}>{item}</li>)}
            </ul>
          </div>
        ) : null}
      </div>

      {documentation.data_accuracy_notes.length ? (
        <div className="mt-5 rounded-[26px] border border-sky-300/15 bg-sky-300/10 p-5">
          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-sky-100">Data accuracy notes</p>
          <ul className="mt-3 space-y-2 text-sm leading-7 text-slate-100">
            {documentation.data_accuracy_notes.map((item) => <li key={item}>{item}</li>)}
          </ul>
        </div>
      ) : null}

      {documentation.display_notes ? (
        <div className="mt-5 rounded-[26px] border border-[#ffcfbf]/18 bg-[#ffcfbf]/10 p-5">
          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-[#fff0ea]">Display note</p>
          <p className="mt-3 text-sm leading-7 text-slate-100">{documentation.display_notes}</p>
        </div>
      ) : null}
    </section>
  )
}

function PromptPlaceholderCard({ placeholder }) {
  if (!placeholder || typeof placeholder !== 'object') return null

  const example = placeholder.example
  const defaultValue = placeholder.default
  const renderValue = (value) => {
    if (value == null || value === '') return null

    if (typeof value === 'object') {
      return <pre className="mt-2 overflow-x-auto rounded-[20px] border border-white/10 bg-slate-950/70 p-3 text-xs leading-6 text-slate-200">{JSON.stringify(value, null, 2)}</pre>
    }

    return <p className="mt-2 text-sm leading-6 text-slate-200">{String(value)}</p>
  }

  return (
    <article className="rounded-[28px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.04),rgba(15,23,42,0.2))] p-5 shadow-[0_16px_40px_rgba(2,6,23,0.16)]">
      <div className="flex flex-wrap items-start justify-between gap-3">
        <div>
          <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Placeholder</p>
          <code className="mt-3 inline-flex rounded-full border border-white/10 bg-black/25 px-3 py-1.5 font-mono text-sm text-white">[{placeholder.key || 'VALUE'}]</code>
          {placeholder.label ? <p className="mt-3 text-lg font-semibold tracking-[-0.03em] text-white">{placeholder.label}</p> : null}
        </div>
        <div className="flex flex-wrap gap-2">
          {placeholder.type ? <span className="rounded-full border border-white/10 bg-white/[0.04] px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-300">{placeholder.type}</span> : null}
          {placeholder.required ? <span className="rounded-full border border-amber-300/20 bg-amber-300/10 px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-amber-100">Required</span> : null}
        </div>
      </div>

      {placeholder.description ? <p className="mt-4 text-sm leading-7 text-slate-300">{placeholder.description}</p> : null}

      {example != null && example !== '' ? (
        <div className="mt-4 rounded-[22px] border border-white/10 bg-black/20 p-4">
          <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-slate-400">Example</p>
          {renderValue(example)}
        </div>
      ) : null}

      {defaultValue != null && defaultValue !== '' ? (
        <div className="mt-4 rounded-[22px] border border-white/10 bg-black/20 p-4">
          <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-slate-400">Default</p>
          {renderValue(defaultValue)}
        </div>
      ) : null}
    </article>
  )
}

function PromptHelperPromptCard({ helperPrompt, analytics, contentId }) {
  if (!helperPrompt || typeof helperPrompt !== 'object') return null

  return (
    <details className="group rounded-[28px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.04),rgba(15,23,42,0.2))] p-5 shadow-[0_16px_40px_rgba(2,6,23,0.16)]">
      <summary className="flex cursor-pointer list-none flex-wrap items-start justify-between gap-4">
        <div>
          <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-[#ffd8cd]">Helper prompt</p>
          <h3 className="mt-2 text-xl font-semibold tracking-[-0.03em] text-white">{helperPrompt.title || 'Helper prompt'}</h3>
          {helperPrompt.description ? <p className="mt-2 max-w-2xl text-sm leading-7 text-slate-300">{helperPrompt.description}</p> : null}
        </div>
        <div className="flex flex-wrap gap-2">
          {helperPrompt.type ? <span className="rounded-full border border-white/10 bg-white/[0.04] px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-300">{formatMetaDisplay(helperPrompt.type)}</span> : null}
          {helperPrompt.expected_output ? <span className="rounded-full border border-sky-300/18 bg-sky-300/10 px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-sky-100">{helperPrompt.expected_output}</span> : null}
        </div>
      </summary>

      <div className="mt-5 rounded-[24px] border border-white/10 bg-black/25 p-4 md:p-5">
        <div className="flex flex-wrap items-center justify-between gap-3">
          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-slate-400">Prompt text</p>
          <PromptCopyButton prompt={helperPrompt.prompt} label="Copy helper prompt" analytics={analytics} contentId={contentId} eventType="academy_prompt_helper_copy" metadata={{ copy_type: 'helper_prompt', helper_prompt_title: helperPrompt.title || '', source: 'prompt_helper' }} />
        </div>
        <pre className="mt-4 whitespace-pre-wrap rounded-[22px] border border-white/10 bg-slate-950/70 p-4 text-sm leading-7 text-slate-100">{helperPrompt.prompt}</pre>
      </div>
    </details>
  )
}

function PromptVariantCard({ variant, analytics, contentId }) {
  if (!variant || typeof variant !== 'object') return null

  return (
    <article className={`rounded-[28px] border p-5 shadow-[0_16px_40px_rgba(2,6,23,0.16)] ${variant.recommended ? 'border-[#ffcfbf]/22 bg-[linear-gradient(180deg,rgba(255,207,191,0.08),rgba(15,23,42,0.24))]' : 'border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.04),rgba(15,23,42,0.2))]'}`}>
      <div className="flex flex-wrap items-start justify-between gap-4">
        <div>
          <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Prompt variant</p>
          <h3 className="mt-2 text-xl font-semibold tracking-[-0.03em] text-white">{variant.title || 'Variant'}</h3>
          {variant.description ? <p className="mt-2 max-w-2xl text-sm leading-7 text-slate-300">{variant.description}</p> : null}
        </div>
        <div className="flex flex-wrap gap-2">
          {variant.recommended ? <span className="rounded-full border border-[#ffcfbf]/22 bg-[#ffcfbf]/12 px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-[#fff0ea]">Recommended</span> : null}
          {variant.slug ? <span className="rounded-full border border-white/10 bg-white/[0.04] px-3 py-1 font-mono text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-300">{variant.slug}</span> : null}
        </div>
      </div>

      {variant.recommended_for?.length ? (
        <div className="mt-4 flex flex-wrap gap-2">
          {variant.recommended_for.map((item) => (
            <span key={item} className="rounded-full border border-sky-300/20 bg-sky-300/10 px-3 py-1.5 text-xs font-semibold uppercase tracking-[0.18em] text-sky-100">{item}</span>
          ))}
        </div>
      ) : null}

      <div className="mt-5 rounded-[24px] border border-white/10 bg-black/25 p-4 md:p-5">
        <div className="flex flex-wrap items-center justify-between gap-3">
          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-slate-400">Variant prompt</p>
          <PromptCopyButton prompt={variant.prompt} label="Copy variant" analytics={analytics} contentId={contentId} eventType="academy_prompt_variant_copy" metadata={{ copy_type: 'prompt_variant', variant_title: variant.title || '', source: 'prompt_variant' }} />
        </div>
        <pre className="mt-4 whitespace-pre-wrap rounded-[22px] border border-white/10 bg-slate-950/70 p-4 text-sm leading-7 text-slate-100">{variant.prompt}</pre>
      </div>

      {variant.negative_prompt ? (
        <div className="mt-4 rounded-[24px] border border-white/10 bg-black/20 p-4 md:p-5">
          <div className="flex flex-wrap items-center justify-between gap-3">
            <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-slate-400">Negative prompt</p>
            <PromptCopyButton prompt={variant.negative_prompt} label="Copy negative" analytics={analytics} contentId={contentId} eventType="academy_prompt_variant_negative_copy" metadata={{ copy_type: 'prompt_variant_negative', variant_title: variant.title || '', source: 'prompt_variant' }} />
          </div>
          <pre className="mt-4 whitespace-pre-wrap rounded-[22px] border border-white/10 bg-slate-950/70 p-4 text-sm leading-7 text-slate-200">{variant.negative_prompt}</pre>
        </div>
      ) : null}

      {variant.risk_notes?.length ? (
        <div className="mt-4 rounded-[22px] border border-amber-300/15 bg-amber-300/10 p-4">
          <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-amber-100">Risk notes</p>
          <ul className="mt-3 space-y-2 text-sm leading-7 text-slate-100">
            {variant.risk_notes.map((item) => <li key={item}>{item}</li>)}
          </ul>
        </div>
      ) : null}
    </article>
  )
}

function PromptVariantsSection({ variants, analytics, contentId }) {
  const visibleVariants = Array.isArray(variants) ? variants.filter((variant) => variant && typeof variant === 'object') : []
  const [activeVariantKey, setActiveVariantKey] = useState('')

  useEffect(() => {
    if (!visibleVariants.length) {
      setActiveVariantKey('')
      return
    }

    const recommendedVariant = visibleVariants.find((variant) => variant?.recommended)
    const nextDefaultKey = String(recommendedVariant?.slug || recommendedVariant?.title || visibleVariants[0]?.slug || visibleVariants[0]?.title || 'variant-0')

    setActiveVariantKey((current) => {
      if (visibleVariants.some((variant, index) => String(variant?.slug || variant?.title || `variant-${index}`) === current)) {
        return current
      }

      return nextDefaultKey
    })
  }, [visibleVariants])

  if (!visibleVariants.length) return null

  const activeVariant = visibleVariants.find((variant, index) => String(variant?.slug || variant?.title || `variant-${index}`) === activeVariantKey) || visibleVariants[0]

  return (
    <section className="academy-paywalled-content rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.045),rgba(148,163,184,0.03))] p-6 text-slate-200 shadow-[0_24px_70px_rgba(2,6,23,0.2)] md:p-8">
      <div className="max-w-3xl">
        <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Variants</p>
        <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Alternative prompt versions</h2>
        <p className="mt-3 text-sm leading-7 text-slate-300">Switch between safer, shorter, or more specialized prompt variants without losing the core creative direction.</p>
      </div>

      <div className="mt-6 overflow-x-auto pb-2">
        <div className="inline-flex min-w-full gap-3" role="tablist" aria-label="Prompt variants">
          {visibleVariants.map((variant, index) => {
            const variantKey = String(variant?.slug || variant?.title || `variant-${index}`)
            const isActive = activeVariant === variant

            return (
              <button
                key={variantKey}
                type="button"
                role="tab"
                aria-selected={isActive}
                onClick={() => setActiveVariantKey(variantKey)}
                className={[
                  'min-w-[220px] rounded-[24px] border px-4 py-3 text-left transition',
                  isActive
                    ? 'border-sky-300/30 bg-sky-300/12 shadow-[0_16px_40px_rgba(2,6,23,0.18)]'
                    : 'border-white/10 bg-black/20 hover:border-white/20 hover:bg-white/[0.05]',
                ].join(' ')}
              >
                <div className="flex items-start justify-between gap-3">
                  <div className="min-w-0">
                    <p className="truncate text-sm font-semibold text-white">{variant.title || `Variant ${index + 1}`}</p>
                    {variant.description ? <p className="mt-1 line-clamp-2 text-xs leading-5 text-slate-300">{variant.description}</p> : null}
                  </div>
                  {variant.recommended ? <span className="shrink-0 rounded-full border border-[#ffcfbf]/22 bg-[#ffcfbf]/12 px-2.5 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-[#fff0ea]">Top pick</span> : null}
                </div>
                <div className="mt-3 flex flex-wrap gap-2">
                  {variant.slug ? <span className="rounded-full border border-white/10 bg-white/[0.04] px-2.5 py-1 font-mono text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-300">{variant.slug}</span> : null}
                  {variant.recommended_for?.length ? <span className="rounded-full border border-white/10 bg-white/[0.04] px-2.5 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-300">{variant.recommended_for.length} use case{variant.recommended_for.length === 1 ? '' : 's'}</span> : null}
                </div>
              </button>
            )
          })}
        </div>
      </div>

      <div className="mt-6">
        <PromptVariantCard variant={activeVariant} analytics={analytics} contentId={contentId} />
      </div>
    </section>
  )
}

function PromptPublicExampleCard({ example, index, galleryIndex, onOpenImage, className = '', frameClassName }) {
  if (!example || typeof example !== 'object') return null

  const previewUrl = promptInlineImage(example.image_url, example.thumb_url)
  if (!previewUrl) return null

  const title = example.title || `Prompt Example ${index + 1}`
  const subtitle = [example.provider, example.model_name].filter(Boolean).join(' · ')
  const resolvedFrameClassName = frameClassName || (index === 0 ? 'aspect-[6/5]' : 'aspect-[4/5]')

  return (
    <article className={`group overflow-hidden rounded-[24px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.04),rgba(15,23,42,0.3))] shadow-[0_16px_40px_rgba(2,6,23,0.18)] transition hover:-translate-y-0.5 hover:border-sky-300/20 hover:shadow-[0_22px_50px_rgba(2,6,23,0.28)] ${className}`}>
      <button
        type="button"
        onClick={() => onOpenImage?.(galleryIndex)}
        className="group block w-full text-left"
        aria-label={`Open example image for ${title}`}
      >
        <div className={`relative ${resolvedFrameClassName} overflow-hidden bg-slate-950/80`}>
          <img src={previewUrl} srcSet={example.image_srcset || undefined} sizes="(max-width: 767px) calc(100vw - 4rem), (max-width: 1279px) calc(50vw - 2rem), 420px" alt={example.alt || title} loading="lazy" className="h-full w-full object-cover transition duration-500 group-hover:scale-[1.04]" />
          <div className="absolute inset-0 bg-[linear-gradient(180deg,rgba(2,6,23,0.02),rgba(2,6,23,0.14)_52%,rgba(2,6,23,0.9))] opacity-0 transition duration-300 group-hover:opacity-100" />
          <div className="absolute inset-x-0 top-0 flex items-start justify-between gap-3 p-3 opacity-0 transition duration-300 group-hover:opacity-100">
            <span className="rounded-full border border-white/10 bg-black/35 px-2.5 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-100 backdrop-blur-sm">{example.type_label || 'Variation'}</span>
            {example.score ? <span className="rounded-full border border-[#ffcfbf]/20 bg-[#ffcfbf]/15 px-2.5 py-1 text-[10px] font-semibold text-[#fff0ea] backdrop-blur-sm">{`${example.score}/10`}</span> : null}
          </div>
          <div className="absolute inset-x-0 bottom-0 translate-y-2 px-3 py-3 opacity-0 transition duration-300 group-hover:translate-y-0 group-hover:opacity-100">
            <p className="text-sm font-semibold text-white">{title}</p>
            {subtitle ? <p className="mt-1 text-xs text-slate-300">{subtitle}</p> : null}
            {example.caption ? <p className="mt-2 line-clamp-2 text-xs leading-5 text-slate-300/95">{example.caption}</p> : null}
          </div>
        </div>
      </button>
    </article>
  )
}

function AiComparisonSection({ block }) {
  const payload = block?.payload || {}
  const criteria = Array.isArray(payload.criteria) ? payload.criteria.filter(Boolean) : []
  const results = Array.isArray(block?.comparison_results) ? block.comparison_results.filter((result) => result?.active !== false) : []
  const hasPrompt = Boolean(payload.prompt)
  const hasNegativePrompt = Boolean(payload.negative_prompt)
  const hasUsefulData = Boolean(block?.title || payload.title || payload.intro || hasPrompt || hasNegativePrompt || payload.aspect_ratio || criteria.length || results.length)

  if (!hasUsefulData) return null

  return (
    <section className="rounded-[32px] border border-white/10 bg-[radial-gradient(circle_at_top_left,rgba(255,151,132,0.14),transparent_30%),linear-gradient(180deg,rgba(15,23,42,0.96),rgba(2,6,23,0.92))] p-6 shadow-[0_24px_80px_rgba(2,6,23,0.28)] md:p-7">
      <div className="flex flex-wrap items-start justify-between gap-4">
        <div className="max-w-3xl">
          <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffb8aa]">AI Model Comparison</p>
          <h2 className="mt-3 text-2xl font-semibold tracking-[-0.04em] text-white md:text-3xl">{payload.title || block.title || 'Same Prompt, Different AI Models'}</h2>
          {payload.intro ? <p className="mt-3 text-sm leading-7 text-slate-300 md:text-base">{payload.intro}</p> : null}
        </div>
        {payload.aspect_ratio ? <div className="rounded-full border border-white/10 bg-white/[0.04] px-4 py-2 text-xs font-semibold uppercase tracking-[0.18em] text-slate-200">Aspect ratio {payload.aspect_ratio}</div> : null}
      </div>

      {hasPrompt ? (
        <div className="mt-6 rounded-[26px] border border-[#ffb8aa]/15 bg-black/25 p-4 md:p-5">
          <div className="flex flex-wrap items-center justify-between gap-3">
            <div>
              <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-[#ffd0c6]">Prompt used</p>
              <p className="mt-2 text-xs uppercase tracking-[0.16em] text-slate-500">Shared source prompt across all compared models</p>
            </div>
            <PromptCopyButton prompt={payload.prompt} />
          </div>
          <pre className="mt-4 whitespace-pre-wrap rounded-[22px] border border-white/10 bg-slate-950/70 p-4 text-sm leading-7 text-slate-100">{payload.prompt}</pre>
          {hasNegativePrompt ? (
            <div className="mt-4 rounded-[22px] border border-white/10 bg-white/[0.03] p-4">
              <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-slate-400">Negative prompt</p>
              <pre className="mt-3 whitespace-pre-wrap text-sm leading-7 text-slate-300">{payload.negative_prompt}</pre>
            </div>
          ) : null}
        </div>
      ) : null}

      {criteria.length ? (
        <div className="mt-6">
          <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">What we compare</p>
          <div className="mt-3 flex flex-wrap gap-2">
            {criteria.map((criterion) => (
              <span key={criterion} className="rounded-full border border-white/10 bg-white/[0.04] px-3 py-2 text-sm font-medium text-slate-100">{criterion}</span>
            ))}
          </div>
        </div>
      ) : null}

      {results.length ? (
        <div className="mt-6 grid gap-5 md:grid-cols-2 2xl:grid-cols-4">
          {results.map((result) => {
            const imageUrl = result.thumb_url || result.image_url || result.thumb_path || result.image_path || ''
            const score = Number(result.score || 0)
            const hasScore = Number.isFinite(score) && score > 0
            const altText = `${result.model_name || 'AI model'} by ${result.provider || 'unknown provider'} result for ${payload.prompt || 'comparison prompt'}`

            return (
              <article key={result.id || `${result.provider}-${result.model_name}-${result.sort_order || 0}`} className="overflow-hidden rounded-[28px] border border-white/10 bg-white/[0.04] shadow-[0_16px_40px_rgba(2,6,23,0.18)]">
                <div className="aspect-video overflow-hidden bg-slate-950/80">
                  {imageUrl ? (
                    <img src={imageUrl} alt={altText} loading="lazy" className="h-full w-full object-cover" />
                  ) : (
                    <div className="flex h-full items-center justify-center px-6 text-center text-sm text-slate-500">No comparison image provided.</div>
                  )}
                </div>

                <div className="space-y-4 p-5">
                  <div className="flex flex-wrap items-start justify-between gap-3">
                    <div>
                      <h3 className="text-xl font-semibold tracking-[-0.03em] text-white">{result.model_name || result.provider || 'AI model'}</h3>
                      {result.provider ? <p className="mt-1 text-sm text-slate-400">{result.provider}</p> : null}
                    </div>
                    {hasScore ? <div className="rounded-full border border-[#ffb8aa]/20 bg-[#ffb8aa]/10 px-3 py-1 text-sm font-semibold text-[#ffe3dd]">{`Skinbase score ${score}/10`}</div> : null}
                  </div>

                  {result.settings ? (
                    <div className="rounded-[20px] border border-white/10 bg-black/20 p-4">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-slate-500">Settings</p>
                      <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-300">{result.settings}</p>
                    </div>
                  ) : null}

                  {result.strengths ? (
                    <div>
                      <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-emerald-200/75">Strengths</p>
                      <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-200">{result.strengths}</p>
                    </div>
                  ) : null}

                  {result.weaknesses ? (
                    <div>
                      <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-amber-200/75">Weaknesses</p>
                      <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-300">{result.weaknesses}</p>
                    </div>
                  ) : null}

                  {result.best_for ? (
                    <div>
                      <p className="text-[11px] font-semibold uppercase tracking-[0.18em] text-sky-200/75">Best for</p>
                      <p className="mt-2 whitespace-pre-wrap text-sm leading-7 text-slate-200">{result.best_for}</p>
                    </div>
                  ) : null}
                </div>
              </article>
            )
          })}
        </div>
      ) : null}
    </section>
  )
}

export default function AcademyShow({ pageType, item, relatedLessons = [], relatedCourses = [], previousLesson = null, nextLesson = null, seo, pricingUrl, completeUrl, completed: initialCompleted, saveUrl, unsaveUrl, saved: initialSaved, submitUrl, courseContext = null, interaction = null, interactionRoutes = null, loginUrl = null, analytics = null, progressRoutes = null }) {
  const flash = usePage().props.flash || {}
  useAcademyPageAnalytics(analytics)
  const [completed, setCompleted] = useState(Boolean(initialCompleted))
  const [saved, setSaved] = useState(Boolean(initialSaved))
  const [liked, setLiked] = useState(Boolean(interaction?.liked))
  const [likesCount, setLikesCount] = useState(Number(interaction?.likes_count || 0))
  const [savesCount, setSavesCount] = useState(Number(interaction?.saves_count || 0))
  const [tableOfContents, setTableOfContents] = useState([])
  const [activeHeadingId, setActiveHeadingId] = useState('')
  const [lightboxGallery, setLightboxGallery] = useState(null)
  const articleContentRef = useRef(null)
  const handledInitialHashRef = useRef(false)
  const lessonCover = item?.cover_image_url || item?.cover_image || ''
  const articleCover = item?.article_cover_image_url || item?.article_cover_image || ''
  const lessonCategory = item?.category?.name || 'Academy'
  const lessonSeries = String(item?.series_name || '').trim() || lessonCategory
  const lessonDifficulty = item?.difficulty || 'Intermediate'
  const lessonMinutes = formatLessonMinutes(item?.reading_minutes)
  const lessonUpdated = formatLessonDate(item?.published_at)
  const lessonBlocks = Array.isArray(item?.blocks) ? item.blocks : []
  const relatedLessonList = Array.isArray(relatedLessons) ? relatedLessons : []
  const relatedCourseList = Array.isArray(relatedCourses) ? relatedCourses : []
  const courseOutline = Array.isArray(courseContext?.outline) ? courseContext.outline : []
  const lessonSummary = item.excerpt || item.description || item.prompt_preview || item.content_preview || 'A focused Academy lesson with practical guidance and examples.'
  const lessonTags = Array.isArray(item?.tags) ? item.tags.filter(Boolean) : []
  const promptPreviewImage = item?.preview_image || ''
  const promptPreviewThumbImage = item?.preview_image_thumb || promptPreviewImage
  const promptPreviewSrcSet = item?.preview_image_srcset || ''
  const promptBody = item?.prompt || item?.prompt_preview || ''
  const promptDocumentation = normalizePromptDocumentation(item?.documentation)
  const promptPlaceholders = Array.isArray(item?.placeholders)
    ? item.placeholders.filter((placeholder) => placeholder && typeof placeholder === 'object' && [
      placeholder.key,
      placeholder.label,
      placeholder.description,
      placeholder.example,
      placeholder.default,
      placeholder.type,
    ].some((value) => value != null && value !== '' && value !== false))
    : []
  const promptHelperPrompts = Array.isArray(item?.helper_prompts)
    ? item.helper_prompts.filter((helperPrompt) => helperPrompt && typeof helperPrompt === 'object' && [
      helperPrompt.title,
      helperPrompt.description,
      helperPrompt.prompt,
      helperPrompt.expected_output,
      helperPrompt.type,
    ].some(Boolean))
    : []
  const promptVariants = Array.isArray(item?.prompt_variants)
    ? item.prompt_variants.filter((variant) => variant && typeof variant === 'object' && [
      variant.title,
      variant.description,
      variant.prompt,
      variant.negative_prompt,
      variant.slug,
      variant.recommended,
      ...(Array.isArray(variant.recommended_for) ? variant.recommended_for : []),
      ...(Array.isArray(variant.risk_notes) ? variant.risk_notes : []),
    ].some((value) => value != null && value !== '' && value !== false))
    : []
  const promptPublicExamples = Array.isArray(item?.public_examples)
    ? item.public_examples.filter((example) => example && typeof example === 'object' && [
      example.title,
      example.caption,
      example.image_path,
      example.image_url,
      example.thumb_path,
      example.thumb_url,
      example.provider,
      example.model_name,
      example.score,
    ].some(Boolean))
    : []
  const promptComparisons = Array.isArray(item?.tool_notes)
    ? item.tool_notes.filter((note) => note && typeof note === 'object' && note.active !== false && [
      note.display_type,
      note.provider,
      note.model_name,
      note.notes,
      note.strengths,
      note.weaknesses,
      note.best_for,
      note.image_path,
      note.image_url,
      note.thumb_path,
      note.thumb_url,
      note.settings,
      note.score,
    ].some(Boolean))
    : []
  const promptUsageNotes = String(item?.usage_notes || '').trim()
  const promptWorkflowNotes = String(item?.workflow_notes || '').trim()
  const promptHasFullAccess = Boolean(item?.prompt)
  const hasPromptDocumentation = Boolean(
    promptDocumentation.summary
    || promptDocumentation.display_notes
    || promptDocumentation.best_for.length
    || promptDocumentation.how_to_use.length
    || promptDocumentation.required_inputs.length
    || promptDocumentation.workflow.length
    || promptDocumentation.tips.length
    || promptDocumentation.common_mistakes.length
    || promptDocumentation.data_accuracy_notes.length,
  )
  const hasPromptPlaceholders = Boolean(item?.has_placeholder_inputs) && promptPlaceholders.length > 0
  const promptHasLockedHelperPrompts = Boolean(item?.has_helper_prompts) && !promptHasFullAccess
  const promptHasLockedVariants = Boolean(item?.has_prompt_variants) && !promptHasFullAccess
  const hasPromptHelperPrompts = promptHelperPrompts.length > 0
  const hasPromptVariants = promptVariants.length > 0
  const showPromptHelperPrompts = false
  const promptAccessRequirement = item?.access_requirement || promptRequirementText(item?.access_level)
  const promptUnlockTitle = item?.unlock_heading || promptUnlockHeading(item?.access_level)
  const promptUnlockDetails = item?.unlock_description || promptUnlockDescription(item?.access_level)
  const promptFeaturedExamples = promptPreviewImage ? promptPublicExamples.slice(0, 2) : promptPublicExamples.slice(0, 4)
  const promptOverflowExamples = promptPublicExamples.slice(promptFeaturedExamples.length)
  const promptModelsCovered = (promptHasFullAccess && promptComparisons.length ? promptComparisons : promptPublicExamples)
    .map((entry, index) => entry.model_name || entry.provider || entry.title || `Model ${index + 1}`)
  const promptComparisonGalleryImages = promptComparisons
      .map((note, index) => {
        const src = note.image_url || note.thumb_url || ''
        if (!src) return null

        return {
          src,
          alt: note.model_name || note.provider || `Comparison ${index + 1}`,
        }
      })
      .filter(Boolean)
  const promptPublicExampleGalleryImages = [
    ...(promptPreviewImage ? [{ src: promptPreviewImage, alt: item?.title || 'Prompt preview' }] : []),
    ...promptPublicExamples
      .map((example, index) => {
        const src = example.image_url || example.thumb_url || ''
        if (!src) return null

        return {
          src,
          alt: example.alt || example.title || `Prompt example ${index + 1}`,
        }
      })
      .filter(Boolean),
  ]
  const promptBestUseCase = promptComparisons[0]?.best_for
    || promptDocumentation.best_for[0]
    || promptUsageNotes
    || lessonSummary
  const academyBreadcrumbs = pageType === 'prompt'
    ? [
      { label: 'Academy', href: '/academy' },
      { label: 'Prompt Library', href: '/academy/prompts' },
      { label: item?.title || 'Prompt' },
    ]
    : []
  const fontScaleStorageKey = 'academy.lesson.font-scale'
  const fontScaleMin = 0.95
  const fontScaleMax = 1.12
  const fontScaleStep = 0.04
  const [lessonFontScale, setLessonFontScale] = useState(1.04)

  const findArticleHeading = (headingId) => {
    if (!headingId || typeof document === 'undefined') {
      return null
    }

    const escapedHeadingId = typeof CSS !== 'undefined' && typeof CSS.escape === 'function'
      ? CSS.escape(headingId)
      : String(headingId).replace(/[^a-zA-Z0-9_-]/g, '')

    return articleContentRef.current?.querySelector(`#${escapedHeadingId}`) || document.getElementById(headingId)
  }

  const markComplete = () => {
    if (!completeUrl || completed) return
    router.post(completeUrl, courseContext?.completePayload || {}, {
      preserveScroll: true,
      onSuccess: () => setCompleted(true),
    })
  }

  const requireLogin = () => {
    if (loginUrl && typeof window !== 'undefined') {
      window.location.href = loginUrl
    }
  }

  const toggleLike = async () => {
    if (!interactionRoutes?.like || !analytics?.contentType || !analytics?.contentId) {
      return
    }

    if (analytics?.isGuest) {
      requireLogin()
      return
    }

    const payload = await postAcademyAction(interactionRoutes.like, {
      content_type: analytics.contentType,
      content_id: analytics.contentId,
    })

    if (payload?.liked !== undefined) {
      setLiked(Boolean(payload.liked))
      setLikesCount(Number(payload.likes_count || 0))
    }
  }

  const toggleSave = async () => {
    if (interactionRoutes?.save && analytics?.contentType && analytics?.contentId) {
      if (analytics?.isGuest) {
        requireLogin()
        return
      }

      const payload = await postAcademyAction(interactionRoutes.save, {
        content_type: analytics.contentType,
        content_id: analytics.contentId,
      })

      if (payload?.saved !== undefined) {
        setSaved(Boolean(payload.saved))
        setSavesCount(Number(payload.saves_count || 0))
      }

      return
    }

    const url = saved ? unsaveUrl : saveUrl
    if (!url) return
    const method = saved ? router.delete : router.post
    method(url, {}, {
      preserveScroll: true,
      onSuccess: () => setSaved(!saved),
    })
  }

  useEffect(() => {
    if (pageType !== 'lesson' || !progressRoutes?.startLesson || !item?.id || analytics?.isGuest || completed || typeof window === 'undefined') {
      return
    }

    const onceKey = `academy-start-lesson:${item.id}:${courseContext?.id || 'solo'}`
    if (window.sessionStorage.getItem(onceKey)) {
      return
    }

    window.sessionStorage.setItem(onceKey, '1')
    void postAcademyAction(progressRoutes.startLesson, {
      lesson_id: item.id,
      course_id: courseContext?.id || null,
    })
  }, [analytics?.isGuest, completed, courseContext?.id, item?.id, pageType, progressRoutes?.startLesson])

  const decreaseFontSize = () => {
    setLessonFontScale((current) => Math.max(fontScaleMin, Number((current - fontScaleStep).toFixed(2))))
  }

  const increaseFontSize = () => {
    setLessonFontScale((current) => Math.min(fontScaleMax, Number((current + fontScaleStep).toFixed(2))))
  }

  const openPromptPreviewImage = () => {
    if (!promptPreviewImage) return

    setLightboxGallery({
      images: [{ src: promptPreviewImage, alt: item?.title || 'Prompt preview' }],
      index: 0,
    })
  }

  const openPromptComparisonGallery = (index) => {
    if (!promptComparisonGalleryImages.length) return

    setLightboxGallery({
      images: promptComparisonGalleryImages,
      index: Math.max(0, Math.min(promptComparisonGalleryImages.length - 1, Number(index || 0))),
    })
  }

  const openPromptExampleGallery = (index) => {
    if (!promptPublicExampleGalleryImages.length) return

    setLightboxGallery({
      images: promptPublicExampleGalleryImages,
      index: Math.max(0, Math.min(promptPublicExampleGalleryImages.length - 1, Number(index || 0))),
    })
  }

  const navigateLightboxGallery = (direction) => {
    setLightboxGallery((current) => {
      if (!current?.images?.length) return current

      const total = current.images.length
      const nextIndex = typeof direction === 'number' && Math.abs(direction) > 1
        ? Math.max(0, Math.min(total - 1, current.index + direction))
        : (current.index + direction + total) % total

      return {
        ...current,
        index: nextIndex,
      }
    })
  }

  const scrollToHeading = (headingId, behavior = 'smooth') => {
    if (typeof window === 'undefined') {
      return
    }

    const heading = findArticleHeading(headingId)

    if (!heading) {
      return
    }

    const top = Math.max(0, window.scrollY + heading.getBoundingClientRect().top - 112)
    window.scrollTo({ top, behavior })
    setActiveHeadingId(headingId)

    if (window.history?.replaceState) {
      window.history.replaceState(null, '', `${window.location.pathname}${window.location.search}#${headingId}`)
    }
  }

  useEffect(() => {
    handledInitialHashRef.current = false
  }, [item?.slug])

  useEffect(() => {
    if (pageType !== 'lesson' || !item?.content || !articleContentRef.current) {
      setTableOfContents([])
      setActiveHeadingId('')
      return
    }

    const headings = Array.from(articleContentRef.current.querySelectorAll('h2, h3'))
    const seenIds = new Map()
    const nextTableOfContents = headings.map((heading, index) => {
      const baseId = slugifyHeading(heading.textContent, `section-${index + 1}`)
      const seenCount = seenIds.get(baseId) ?? 0
      const nextId = seenCount > 0 ? `${baseId}-${seenCount + 1}` : baseId

      seenIds.set(baseId, seenCount + 1)
      heading.id = nextId
      heading.style.scrollMarginTop = '128px'

      return {
        id: nextId,
        title: heading.textContent?.trim() || `Section ${index + 1}`,
        level: heading.tagName.toLowerCase(),
      }
    })

    setTableOfContents(nextTableOfContents)
  }, [item?.content, pageType])

  useEffect(() => {
    if (pageType !== 'lesson' || tableOfContents.length === 0 || handledInitialHashRef.current || typeof window === 'undefined') {
      return
    }

    const hash = window.location.hash.replace(/^#/, '').trim()

    if (!hash) {
      handledInitialHashRef.current = true
      return
    }

    const matchingEntry = tableOfContents.find((entry) => entry.id === hash)

    if (!matchingEntry) {
      handledInitialHashRef.current = true
      return
    }

    handledInitialHashRef.current = true
    window.requestAnimationFrame(() => scrollToHeading(matchingEntry.id, 'auto'))
  }, [pageType, tableOfContents])

  useEffect(() => {
    if (pageType !== 'lesson' || tableOfContents.length === 0 || typeof window === 'undefined') {
      return undefined
    }

    const handleHashChange = () => {
      const hash = window.location.hash.replace(/^#/, '').trim()

      if (!hash) {
        return
      }

      const matchingEntry = tableOfContents.find((entry) => entry.id === hash)

      if (!matchingEntry) {
        return
      }

      window.requestAnimationFrame(() => scrollToHeading(matchingEntry.id, 'auto'))
    }

    window.addEventListener('hashchange', handleHashChange)
    return () => window.removeEventListener('hashchange', handleHashChange)
  }, [pageType, tableOfContents])

  useEffect(() => {
    if (pageType !== 'lesson' || tableOfContents.length === 0 || !articleContentRef.current) {
      setActiveHeadingId('')
      return
    }

    const getActiveId = () => {
      const headings = Array.from(articleContentRef.current.querySelectorAll('h2[id], h3[id]'))
      if (!headings.length) return ''

      // offset accounts for sticky header height + small buffer
      const offset = 140
      let activeId = headings[0].id

      for (const heading of headings) {
        if (heading.getBoundingClientRect().top <= offset) {
          activeId = heading.id
        }
      }

      return activeId
    }

    setActiveHeadingId(getActiveId())

    const onScroll = () => setActiveHeadingId(getActiveId())
    window.addEventListener('scroll', onScroll, { passive: true })

    return () => window.removeEventListener('scroll', onScroll)
  }, [pageType, tableOfContents, lessonFontScale])

  useEffect(() => {
    if (typeof window === 'undefined') {
      return
    }

    const storedValue = Number(window.localStorage.getItem(fontScaleStorageKey))

    if (!Number.isFinite(storedValue)) {
      return
    }

    setLessonFontScale(Math.min(fontScaleMax, Math.max(fontScaleMin, storedValue)))
  }, [fontScaleMax, fontScaleMin, fontScaleStorageKey])

  useEffect(() => {
    if (typeof window === 'undefined') {
      return
    }

    window.localStorage.setItem(fontScaleStorageKey, String(lessonFontScale))
  }, [lessonFontScale])

  useEffect(() => {
    if (pageType !== 'lesson' || !item?.content || !articleContentRef.current) {
      return
    }

    const codeBlocks = Array.from(articleContentRef.current.querySelectorAll('pre code'))

    if (!codeBlocks.length) {
      return
    }

    const fallbackCopyText = (text) => {
      const textarea = document.createElement('textarea')
      textarea.value = text
      textarea.setAttribute('readonly', 'true')
      textarea.style.position = 'fixed'
      textarea.style.top = '-1000px'
      textarea.style.left = '-1000px'
      document.body.appendChild(textarea)
      textarea.select()

      try {
        return document.execCommand('copy')
      } catch (_error) {
        return false
      } finally {
        document.body.removeChild(textarea)
      }
    }

    const copyText = (text) => {
      if (navigator.clipboard && typeof navigator.clipboard.writeText === 'function') {
        return navigator.clipboard.writeText(text)
      }

      return fallbackCopyText(text)
        ? Promise.resolve()
        : Promise.reject(new Error('Clipboard unavailable'))
    }

    codeBlocks.forEach((block) => {
      const pre = block.parentElement

      if (!pre || pre.dataset.academyCopyButtonMounted === 'true') {
        return
      }

      const button = document.createElement('button')
      const icon = document.createElement('span')
      const label = document.createElement('span')

      button.type = 'button'
      button.className = 'story-code-copy-button academy-code-copy-button'
      icon.className = 'story-code-copy-icon'
      icon.setAttribute('aria-hidden', 'true')
      icon.textContent = '⧉'
      label.className = 'story-code-copy-label'
      label.textContent = 'Copy'
      button.appendChild(icon)
      button.appendChild(label)
      button.dataset.copied = 'idle'
      button.setAttribute('aria-label', 'Copy code block')

      let resetTimer = 0

      button.addEventListener('click', () => {
        const source = block.innerText || block.textContent || ''

        copyText(source)
          .then(() => {
            icon.textContent = '✓'
            label.textContent = 'Copied'
            button.dataset.copied = 'true'
          })
          .catch(() => {
            icon.textContent = '!'
            label.textContent = 'Failed'
            button.dataset.copied = 'false'
          })
          .finally(() => {
            window.clearTimeout(resetTimer)
            resetTimer = window.setTimeout(() => {
              icon.textContent = '⧉'
              label.textContent = 'Copy'
              button.dataset.copied = 'idle'
            }, 1800)
          })
      })

      pre.appendChild(button)
      pre.dataset.academyCopyButtonMounted = 'true'
    })
  }, [item?.content, lessonFontScale, pageType])

  return (
    <main className="min-h-screen bg-[radial-gradient(circle_at_top_left,_rgba(56,189,248,0.16),_transparent_24%),radial-gradient(circle_at_bottom_right,_rgba(59,130,246,0.14),_transparent_26%),linear-gradient(180deg,_#0b1220_0%,_#111827_46%,_#0f172a_100%)] px-4 py-8 sm:px-6 lg:px-8">
      <SeoHead seo={seo || {}} title={item?.title} description={item?.excerpt || item?.description} />

      <div className="mx-auto max-w-[1320px] space-y-6">
        {flash.success ? <div className="rounded-2xl border border-emerald-300/20 bg-emerald-300/10 px-4 py-3 text-sm text-emerald-100">{flash.success}</div> : null}
        {flash.error ? <div className="rounded-2xl border border-rose-300/20 bg-rose-300/10 px-4 py-3 text-sm text-rose-100">{flash.error}</div> : null}

        {item.locked ? <LockedPanel pricingUrl={pricingUrl} label={pageType} accessLevel={item?.access_level} onUpgrade={() => trackUpgradeClick(analytics, { source: `${pageType}_locked_panel` })} /> : null}

        {pageType === 'lesson' ? (
          <div className="space-y-8">
            <section className="overflow-hidden rounded-[40px] border border-white/10 bg-black/20 shadow-[0_24px_90px_rgba(15,23,42,0.34)]">
              <div className="grid gap-0 lg:grid-cols-[minmax(0,1fr)_360px]">
                <div className="relative overflow-hidden p-8 md:p-10 lg:p-12">
                  {lessonCover ? <img src={lessonCover} alt="" aria-hidden="true" className="absolute inset-0 h-full w-full object-cover opacity-15" /> : null}
                  <div className="absolute inset-0 bg-[radial-gradient(circle_at_top_left,_rgba(56,189,248,0.22),_transparent_34%),linear-gradient(135deg,_rgba(2,6,23,0.96),_rgba(15,23,42,0.78))]" />
                  <div className="relative z-10 max-w-3xl">
                    <div className="flex flex-wrap gap-2">
                      <span className="rounded-full border border-sky-300/20 bg-sky-300/10 px-3 py-1 text-[11px] font-semibold uppercase tracking-[0.24em] text-sky-100">Skinbase AI Academy</span>
                      <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-300">{lessonCategory}</span>
                      <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-300">{lessonDifficulty}</span>
                    </div>

                    {item.lesson_label ? <p className="mt-5 text-sm font-semibold uppercase tracking-[0.24em] text-amber-100">{item.lesson_label}</p> : null}

                    <h1 className="mt-5 text-4xl font-semibold tracking-[-0.055em] text-white md:text-5xl lg:text-6xl">{item.title}</h1>
                    <p className="mt-5 max-w-2xl text-base leading-8 text-slate-300 md:text-lg">{lessonSummary}</p>

                    {lessonTags.length ? (
                      <div className="mt-5 flex flex-wrap gap-2">
                        {lessonTags.map((tag) => (
                          <span key={tag} className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-[11px] font-semibold uppercase tracking-[0.18em] text-slate-200">{tag}</span>
                        ))}
                      </div>
                    ) : null}

                    {courseContext?.title ? (
                      <div className="mt-6 max-w-2xl rounded-[24px] border border-white/10 bg-black/25 p-5">
                        <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Part of course</p>
                        <Link href={courseContext.showUrl} className="mt-2 inline-flex text-lg font-semibold text-sky-100 transition hover:text-white">{courseContext.title}</Link>
                        <p className="mt-2 text-sm leading-7 text-slate-300">{courseContext.subtitle || 'This lesson is being viewed inside a structured Academy course path.'}</p>
                      </div>
                    ) : null}

                    <div className="mt-7 flex flex-wrap gap-3">
                      {completeUrl ? <button type="button" onClick={markComplete} className="rounded-full border border-emerald-300/25 bg-emerald-300/12 px-5 py-3 text-sm font-semibold text-emerald-100">{completed ? 'Completed' : 'Mark complete'}</button> : null}
                      <button type="button" onClick={toggleLike} className="rounded-full border border-white/10 bg-white/[0.06] px-5 py-3 text-sm font-semibold text-white transition hover:border-white/20 hover:bg-white/[0.08]">{liked ? `Liked · ${likesCount}` : `Like · ${likesCount}`}</button>
                      <button type="button" onClick={toggleSave} className="rounded-full border border-sky-300/25 bg-sky-300/12 px-5 py-3 text-sm font-semibold text-sky-100">{saved ? `Saved · ${savesCount}` : `Save · ${savesCount}`}</button>
                      {submitUrl ? <Link href={submitUrl} className="rounded-full border border-white/10 bg-white/[0.06] px-5 py-3 text-sm font-semibold text-white transition hover:border-sky-300/25 hover:bg-sky-300/12 hover:text-sky-100">Submit artwork</Link> : null}
                    </div>

                    <div className="mt-8 grid gap-3 sm:grid-cols-2 xl:grid-cols-4">
                      <StatPill label="Category" value={lessonCategory} />
                      <StatPill label="Reading" value={lessonMinutes} />
                      <StatPill label="Updated" value={lessonUpdated} />
                      <StatPill label={courseContext?.title ? 'Course progress' : 'Access'} value={courseContext?.progress ? `${courseContext.progress.percent}%` : (item.access_level || 'free')} />
                    </div>
                  </div>
                </div>

                <aside className="border-t border-white/10 bg-white/[0.03] p-6 lg:border-l lg:border-t-0 lg:p-8">
                  <div className="space-y-5 lg:sticky lg:top-6">
                    <div className="overflow-hidden rounded-[28px] border border-white/10 bg-black/20">
                      {lessonCover ? <img src={lessonCover} alt={item.title} className="h-52 w-full object-cover" /> : <div className="flex h-52 items-center justify-center bg-[linear-gradient(135deg,_rgba(14,165,233,0.18),_rgba(17,24,39,0.94))] text-sm font-semibold uppercase tracking-[0.24em] text-slate-300">Lesson cover</div>}
                    </div>

                    <div className="space-y-3">
                      <LessonInfoRow label="Series" value={lessonSeries} />
                      {item.formatted_lesson_number ? <LessonInfoRow label="Lesson" value={item.formatted_lesson_number} /> : null}
                      <LessonInfoRow label="Difficulty" value={lessonDifficulty} />
                      <LessonInfoRow label="Reading time" value={lessonMinutes} />
                      <LessonInfoRow label="Published" value={lessonUpdated} />
                    </div>

                    <div className="rounded-[28px] border border-white/10 bg-black/20 p-5">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Lesson status</p>
                      <p className="mt-3 text-sm leading-7 text-slate-300">{item.locked ? 'This lesson is partially locked for your account level.' : courseContext?.title ? 'This lesson is being tracked inside a course. Completion updates your course progress.' : 'Full lesson content is available below.'}</p>
                    </div>
                  </div>
                </aside>
              </div>
            </section>

            <div className="grid gap-8 lg:grid-cols-[minmax(0,1fr)_360px]">
              <article className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.045),rgba(148,163,184,0.03))] p-6 text-slate-200 shadow-[0_24px_70px_rgba(2,6,23,0.2)] md:p-8">
                <div className="flex flex-wrap items-center justify-between gap-4 border-b border-white/10 pb-5">
                  <div>
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-sky-200/80">Article</p>
                    <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Lesson content</h2>
                  </div>
                  <div className="flex flex-wrap items-center gap-2">
                    <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-xs font-semibold uppercase tracking-[0.2em] text-slate-300">{lessonMinutes}</span>
                    <div className="flex items-center gap-1 rounded-full border border-white/10 bg-black/20 p-1">
                      <button
                        type="button"
                        onClick={decreaseFontSize}
                        disabled={lessonFontScale <= fontScaleMin}
                        aria-label="Decrease article text size"
                        className="inline-flex h-8 w-8 items-center justify-center rounded-full border border-white/10 bg-white/[0.04] text-sm font-semibold text-slate-200 transition hover:border-sky-300/30 hover:bg-sky-300/12 hover:text-sky-100 disabled:cursor-not-allowed disabled:opacity-40"
                      >
                        -
                      </button>
                      <span className="min-w-12 px-1 text-center text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">{Math.round(lessonFontScale * 100)}%</span>
                      <button
                        type="button"
                        onClick={increaseFontSize}
                        disabled={lessonFontScale >= fontScaleMax}
                        aria-label="Increase article text size"
                        className="inline-flex h-8 w-8 items-center justify-center rounded-full border border-white/10 bg-white/[0.04] text-sm font-semibold text-slate-200 transition hover:border-sky-300/30 hover:bg-sky-300/12 hover:text-sky-100 disabled:cursor-not-allowed disabled:opacity-40"
                      >
                        +
                      </button>
                    </div>
                  </div>
                </div>

                <div className="mt-6">
                  {articleCover ? (
                    <div className="mb-8 overflow-hidden rounded-[28px] border border-white/10 bg-black/20">
                      <img src={articleCover} alt={`${item.title} article cover`} className="w-full object-cover" />
                    </div>
                  ) : null}

                  {item.content ? (
                    <div className="space-y-8">
                      <div
                        ref={articleContentRef}
                        className="story-prose academy-lesson-prose prose prose-invert max-w-none"
                        style={{ '--academy-lesson-font-scale': lessonFontScale }}
                        dangerouslySetInnerHTML={{ __html: item.content }}
                      />
                      {lessonBlocks.map((block) => <AiComparisonSection key={block.id || `${block.type}-${block.sort_order || 0}`} block={block} />)}
                    </div>
                  ) : (
                    <div className="space-y-8">
                      <div className="whitespace-pre-wrap text-sm leading-8 text-slate-200">{item.content_preview}</div>
                      {lessonBlocks.map((block) => <AiComparisonSection key={block.id || `${block.type}-${block.sort_order || 0}`} block={block} />)}
                    </div>
                  )}
                </div>

                {(previousLesson || nextLesson) ? (
                  <section className="mt-10 border-t border-white/10 pt-8">
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">{courseContext?.title ? 'Course navigation' : 'Lesson navigation'}</p>
                    <h3 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">{courseContext?.title ? 'Continue this course' : 'Continue in order'}</h3>

                    <div className="mt-5 grid gap-4 md:grid-cols-2">
                      <LessonNavCard direction="previous" lesson={previousLesson} />
                      <LessonNavCard direction="next" lesson={nextLesson} />
                    </div>
                  </section>
                ) : null}
              </article>

              <aside className="space-y-6 lg:sticky lg:top-6 lg:self-start">
                {tableOfContents.length ? (
                  <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">On this page</p>
                    <h3 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Table of contents</h3>

                    <nav aria-label="Lesson table of contents" className="mt-5 space-y-1.5">
                      {tableOfContents.map((entry) => (
                        <a
                          key={entry.id}
                          href={`#${entry.id}`}
                          onClick={(event) => {
                            event.preventDefault()
                            scrollToHeading(entry.id)
                          }}
                          aria-current={activeHeadingId === entry.id ? 'location' : undefined}
                          className={`academy-lesson-toc-link ${entry.level === 'h3' ? 'academy-lesson-toc-link-subtle' : ''} ${activeHeadingId === entry.id ? 'academy-lesson-toc-link-active' : ''}`}
                        >
                          <span className="academy-lesson-toc-link-indicator" aria-hidden="true" />
                          <span>{entry.title}</span>
                        </a>
                      ))}
                    </nav>
                  </section>
                ) : null}

                <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                  <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">{courseContext?.title ? 'Course progress' : 'Series info'}</p>
                  <h3 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">{courseContext?.title ? courseContext.title : lessonSeries}</h3>
                  <div className="mt-5 space-y-3">
                    <LessonInfoRow label="Category" value={lessonCategory} />
                    {item.formatted_lesson_number ? <LessonInfoRow label="Lesson" value={item.formatted_lesson_number} /> : null}
                    <LessonInfoRow label="Difficulty" value={lessonDifficulty} />
                    <LessonInfoRow label="Reading" value={lessonMinutes} />
                    <LessonInfoRow label={courseContext?.title ? 'Progress' : 'Updated'} value={courseContext?.progress ? `${courseContext.progress.completedRequired}/${courseContext.progress.totalRequired} completed` : lessonUpdated} />
                  </div>
                </section>

                {courseOutline.length ? (
                  <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Course outline</p>
                    <div className="mt-4 space-y-2">
                      {courseOutline.map((outlineLesson, index) => (
                        <Link key={outlineLesson.course_lesson_id || outlineLesson.id || index} href={outlineLesson.course_url || `/academy/lessons/${outlineLesson.slug}`} className={`flex items-start gap-3 rounded-[20px] border px-4 py-3 text-sm transition ${outlineLesson.slug === item.slug ? 'border-sky-300/25 bg-sky-300/10 text-sky-100' : 'border-white/10 bg-black/20 text-slate-300 hover:border-sky-300/25 hover:bg-white/[0.06]'}`}>
                          <span className="mt-0.5 inline-flex h-6 w-6 shrink-0 items-center justify-center rounded-full border border-white/10 bg-white/[0.05] text-[10px] font-semibold">{String(index + 1).padStart(2, '0')}</span>
                          <span className="min-w-0 flex-1">
                            <span className="block font-semibold">{outlineLesson.title}</span>
                            <span className="mt-1 block text-xs uppercase tracking-[0.16em] text-slate-500">{outlineLesson.is_required ? 'Required' : 'Optional'}</span>
                          </span>
                        </Link>
                      ))}
                    </div>
                  </section>
                ) : null}

                {lessonTags.length ? (
                  <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Microtags</p>
                    <div className="mt-4 flex flex-wrap gap-2">
                      {lessonTags.map((tag) => (
                        <span key={tag} className="rounded-full border border-sky-300/20 bg-sky-300/10 px-3 py-1.5 text-xs font-semibold uppercase tracking-[0.18em] text-sky-100">{tag}</span>
                      ))}
                    </div>
                  </section>
                ) : null}

                {relatedLessonList.length ? (
                  <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Continue learning</p>
                    <h3 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">More in {lessonSeries}</h3>

                    <div className="mt-5 space-y-3">
                      {relatedLessonList.map((relatedLesson, index) => (
                        <Link
                          key={relatedLesson.id}
                          href={relatedLesson.course_url || `/academy/lessons/${relatedLesson.slug}`}
                          className="group flex gap-4 rounded-[22px] border border-white/10 bg-black/20 p-4 transition hover:border-sky-300/25 hover:bg-white/[0.06]"
                        >
                          <div className="flex h-12 w-12 shrink-0 items-center justify-center rounded-2xl border border-sky-300/15 bg-sky-300/10 text-sm font-semibold text-sky-100">
                            {String(index + 1).padStart(2, '0')}
                          </div>

                          <div className="min-w-0 flex-1">
                            <div className="flex items-start justify-between gap-3">
                              <div>
                                {relatedLesson.formatted_lesson_number ? <p className="text-[10px] font-semibold uppercase tracking-[0.18em] text-amber-100">{relatedLesson.formatted_lesson_number}</p> : null}
                                <h4 className="text-sm font-semibold text-white transition group-hover:text-sky-100">{relatedLesson.title}</h4>
                              </div>
                              <span className="shrink-0 rounded-full border border-white/10 bg-white/[0.04] px-2.5 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-400">{formatLessonMinutes(relatedLesson.reading_minutes)}</span>
                            </div>
                            <p className="mt-2 text-xs leading-6 text-slate-400">{relatedLesson.excerpt || relatedLesson.content_preview || 'Continue the series with the next lesson.'}</p>
                          </div>
                        </Link>
                      ))}
                    </div>
                  </section>
                ) : null}

                {relatedCourseList.length ? (
                  <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Related courses</p>
                    <div className="mt-4 space-y-3">
                      {relatedCourseList.map((course) => (
                        <Link key={course.id} href={course.public_url} className="block rounded-[22px] border border-white/10 bg-black/20 p-4 transition hover:border-sky-300/25 hover:bg-white/[0.06]">
                          <p className="text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-500">{course.difficulty} · {course.access_level}</p>
                          <h4 className="mt-2 text-sm font-semibold text-white">{course.title}</h4>
                          <p className="mt-2 text-xs leading-6 text-slate-400">{course.excerpt || course.description || 'Open this course to continue with a guided path.'}</p>
                        </Link>
                      ))}
                    </div>
                  </section>
                ) : null}
              </aside>
            </div>
          </div>
        ) : pageType === 'prompt' ? (
          <div className="space-y-8">
            <section className="overflow-hidden rounded-[40px] border border-white/10 bg-[linear-gradient(135deg,rgba(4,10,20,0.98),rgba(15,23,42,0.9))] shadow-[0_24px_90px_rgba(15,23,42,0.34)]">
              <div className="grid gap-0 lg:grid-cols-[minmax(340px,0.8fr)_minmax(0,1.2fr)]">
                <div className="relative border-b border-white/10 bg-[radial-gradient(circle_at_top_left,rgba(56,189,248,0.18),transparent_34%),radial-gradient(circle_at_bottom_right,rgba(255,183,139,0.18),transparent_32%),linear-gradient(180deg,rgba(5,10,20,0.98),rgba(10,17,30,0.94))] p-5 md:p-6 lg:min-h-[660px] lg:border-b-0 lg:border-r lg:border-white/10 lg:p-8">
                  <div className="absolute inset-0 bg-[radial-gradient(circle_at_20%_20%,rgba(125,211,252,0.12),transparent_24%),radial-gradient(circle_at_80%_75%,rgba(255,207,191,0.12),transparent_28%)]" />
                  <div className="relative flex h-full flex-col">
                    <div className="flex items-center justify-between gap-3">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffd8cd]">Preview artwork</p>
                      {promptPreviewImage ? <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.18em] text-slate-300">Click to zoom</span> : null}
                    </div>

                    <button
                      type="button"
                      onClick={openPromptPreviewImage}
                      className="group mt-3 flex-1 overflow-hidden rounded-[32px] border border-white/10 bg-black/30 text-left shadow-[0_24px_80px_rgba(2,6,23,0.26)] transition hover:border-sky-300/25 focus:outline-none focus:ring-2 focus:ring-sky-300/35"
                      disabled={!promptPreviewImage}
                      aria-label={promptPreviewImage ? `Open preview image for ${item.title}` : 'Preview image unavailable'}
                    >
                      {promptPreviewImage ? (
                        <div className="relative h-full min-h-[320px] overflow-hidden lg:min-h-[540px]">
                          <img src={promptPreviewThumbImage} srcSet={promptPreviewSrcSet || undefined} sizes="(max-width: 1023px) calc(100vw - 3rem), 720px" alt={item.title} className="h-full w-full object-cover transition duration-500 group-hover:scale-[1.03]" />
                          <div className="absolute inset-0 bg-[linear-gradient(180deg,rgba(2,6,23,0.02),rgba(2,6,23,0.28))]" />
                          <div className="absolute bottom-4 left-4 right-4 flex items-end justify-between gap-4 rounded-[24px] border border-white/10 bg-black/25 px-4 py-3 backdrop-blur-md">
                            <div>
                              <p className="text-[10px] font-semibold uppercase tracking-[0.22em] text-sky-100/80">Prompt visual</p>
                              <p className="mt-1 text-sm font-semibold text-white">Open full-size preview</p>
                            </div>
                            <span className="inline-flex h-10 w-10 items-center justify-center rounded-full border border-white/10 bg-white/10 text-white">
                              <i className="fa-solid fa-expand" />
                            </span>
                          </div>
                        </div>
                      ) : (
                        <div className="flex h-full min-h-[360px] items-center justify-center bg-[linear-gradient(135deg,rgba(251,146,60,0.14),rgba(17,24,39,0.96))] px-8 text-center lg:min-h-[620px]">
                          <div>
                            <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Visual placeholder</p>
                            <p className="mt-4 text-lg font-semibold text-white">Preview image coming soon</p>
                            <p className="mt-3 text-sm leading-7 text-slate-300">This prompt page will feel much better once the generated cover image is attached.</p>
                          </div>
                        </div>
                      )}
                    </button>
                  </div>
                </div>

                <div className="relative overflow-hidden p-6 md:p-8 lg:p-9">
                  <div className="absolute inset-0 bg-[radial-gradient(circle_at_top_left,_rgba(255,183,139,0.14),_transparent_28%),radial-gradient(circle_at_bottom_right,_rgba(56,189,248,0.12),_transparent_28%)]" />
                  <div className="relative z-10 max-w-3xl">
                    {academyBreadcrumbs.length ? (
                      <div className="mb-5">
                        <AcademyBreadcrumbs items={academyBreadcrumbs} />
                      </div>
                    ) : null}

                    <div className="flex flex-wrap gap-2">
                      <span className="rounded-full border border-[#ffcfbf]/20 bg-[#ffcfbf]/10 px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.22em] text-[#fff0ea]">Skinbase AI Academy</span>
                      <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.22em] text-slate-300">{lessonCategory}</span>
                      <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.22em] text-slate-300">{lessonDifficulty}</span>
                      {item.aspect_ratio ? <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.22em] text-slate-300">{item.aspect_ratio}</span> : null}
                      {item.prompt_of_week ? <span className="rounded-full border border-amber-300/25 bg-amber-300/10 px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.22em] text-amber-100">Prompt of the week</span> : null}
                      {item.featured ? <span className="rounded-full border border-sky-300/20 bg-sky-300/10 px-3 py-1 text-[10px] font-semibold uppercase tracking-[0.22em] text-sky-100">Featured</span> : null}
                    </div>

                    <p className="mt-6 text-xs font-semibold uppercase tracking-[0.22em] text-[#ffd8cd]">Prompt template</p>
                    <h1 className="mt-3 max-w-3xl text-[clamp(2.4rem,4.8vw,4.5rem)] font-semibold leading-[0.95] tracking-[-0.05em] text-white">{item.title}</h1>
                    <p className="mt-4 max-w-2xl text-[15px] leading-7 text-slate-300 md:text-base">{lessonSummary}</p>

                    <div className="mt-6 flex flex-wrap gap-3">
                      <button type="button" onClick={toggleLike} className="rounded-full border border-white/10 bg-white/[0.06] px-4 py-2.5 text-sm font-semibold text-white transition hover:border-white/20 hover:bg-white/[0.08]">{liked ? `Liked · ${likesCount}` : `Like · ${likesCount}`}</button>
                      <button type="button" onClick={toggleSave} className="rounded-full border border-sky-300/25 bg-sky-300/12 px-4 py-2.5 text-sm font-semibold text-sky-100">{saved ? `Saved · ${savesCount}` : `Save · ${savesCount}`}</button>
                      {promptHasFullAccess ? <PromptCopyButton prompt={item.prompt} analytics={analytics} contentId={item.id} eventType="academy_prompt_copy" metadata={{ copy_type: 'main_prompt', source: 'prompt_detail' }} /> : null}
                      {promptHasFullAccess && item.negative_prompt ? <PromptCopyButton prompt={item.negative_prompt} label="Copy negative" analytics={analytics} contentId={item.id} eventType="academy_prompt_negative_copy" metadata={{ copy_type: 'negative_prompt', source: 'prompt_detail' }} /> : null}
                    </div>

                    <div className="mt-7 grid gap-3 sm:grid-cols-2 xl:grid-cols-4">
                      <PromptHeaderStat
                        label="Category"
                        value={lessonCategory}
                        icon="fa-layer-group"
                        accentClassName="border-sky-300/15 bg-sky-300/10 text-sky-100"
                        valueClassName="text-white"
                      />
                      <PromptHeaderStat
                        label="Access"
                        value={formatMetaDisplay(item.access_level || 'free')}
                        icon={normalizePromptAccessLevel(item.access_level) === 'pro' ? 'fa-crown' : normalizePromptAccessLevel(item.access_level) === 'creator' ? 'fa-key' : 'fa-lock-open'}
                        accentClassName={normalizePromptAccessLevel(item.access_level) === 'pro' ? 'border-amber-300/20 bg-amber-300/10 text-amber-100' : normalizePromptAccessLevel(item.access_level) === 'creator' ? 'border-violet-300/20 bg-violet-300/10 text-violet-100' : 'border-emerald-300/20 bg-emerald-300/10 text-emerald-100'}
                        valueClassName={normalizePromptAccessLevel(item.access_level) === 'pro' ? 'text-amber-50' : normalizePromptAccessLevel(item.access_level) === 'creator' ? 'text-violet-50' : 'text-emerald-50'}
                      />
                      <PromptHeaderStat
                        label="Difficulty"
                        value={formatMetaDisplay(lessonDifficulty)}
                        icon={String(lessonDifficulty || '').toLowerCase() === 'advanced' ? 'fa-bolt' : String(lessonDifficulty || '').toLowerCase() === 'beginner' ? 'fa-seedling' : 'fa-compass-drafting'}
                        accentClassName={String(lessonDifficulty || '').toLowerCase() === 'advanced' ? 'border-rose-300/20 bg-rose-300/10 text-rose-100' : String(lessonDifficulty || '').toLowerCase() === 'beginner' ? 'border-emerald-300/20 bg-emerald-300/10 text-emerald-100' : 'border-sky-300/20 bg-sky-300/10 text-sky-100'}
                        valueClassName={String(lessonDifficulty || '').toLowerCase() === 'advanced' ? 'text-rose-50' : String(lessonDifficulty || '').toLowerCase() === 'beginner' ? 'text-emerald-50' : 'text-sky-50'}
                      />
                      <PromptHeaderStat
                        label="Updated"
                        value={lessonUpdated}
                        icon="fa-calendar-days"
                        accentClassName="border-white/10 bg-white/[0.05] text-slate-200"
                        valueClassName="text-white"
                      />
                    </div>

                    {lessonTags.length ? (
                      <div className="mt-7 rounded-[28px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.045),rgba(148,163,184,0.03))] p-4 md:p-5">
                        <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Microtags</p>
                        <div className="mt-3 flex flex-wrap gap-2">
                          {lessonTags.map((tag) => (
                            <span key={tag} className="rounded-full border border-sky-300/20 bg-sky-300/10 px-3 py-1.5 text-xs font-semibold uppercase tracking-[0.18em] text-sky-100">{tag}</span>
                          ))}
                        </div>
                      </div>
                    ) : null}

                    <div className="mt-7 grid gap-4 xl:grid-cols-[minmax(0,1.08fr)_minmax(260px,0.92fr)]">
                      <div className="rounded-[28px] border border-white/10 bg-black/20 p-4 md:p-5">
                        <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Prompt status</p>
                        <p className="mt-3 text-sm leading-7 text-slate-300">
                          {item.locked
                            ? `${promptAccessRequirement ? `${promptAccessRequirement} ` : ''}This page shows the prompt summary and public example results, but the reusable prompt system stays locked until your Academy access level matches the template.`
                            : 'This template includes the main prompt, reuse guidance, and model-specific comparison notes in one place.'}
                        </p>
                      </div>

                      {promptModelsCovered.length ? (
                        <div className="rounded-[28px] border border-[#ffcfbf]/12 bg-[linear-gradient(180deg,rgba(255,207,191,0.08),rgba(255,255,255,0.03))] p-4 md:p-5">
                          <div className="flex items-center justify-between gap-3">
                            <div>
                              <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffd8cd]">Compared with</p>
                              <p className="mt-2 text-sm text-slate-300">{promptModelsCovered.length} model{promptModelsCovered.length > 1 ? 's' : ''} documented for this prompt.</p>
                            </div>
                            <span className="rounded-full border border-white/10 bg-white/[0.05] px-3 py-1 text-xs font-semibold text-white">{promptModelsCovered.length}</span>
                          </div>
                          <div className="mt-4 flex flex-wrap gap-2">
                            {promptModelsCovered.map((model) => (
                              <span key={model} className="rounded-full border border-[#ffcfbf]/15 bg-[#ffcfbf]/10 px-3 py-1.5 text-xs font-semibold uppercase tracking-[0.18em] text-[#fff0ea]">{model}</span>
                            ))}
                          </div>
                        </div>
                      ) : null}
                    </div>
                  </div>
                </div>
              </div>
            </section>

            <div className="grid gap-8 lg:grid-cols-[minmax(0,1fr)_360px]">
              <div className="space-y-8">
                {!promptHasFullAccess && (promptPreviewImage || promptPublicExamples.length) ? (
                  <section className="academy-public-examples rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.045),rgba(148,163,184,0.03))] p-6 text-slate-200 shadow-[0_24px_70px_rgba(2,6,23,0.2)] md:p-8">
                    <div className="flex flex-wrap items-end justify-between gap-4">
                      <div>
                        <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffd8cd]">Public examples</p>
                        <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Example results from this prompt</h2>
                        <p className="mt-3 text-sm leading-6 text-slate-300">Preview the visual direction before unlocking the full prompt.</p>
                      </div>
                      {item.locked && promptAccessRequirement ? <span className="rounded-full border border-amber-300/20 bg-amber-300/10 px-3 py-1 text-[11px] font-semibold uppercase tracking-[0.18em] text-amber-100">{promptAccessRequirement}</span> : null}
                    </div>

                    <div className={`mt-6 grid gap-4 ${promptPreviewImage ? 'xl:grid-cols-[minmax(0,0.98fr)_minmax(0,1.02fr)] xl:items-start' : ''}`}>
                      {promptPreviewImage ? (
                        <button
                          type="button"
                          onClick={() => openPromptExampleGallery(0)}
                          className="group overflow-hidden rounded-[28px] border border-white/10 bg-slate-950 text-left shadow-[0_18px_50px_rgba(2,6,23,0.22)] transition hover:border-sky-300/25"
                          aria-label="Open main prompt preview"
                        >
                          <div className="relative aspect-[4/5] overflow-hidden xl:aspect-[6/5]">
                            <img src={promptPreviewThumbImage} srcSet={promptPreviewSrcSet || undefined} sizes="(max-width: 767px) calc(100vw - 4rem), (max-width: 1279px) calc(100vw - 4rem), 640px" alt={item?.title || 'Prompt preview'} className="h-full w-full object-cover transition duration-500 group-hover:scale-[1.03]" />
                            <div className="absolute inset-0 bg-[linear-gradient(180deg,rgba(2,6,23,0.04),rgba(2,6,23,0.42))]" />
                          </div>
                          <div className="space-y-2 border-t border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.94),rgba(2,6,23,0.88))] p-4 md:p-5">
                            <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-[#ffcfbf]">Preview artwork</p>
                            <h3 className="text-xl font-semibold tracking-[-0.03em] text-white">Prompt visual</h3>
                            <p className="text-sm leading-6 text-slate-300">{item?.excerpt || 'Studio-ready packaging, pose, and finish.'}</p>
                          </div>
                        </button>
                      ) : null}

                      {promptFeaturedExamples.length ? (
                        <div className={`grid gap-3 ${promptPreviewImage ? 'sm:grid-cols-2 xl:grid-cols-1' : 'sm:grid-cols-2 xl:grid-cols-3'}`}>
                          {promptFeaturedExamples.map((example, index) => (
                            <PromptPublicExampleCard
                              key={`${example.image_path || example.image_url || 'example'}-${index}`}
                              example={example}
                              index={index}
                              galleryIndex={index + (promptPreviewImage ? 1 : 0)}
                              onOpenImage={openPromptExampleGallery}
                              className={!promptPreviewImage && index === 0 ? 'sm:col-span-2 xl:col-span-2' : ''}
                              frameClassName={promptPreviewImage ? 'aspect-[16/10]' : index === 0 ? 'aspect-[16/10]' : 'aspect-[6/7]'}
                            />
                          ))}
                        </div>
                      ) : null}
                    </div>

                    {promptOverflowExamples.length ? (
                      <div className="mt-4 grid gap-3 sm:grid-cols-2 xl:grid-cols-3">
                        {promptOverflowExamples.map((example, index) => (
                          <PromptPublicExampleCard
                            key={`${example.image_path || example.image_url || 'overflow-example'}-${index}`}
                            example={example}
                            index={index + promptFeaturedExamples.length}
                            galleryIndex={index + promptFeaturedExamples.length + (promptPreviewImage ? 1 : 0)}
                            onOpenImage={openPromptExampleGallery}
                            frameClassName={index % 3 === 0 ? 'aspect-[6/7]' : index % 3 === 1 ? 'aspect-square' : 'aspect-[5/6]'}
                          />
                        ))}
                      </div>
                    ) : null}
                  </section>
                ) : null}

                <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.045),rgba(148,163,184,0.03))] p-6 text-slate-200 shadow-[0_24px_70px_rgba(2,6,23,0.2)] md:p-8">
                  <div className="flex flex-wrap items-center justify-between gap-4 border-b border-white/10 pb-5">
                    <div>
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffd8cd]">Prompt body</p>
                      <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Prompt text and exclusions</h2>
                    </div>
                  </div>

                  <div className="mt-6 space-y-6">
                    <div className="academy-paywalled-content rounded-[28px] border border-[#ffcfbf]/15 bg-[linear-gradient(180deg,rgba(255,207,191,0.08),rgba(255,255,255,0.03))] p-5 md:p-6">
                      <div className="flex flex-wrap items-start justify-between gap-3">
                        <div>
                          <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-[#fff0ea]">{promptHasFullAccess ? 'Full prompt' : 'Preview prompt'}</p>
                          <p className="mt-2 text-xs uppercase tracking-[0.16em] text-slate-500">{promptHasFullAccess ? 'Ready to paste into your generation workflow.' : 'Upgrade your Academy access to reveal the complete prompt text.'}</p>
                        </div>
                        {promptBody ? (
                          <PromptCopyButton
                            prompt={promptBody}
                            label={promptHasFullAccess ? 'Copy prompt' : 'Copy preview'}
                            analytics={analytics}
                            contentId={item.id}
                            eventType="academy_prompt_copy"
                            metadata={{ copy_type: promptHasFullAccess ? 'main_prompt' : 'preview_prompt', source: 'prompt_body' }}
                          />
                        ) : null}
                      </div>
                      <pre className="mt-4 whitespace-pre-wrap rounded-[24px] border border-white/10 bg-slate-950/80 p-4 text-sm leading-7 text-slate-100 md:p-5">{promptBody || 'Prompt text is not available yet.'}</pre>
                      {!promptHasFullAccess ? (
                        <div className="mt-4 rounded-[24px] border border-amber-300/20 bg-amber-300/10 p-4 text-amber-50">
                          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-amber-100/80">{promptUnlockTitle || 'Unlock the full prompt'}</p>
                          <p className="mt-3 text-sm leading-7 text-amber-50/90">{promptUnlockDetails}</p>
                          {promptAccessRequirement ? <p className="mt-3 text-xs font-semibold uppercase tracking-[0.18em] text-amber-100">{promptAccessRequirement}</p> : null}
                        </div>
                      ) : null}
                    </div>

                    {item.negative_prompt ? (
                      <div className="rounded-[28px] border border-white/10 bg-black/20 p-5 md:p-6">
                        <div className="flex flex-wrap items-center justify-between gap-3">
                          <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Negative prompt</p>
                          <PromptCopyButton
                            prompt={item.negative_prompt}
                            label="Copy negative"
                            analytics={analytics}
                            contentId={item.id}
                            eventType="academy_prompt_negative_copy"
                            metadata={{ copy_type: 'negative_prompt', source: 'prompt_body' }}
                          />
                        </div>
                        <pre className="mt-4 whitespace-pre-wrap rounded-[24px] border border-white/10 bg-slate-950/70 p-4 text-sm leading-7 text-slate-200 md:p-5">{item.negative_prompt}</pre>
                      </div>
                    ) : null}
                  </div>
                </section>

                {(promptUsageNotes || promptWorkflowNotes) ? (
                  <section className="academy-paywalled-content rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.82))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)] md:p-8">
                    <div className="flex flex-wrap items-end justify-between gap-4">
                      <div>
                        <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Prompt guidance</p>
                        <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">How to use this prompt</h2>
                      </div>
                      {!promptHasFullAccess ? <span className="rounded-full border border-amber-300/20 bg-amber-300/10 px-3 py-1 text-[11px] font-semibold uppercase tracking-[0.18em] text-amber-100">Full notes visible with access</span> : null}
                    </div>

                    <div className="mt-6 grid gap-5 md:grid-cols-2">
                      {promptUsageNotes ? (
                        <div className="rounded-[26px] border border-white/10 bg-black/20 p-5">
                          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-sky-200/75">Usage notes</p>
                          <p className="mt-3 whitespace-pre-wrap text-sm leading-7 text-slate-200">{promptUsageNotes}</p>
                        </div>
                      ) : null}

                      {promptWorkflowNotes ? (
                        <div className="rounded-[26px] border border-white/10 bg-black/20 p-5">
                          <p className="text-[11px] font-semibold uppercase tracking-[0.2em] text-emerald-200/75">Workflow notes</p>
                          <p className="mt-3 whitespace-pre-wrap text-sm leading-7 text-slate-200">{promptWorkflowNotes}</p>
                        </div>
                      ) : null}
                    </div>
                  </section>
                ) : null}

                {hasPromptDocumentation ? <PromptDocumentationPanel documentation={promptDocumentation} /> : null}

                {hasPromptPlaceholders ? (
                  <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.045),rgba(148,163,184,0.03))] p-6 text-slate-200 shadow-[0_24px_70px_rgba(2,6,23,0.2)] md:p-8">
                    <div className="max-w-3xl">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Data</p>
                      <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Placeholders and required inputs</h2>
                      <p className="mt-3 text-sm leading-7 text-slate-300">Prepare these variables before using the final prompt so the output stays consistent and reusable.</p>
                    </div>

                    <div className="mt-6 grid gap-5 xl:grid-cols-2">
                      {promptPlaceholders.map((placeholder, index) => (
                        <PromptPlaceholderCard key={`${placeholder.key || 'placeholder'}-${index}`} placeholder={placeholder} />
                      ))}
                    </div>
                  </section>
                ) : null}

                {showPromptHelperPrompts && hasPromptHelperPrompts ? (
                  <section className="academy-paywalled-content rounded-[32px] border border-white/10 bg-[radial-gradient(circle_at_top_left,rgba(255,183,139,0.12),transparent_30%),linear-gradient(180deg,rgba(15,23,42,0.96),rgba(2,6,23,0.92))] p-6 text-slate-200 shadow-[0_24px_80px_rgba(2,6,23,0.28)] md:p-8">
                    <div className="max-w-3xl">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffcfbf]">Data helpers</p>
                      <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white md:text-3xl">Helper prompts for preparation and validation</h2>
                      <p className="mt-3 text-sm leading-7 text-slate-300 md:text-base">Use these supporting prompts before or after the main prompt when you need better source data, cleaner structure, or a validation pass.</p>
                    </div>

                    <div className="mt-6 space-y-5">
                      {promptHelperPrompts.map((helperPrompt, index) => (
                        <PromptHelperPromptCard key={`${helperPrompt.title || 'helper'}-${index}`} helperPrompt={helperPrompt} analytics={analytics} contentId={item.id} />
                      ))}
                    </div>
                  </section>
                ) : null}

                {showPromptHelperPrompts && promptHasLockedHelperPrompts ? (
                  <section className="academy-paywalled-content rounded-[32px] border border-white/10 bg-[radial-gradient(circle_at_top_left,rgba(255,183,139,0.12),transparent_30%),linear-gradient(180deg,rgba(15,23,42,0.96),rgba(2,6,23,0.92))] p-6 text-slate-200 shadow-[0_24px_80px_rgba(2,6,23,0.28)] md:p-8">
                    <div className="max-w-3xl">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffcfbf]">Data helpers</p>
                      <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white md:text-3xl">Helper prompts are included with this template</h2>
                      <p className="mt-3 text-sm leading-7 text-slate-300 md:text-base">Data collection, validation, or refinement prompts are available once your Academy access matches this template.</p>
                    </div>
                    <div className="mt-6">
                      <LockedPanel pricingUrl={pricingUrl} label="prompt" accessLevel={item?.access_level} onUpgrade={() => trackUpgradeClick(analytics, { source: 'prompt_helper_locked_panel' })} />
                    </div>
                  </section>
                ) : null}

                {hasPromptVariants ? <PromptVariantsSection variants={promptVariants} analytics={analytics} contentId={item.id} /> : null}

                {promptHasLockedVariants ? (
                  <section className="academy-paywalled-content rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(255,255,255,0.045),rgba(148,163,184,0.03))] p-6 text-slate-200 shadow-[0_24px_70px_rgba(2,6,23,0.2)] md:p-8">
                    <div className="max-w-3xl">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Variants</p>
                      <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white">Alternative prompt versions are included</h2>
                      <p className="mt-3 text-sm leading-7 text-slate-300">This prompt includes recommended or model-specific variants, but they stay locked until your Academy access level matches the template.</p>
                    </div>
                    <div className="mt-6">
                      <LockedPanel pricingUrl={pricingUrl} label="prompt" accessLevel={item?.access_level} onUpgrade={() => trackUpgradeClick(analytics, { source: 'prompt_variant_locked_panel' })} />
                    </div>
                  </section>
                ) : null}

                {promptComparisons.length ? (
                  <section className="academy-paywalled-content rounded-[32px] border border-white/10 bg-[radial-gradient(circle_at_top_left,rgba(255,183,139,0.12),transparent_30%),linear-gradient(180deg,rgba(15,23,42,0.96),rgba(2,6,23,0.92))] p-6 text-slate-200 shadow-[0_24px_80px_rgba(2,6,23,0.28)] md:p-8">
                    <div className="max-w-3xl">
                      <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-[#ffcfbf]">AI model comparisons</p>
                      <h2 className="mt-2 text-2xl font-semibold tracking-[-0.04em] text-white md:text-3xl">How different models respond to the same prompt</h2>
                      <p className="mt-3 text-sm leading-7 text-slate-300 md:text-base">Use these notes to decide which provider fits the result you want before you start tuning or post-processing.</p>
                    </div>

                    <div className="mt-6 grid gap-5 xl:grid-cols-2">
                      {promptComparisons.map((note, index) => <PromptToolNoteCard key={`${note.provider || 'provider'}-${note.model_name || 'model'}-${index}`} note={note} index={index} galleryIndex={index} onOpenImage={openPromptComparisonGallery} />)}
                    </div>
                  </section>
                ) : null}
              </div>

              <aside className="space-y-6 lg:sticky lg:top-6 lg:self-start">
                {lessonTags.length ? (
                  <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                    <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Microtags</p>
                    <div className="mt-4 flex flex-wrap gap-2">
                      {lessonTags.map((tag) => (
                        <span key={tag} className="rounded-full border border-sky-300/20 bg-sky-300/10 px-3 py-1.5 text-xs font-semibold uppercase tracking-[0.18em] text-sky-100">{tag}</span>
                      ))}
                    </div>
                  </section>
                ) : null}

                <section className="rounded-[32px] border border-white/10 bg-[linear-gradient(180deg,rgba(15,23,42,0.92),rgba(15,23,42,0.84))] p-6 text-slate-200 shadow-[0_18px_50px_rgba(2,6,23,0.18)]">
                  <p className="text-[11px] font-semibold uppercase tracking-[0.24em] text-slate-400">Best use case</p>
                  <p className="mt-3 text-sm leading-7 text-slate-300">{promptBestUseCase}</p>
                </section>
              </aside>
            </div>
          </div>
        ) : (
          <section className="rounded-[30px] border border-white/10 bg-white/[0.04] p-6 text-slate-200">
            {pageType === 'pack' ? (
              <div className="space-y-5">
                <p className="text-sm leading-8 text-slate-200">{item.description}</p>
                <div className="grid gap-4 md:grid-cols-2">
                  {(item.prompts || []).map((prompt) => (
                    <div key={prompt.id} className="rounded-2xl border border-white/10 bg-black/20 p-4">
                      <h3 className="text-lg font-semibold text-white">{prompt.title}</h3>
                      <p className="mt-2 text-sm leading-7 text-slate-300">{prompt.excerpt || prompt.prompt_preview}</p>
                    </div>
                  ))}
                </div>
              </div>
            ) : null}
            {pageType === 'challenge' ? (
              <div className="space-y-6">
                <div className="grid gap-6 md:grid-cols-2">
                  <div>
                    <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Brief</p>
                    <div className="mt-3 whitespace-pre-wrap text-sm leading-8 text-slate-200">{item.brief || item.description}</div>
                  </div>
                  <div>
                    <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Rules</p>
                    <div className="mt-3 whitespace-pre-wrap text-sm leading-8 text-slate-200">{item.rules || 'No special rules posted yet.'}</div>
                  </div>
                </div>
                {(item.submissions || []).length ? (
                  <div>
                    <p className="text-[11px] font-semibold uppercase tracking-[0.22em] text-slate-400">Approved submissions</p>
                    <div className="mt-4 grid gap-4 md:grid-cols-2">
                      {item.submissions.map((submission) => (
                        <div key={submission.id} className="rounded-2xl border border-white/10 bg-black/20 p-4">
                          <h3 className="text-lg font-semibold text-white">{submission.artwork?.title || 'Submission'}</h3>
                          <p className="mt-2 text-sm text-slate-400">{submission.user?.name || 'Unknown creator'}</p>
                        </div>
                      ))}
                    </div>
                  </div>
                ) : null}
              </div>
            ) : null}
          </section>
        )}
      </div>

      <ImageLightbox gallery={lightboxGallery} onClose={() => setLightboxGallery(null)} onNavigate={navigateLightboxGallery} />
    </main>
  )
}