[object Object]

← back to Cncp Failures Mockups

cncp mockups: make entire card clickable to open variant + new-tab link · keyboard navigable

71f59dd52f98d35ca18b84bd1d48940d4df059c5 · 2026-05-11 16:34:53 -0700 · Steve

Files touched

Diff

commit 71f59dd52f98d35ca18b84bd1d48940d4df059c5
Author: Steve <steve@designerwallcoverings.com>
Date:   Mon May 11 16:34:53 2026 -0700

    cncp mockups: make entire card clickable to open variant + new-tab link · keyboard navigable
---
 public/index.html | 18 +++++++++++++++---
 1 file changed, 15 insertions(+), 3 deletions(-)

diff --git a/public/index.html b/public/index.html
index 677fd43..12a9fa1 100644
--- a/public/index.html
+++ b/public/index.html
@@ -11,8 +11,10 @@
   .ctrl-btn:hover { background:#1f2535; }
   .ctrl-btn.active { background:var(--accent); border-color:var(--accent); color:#fff; }
   .grid { display:grid; grid-template-columns:repeat(auto-fill,minmax(440px,1fr)); gap:18px; padding:18px 32px 60px; max-width:1280px; margin:0 auto; }
-  .card { background:var(--panel); border:1px solid var(--border); border-radius:10px; overflow:hidden; display:flex; flex-direction:column; transition: transform 0.15s, border-color 0.15s; }
+  .card { background:var(--panel); border:1px solid var(--border); border-radius:10px; overflow:hidden; display:flex; flex-direction:column; transition: transform 0.15s, border-color 0.15s; cursor:pointer; }
   .card:hover { transform:translateY(-2px); border-color:var(--accent); }
+  .card:hover .preview::after { background:rgba(124,58,237,0.08); }
+  .card .preview::after { content:''; position:absolute; inset:0; background:transparent; transition:background 0.15s; pointer-events:none; }
   .card .preview { aspect-ratio: 16/10; width:100%; background:#000; border-bottom:1px solid var(--border); overflow:hidden; position:relative; }
   .card iframe { width:200%; height:200%; transform-origin: 0 0; transform: scale(0.5); border:none; pointer-events:none; }
   .card .info { padding:12px 14px 14px; }
@@ -65,14 +67,24 @@ const variants = [
 function renderGrid(mode) {
   const q = mode === 'seed' ? '?seed=1' : '';
   document.getElementById('grid').innerHTML = variants.map((v, i) => `
-    <div class="card">
+    <div class="card" onclick="openFull(${i})" role="link" tabindex="0" aria-label="Open ${v.title}" data-variant-id="${v.id}">
       <div class="preview"><iframe src="${v.id}.html${q}#nocache=${Date.now()}" loading="lazy"></iframe></div>
       <div class="info">
         <h3>${v.title}</h3>
         <div class="desc">${v.desc}</div>
-        <a href="${v.id}.html${q}" class="open" onclick="event.preventDefault(); openFull(${i})">Open full-screen →</a>
+        <a href="${v.id}.html${q}" class="open" onclick="event.stopPropagation(); event.preventDefault(); openFull(${i})">Open full-screen →</a>
+        <a href="${v.id}.html${q}" class="open" style="margin-left:8px" onclick="event.stopPropagation()" target="_blank" rel="noopener">Open in new tab ↗</a>
       </div>
     </div>`).join('');
+  // Enter/Space on a focused card opens it
+  document.getElementById('grid').addEventListener('keydown', function(e) {
+    if (e.key !== 'Enter' && e.key !== ' ') return;
+    const card = e.target.closest('.card');
+    if (!card) return;
+    e.preventDefault();
+    const idx = Array.prototype.indexOf.call(card.parentNode.children, card);
+    openFull(idx);
+  });
 }
 
 let _mode = 'live';

← e689769 v7 voices = per-band ElevenLabs stock voices (no pitch-shift  ·  back to Cncp Failures Mockups  ·  gitignore: protect .env* from accidental commits per MEMORY c2c9b1a →