<div className="grid sm:grid-cols-2 lg:grid-cols-3 gap-4">
        {LIBRARY.map(item => {
          const sel = !!selected[item.id];
          const colA = overrides[item.id]?.a || accents[item.colorAIdx ?? 0] || accents[0];
          const colB = overrides[item.id]?.b || accents[item.colorBIdx ?? 2] || accents[2];
          return (
            <div key={item.id} className={`rounded-xl border ${sel ? "border-sky-500/50 bg-sky-500/5" : "border-white/10 bg-slate-900/60"} p-4`}>
              <div className="flex items-start justify-between">
                <div>
                  <div className="font-medium">{item.name}</div>
                  <div className="text-xs text-slate-400">{item.count} sections</div>
                </div>
                <label className="inline-flex items-center gap-2 text-sm">
                  <input type="checkbox" checked={sel} onChange={()=>toggle(item.id)} className="accent-sky-500"/>
                  Select
                </label>
              </div>

              <div className="mt-3 rounded-lg overflow-hidden border border-white/10 bg-white">
                <div className="aspect-video">
                  <Preview layout={item.layout} count={item.count} colorA={colA} colorB={colB}/>
                </div>
              </div>

              <div className="mt-3 grid grid-cols-2 gap-2">
                <label className="flex items-center gap-2 text-xs">
                  <input type="color" value={colA} onChange={(e)=>setColor(item.id,"a", e.target.value)} />
                  <span>Primary</span>
                </label>
                <label className="flex items-center gap-2 text-xs">
                  <input type="color" value={colB} onChange={(e)=>setColor(item.id,"b", e.target.value)} />
                  <span>Secondary</span>
                </label>
              </div>

              <div className="mt-3 flex items-center justify-between">
                <button onClick={()=>quickDownload(item)} className="px-3 py-1.5 rounded-lg border border-white/10 hover:bg-white/5 text-sm">
                  Quick Download
                </button>
                <span className="text-xs text-slate-400">Editable in PPT</span>
              </div>
            </div>
          );
        })}
      </div>
    </div>
  );
}
2) Navigation (if you already mounted “Infographics”, you’re done)
If not, add to routes.tsx (was done earlier):

tsx
Copy code
const Infographics = React.lazy(() => import("./pages/business-assets/templates/Infographics"));
{ label: "Infographics", path: "/business-assets/templates/infographics", icon: <GitBranch className="w-4 h-4" /> },
{ path: "/business-assets/templates/infographics", element: <Infographics /> },
3) Presentation Template export already works
The “Add Selected to Template” button saves entries to pt.infographicsDetailed, and your Presentation Template → Generate already merges those into the PPTX via the detailed renderer we wired.

How this matches your vision
Library, not forms: users pick pages from ready-made designs.

Lightweight edits: only colors (Primary/Secondary) at pick time; text stays editable later in PPT (or you can keep defaults).

Fast previews: inline SVG schematics (no backend calls).

One click handoff: Add Selected to Template batches these into the deck generator.