{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "agency-work",
  "title": "Agency: Selected work",
  "description": "A grid of project covers with a filter by discipline; the grid reflows on a spring.",
  "dependencies": [
    "motion"
  ],
  "registryDependencies": [
    "https://eased.dev/r/eased-tokens.json",
    "https://eased.dev/r/eased-motion.json",
    "https://eased.dev/r/agency-core.json",
    "https://eased.dev/r/segmented.json"
  ],
  "files": [
    {
      "path": "src/registry/eased/templates/agency/work.tsx",
      "content": "\"use client\";\n\nimport { AnimatePresence, motion } from \"motion/react\";\nimport { useState } from \"react\";\nimport { enter, exit, reducedFade, smooth, useSafeReducedMotion } from \"../../lib/motion\";\nimport { Segmented } from \"../../segmented/segmented\";\nimport { ClientArt } from \"./client-art\";\nimport { projects, work, type Discipline, type Project } from \"./content\";\nimport { ArrowLink, Section, useHref } from \"./kit\";\n\ntype Filter = \"All\" | Discipline;\n\n/**\n * Selected work: a filter by discipline over a grid of covers, each cover the client's site\n * drawn at card size. Filtering fades the leavers out and slides the rest into place on the\n * smooth spring; under reduced motion the grid changes at once with a fade.\n */\nexport function Work() {\n  const [filter, setFilter] = useState<Filter>(\"All\");\n  const reduced = useSafeReducedMotion();\n  const shown = filter === \"All\" ? projects : projects.filter((p) => p.disciplines.includes(filter));\n  const options = [work.all, ...work.filters].map((value) => ({ value: value as Filter, label: value }));\n\n  return (\n    <Section id=\"work\" label={work.label} className=\"flex flex-col gap-pad-lg\">\n      <div className=\"flex flex-wrap items-center justify-between gap-in\">\n        <div className=\"max-w-full overflow-x-auto [scrollbar-width:none]\">\n          <Segmented options={options} value={filter} onValueChange={setFilter} aria-label=\"Filter by discipline\" />\n        </div>\n        <ArrowLink href={work.more.href}>{work.more.label}</ArrowLink>\n      </div>\n      <ul className=\"grid gap-x-tiles gap-y-pad-lg sm:grid-cols-2 lg:grid-cols-3\">\n        <AnimatePresence initial={false} mode=\"popLayout\">\n          {shown.map((p) => (\n            <motion.li\n              key={p.id}\n              layout={!reduced}\n              initial={{ opacity: 0 }}\n              animate={{ opacity: 1 }}\n              exit={{ opacity: 0, transition: reduced ? reducedFade : exit }}\n              transition={reduced ? reducedFade : { layout: smooth, opacity: enter }}\n            >\n              <WorkCard project={p} />\n            </motion.li>\n          ))}\n        </AnimatePresence>\n      </ul>\n    </Section>\n  );\n}\n\n/** A cover and its caption; the whole card is one link (rule 59), its cover lifting a shade on hover. */\nexport function WorkCard({ project }: { project: Project }) {\n  const to = useHref();\n  return (\n    <article className=\"group relative flex flex-col gap-in\">\n      <div className=\"image-ring relative aspect-[4/3] overflow-hidden rounded-panel\">\n        <div aria-hidden className=\"absolute inset-0 transition-transform duration-(--eased-duration-fast) ease-enter group-hover-fine:scale-[1.02] reduced:transition-none\">\n          <ClientArt id={project.id} />\n        </div>\n      </div>\n      <div className=\"flex min-w-0 flex-col gap-1\">\n        <h3 className=\"text-ui-md font-medium text-text\">\n          <a href={to(`/work/${project.id}`)} className=\"focus-ring rounded-control-xs after:absolute after:inset-0 after:rounded-panel\">\n            {project.client}\n          </a>\n        </h3>\n        <p className=\"text-ui text-pretty text-text-secondary\">{project.title}</p>\n        <p className=\"text-ui-sm text-text-muted\">{project.disciplines.join(\", \")}</p>\n      </div>\n    </article>\n  );\n}\n",
      "type": "registry:component",
      "target": "@components/eased/templates/agency/work.tsx"
    }
  ],
  "meta": {
    "template": "agency",
    "kind": "template-section",
    "industries": [
      "media"
    ]
  },
  "type": "registry:block"
}