← Commit history

Publish 0.4.0

Colby Knox ·14e84337cf ·2mo ago ·parent 65b56c1
4 files changed +32−18
package.json+1−1
@@ -2,7 +2,7 @@   "slug": "hero-studio",   "title": "Hero Studio",   "type": "app",-  "version": "0.3.1",+  "version": "0.4.0",   "description": "A live playground for the hero image v2 definition: the lower third of every hero is a true-text overlay (type pill, trending score, stars, title, author, wiki slug) rendered by the surface, never baked into the image. Flip screenshot bleeds, brand tile themes, gradient angles, and title placement on real wiki trending data, and see the result in pixel-faithful wiki contexts: the homepage marquee, the index page card grid, and an adom-desktop style right bar. Includes a component-hero mode: real photo, raytraced render, or phong 3D fallback ladder, name plus spec-line hierarchy, and MPN placement options. Generate renders the posed hero server-side to a provenance-stamped 2000x1250 PNG via POST /generate.",   "license": "MIT",   "tags": [
page.json+1−1
@@ -2,7 +2,7 @@   "slug": "hero-studio",   "title": "Hero Studio",   "type": "app",-  "version": "0.3.1",+  "version": "0.4.0",   "description": "A live playground for the hero image v2 definition: the lower third of every hero is a true-text overlay (type pill, trending score, stars, title, author, wiki slug) rendered by the surface, never baked into the image. Flip screenshot bleeds, brand tile themes, gradient angles, and title placement on real wiki trending data, and see the result in pixel-faithful wiki contexts: the homepage marquee, the index page card grid, and an adom-desktop style right bar. Includes a component-hero mode: real photo, raytraced render, or phong 3D fallback ladder, name plus spec-line hierarchy, and MPN placement options. Generate renders the posed hero server-side to a provenance-stamped 2000x1250 PNG via POST /generate.",   "license": "MIT",   "tags": [
public/index.html+29−15
@@ -174,9 +174,9 @@ label.chk input { accent-color:var(--accent); width:14px; height:14px; cursor:po  /* ---------- image-zone text column ---------- */ .textzone {-  position:absolute; left:5.75cqw; top:8.5cqw; width:33cqw; z-index:3;+  position:absolute; left:6cqw; top:3.75cqw; width:37cqw; z-index:3; }-.hero[data-layout=mirror] .textzone { left:auto; right:5.75cqw; }+.hero[data-layout=mirror] .textzone { left:auto; right:6cqw; } .wordmark { display:flex; align-items:center; margin-bottom:2.2cqw; } /* the official Adom wordmark (adom-logo.svg), recolored white for dark heroes via mask */ .wordmark .wmark {@@ -185,13 +185,13 @@ label.chk input { accent-color:var(--accent); width:14px; height:14px; cursor:po           mask:url('adom-logo.svg') no-repeat left center / contain; } .h-title {-  font-family:'Familjen Grotesk'; font-weight:700; font-size:4.1cqw; line-height:1.02;+  font-family:'Familjen Grotesk'; font-weight:700; font-size:5.3cqw; line-height:1.02;   letter-spacing:-.09cqw; color:#e6edf3; margin-bottom:1.4cqw; }-.h-sub { font-size:1.42cqw; line-height:1.48; color:#aeb8c4; margin-bottom:1.1cqw; }+.h-sub { font-size:2cqw; line-height:1.48; color:#aeb8c4; margin-bottom:1.1cqw; } .h-sub .accent { background:var(--grad); -webkit-background-clip:text; background-clip:text; color:transparent; font-weight:500; } .h-sub b { color:#e6edf3; font-weight:500; }-.h-desc { font-size:1.05cqw; line-height:1.5; color:#8b949e; max-width:30cqw; }+.h-desc { font-size:1.35cqw; line-height:1.5; color:#8b949e; max-width:30cqw; }  /* ---------- the app-window mock (the "screenshot") ---------- */ .window {@@ -200,13 +200,13 @@ label.chk input { accent-color:var(--accent); width:14px; height:14px; cursor:po   box-shadow:0 1.7cqw 5cqw rgba(0,0,0,.62), 0 0 8cqw rgba(0,184,177,.07);   display:flex; flex-direction:column; }-.hero[data-layout=bleed-bottom] .window { right:4.5cqw; top:10cqw; width:52cqw; height:56cqw; }-.hero[data-layout=bleed-right] .window { right:-8cqw; top:9cqw; width:56cqw; height:44cqw; border-radius:.9cqw 0 0 .9cqw; }+.hero[data-layout=bleed-bottom] .window { right:4.5cqw; top:6cqw; width:56cqw; height:64cqw; }+.hero[data-layout=bleed-right] .window { right:-8cqw; top:6cqw; width:56cqw; height:44cqw; border-radius:.9cqw 0 0 .9cqw; } .hero[data-layout=bleed-top] .window { right:4.5cqw; top:-6cqw; width:52cqw; height:42cqw; border-radius:0 0 .9cqw .9cqw; } .hero[data-layout=bleed-corner-br] .window { right:-7cqw; top:14cqw; width:56cqw; height:52cqw; border-radius:.9cqw 0 0 0; } .hero[data-layout=bleed-corner-tr] .window { right:-7cqw; top:-6cqw; width:56cqw; height:44cqw; border-radius:0 0 0 .9cqw; }-.hero[data-layout=contained] .window { right:4.5cqw; top:8cqw; width:50cqw; height:33cqw; border-radius:.9cqw; }-.hero[data-layout=mirror] .window { left:4.5cqw; top:10cqw; width:52cqw; height:56cqw; }+.hero[data-layout=contained] .window { right:4.5cqw; top:6cqw; width:50cqw; height:33cqw; border-radius:.9cqw; }+.hero[data-layout=mirror] .window { left:4.5cqw; top:6cqw; width:56cqw; height:64cqw; } .titlebar {   flex:0 0 2.1cqw; background:#181f28; border-bottom:1px solid rgba(255,255,255,.06);   display:flex; align-items:center; padding:0 .9cqw; gap:.6cqw;@@ -283,14 +283,14 @@ body[data-mode=component] .mode-app { display:none; }   -webkit-mask-image:linear-gradient(270deg, transparent 0, #000 26%);           mask-image:linear-gradient(270deg, transparent 0, #000 26%); }-.hero[data-clayout=photo-left] .ctextzone { left:auto; right:5.75cqw; }+.hero[data-clayout=photo-left] .ctextzone { left:auto; right:6cqw; } .hero[data-clayout=photo-full] .comp-side { left:0; width:100%; } .hero[data-clayout=photo-full] .comp-img { -webkit-mask-image:none; mask-image:none; } .hero[data-clayout=photo-full] .comp-img::after {   content:''; position:absolute; inset:0;   background:linear-gradient(90deg, rgba(10,14,20,.88), rgba(10,14,20,.3) 55%, rgba(10,14,20,.12)); }-.ctextzone { position:absolute; left:5.75cqw; top:8.5cqw; width:36cqw; z-index:3; }+.ctextzone { position:absolute; left:6cqw; top:3.75cqw; width:37cqw; z-index:3; } .c-chips { display:flex; gap:.8cqw; margin-bottom:2cqw; flex-wrap:wrap; } .c-family {   display:inline-block; font-family:'JetBrains Mono',monospace; font-size:.9cqw; letter-spacing:.12em;@@ -298,9 +298,9 @@ body[data-mode=component] .mode-app { display:none; }   border-radius:999px; padding:.35cqw 1cqw; text-transform:uppercase; } .c-mpnchip { color:#aeb8c4; border-color:rgba(255,255,255,.16); display:none; }-.c-name { font-family:'Familjen Grotesk'; font-weight:700; font-size:4.2cqw; line-height:1.02; letter-spacing:-.08cqw; color:#e6edf3; margin-bottom:.9cqw; text-shadow:0 2px 12px rgba(0,0,0,.5); }+.c-name { font-family:'Familjen Grotesk'; font-weight:700; font-size:5.5cqw; line-height:1.02; letter-spacing:-.08cqw; color:#e6edf3; margin-bottom:.9cqw; text-shadow:0 2px 12px rgba(0,0,0,.5); } .c-mpn { font-family:'JetBrains Mono',monospace; font-size:1.05cqw; color:#8b949e; margin-bottom:1cqw; display:none; }-.c-spec { font-size:1.5cqw; color:#aeb8c4; line-height:1.45; max-width:30cqw; text-shadow:0 1px 8px rgba(0,0,0,.5); }+.c-spec { font-size:2cqw; color:#aeb8c4; line-height:1.45; max-width:30cqw; text-shadow:0 1px 8px rgba(0,0,0,.5); } .hero[data-mpn=eyebrow] .c-mpnchip { display:inline-block; } .hero[data-mpn=under-title] .c-mpn { display:block; } .hero[data-mpn=overlay] .l-mpn { display:block; }@@ -374,6 +374,17 @@ body[data-mode=component] .mode-app { display:none; } .deskmock { background:var(--surface); border:1px solid var(--border); border-radius:10px; padding:10px; display:flex; flex-direction:column; gap:10px; } .deskhead { font-family:'Familjen Grotesk'; font-weight:500; font-size:11px; letter-spacing:.07em; text-transform:uppercase; color:var(--text-2); } +/* other owners never get the Adom mark: dashed placeholder for their own logo */+.wordmark.noadom .wmark {+  -webkit-mask:none; mask:none; background:transparent;+  border:1.5px dashed rgba(255,255,255,.28); border-radius:.4cqw;+  display:flex; align-items:center; justify-content:center;+}+.wordmark.noadom .wmark::after {+  content:'YOUR LOGO'; font-family:'Familjen Grotesk'; font-weight:700;+  font-size:.8cqw; letter-spacing:.2em; color:rgba(255,255,255,.4);+}+ /* render mode: ?render=1 strips all chrome for the server-side PNG shot */ body[data-render] header, body[data-render] #panel, body[data-render] #contexts, body[data-render] #toasts, body[data-render] .guide { display:none !important; }@@ -511,7 +522,7 @@ body[data-render] #hero { width:1600px; max-width:none; aspect-ratio:auto; heigh       <button class="opt" data-v="image-only">Image only</button>       <button class="opt" data-v="both">Both</button>     </div>-    <div class="hint">John's open question: if the big title lives in the image, the overlay title is redundant. Flip these to compare.</div>+    <div class="hint">Resolved per John: the title lives in the IMAGE; the overlay carries only dynamic data (pills, scores, url). Image only is the default; the others remain for comparison.</div>     </div>      <h3>Overlay content</h3>@@ -720,6 +731,9 @@ function render() {     : d.type + ' · score ' + d.score + ' · ' + d.stars + ' stars · ' + d.installs30d + ' installs/30d';   $('btn-guides').classList.toggle('on', !!state.guides); +  // Adom branding only on adom-owned pages; everyone else gets the placeholder+  document.querySelectorAll('#hero .wordmark').forEach(w => w.classList.toggle('noadom', d.owner !== 'adom'));+   // component image zone   if (mode === 'component' && comps.length) {     const c = compById(state.comp.id);@@ -944,7 +958,7 @@ $('btn-generate').addEventListener('click', () => { });  $('btn-reset').addEventListener('click', () => {-  send({ mode:'app', layout:'bleed-bottom', theme:'midnight', titleMode:'overlay-only', gradAngle:155,+  send({ mode:'app', layout:'bleed-bottom', theme:'midnight', titleMode:'image-only', gradAngle:155,     comp:{ id:'sm02b-srss-tb', imgSrc:'photo', layout:'photo-right', mpn:'under-title' },     show:{ logo:true, title:true, subtitle:true, description:false },     overlay:{ pill:true, scores:true, author:true, slug:true }, guides:true });
server.js+1−1
@@ -16,7 +16,7 @@ let state = {   layout: 'bleed-bottom',   // bleed-bottom | bleed-right | bleed-top | bleed-corner-br | bleed-corner-tr | contained | mirror   theme: 'midnight',        // midnight | pcb | onion | pill | gradient   show: { logo: true, title: true, subtitle: true, description: false },-  titleMode: 'overlay-only', // overlay-only | image-only | both+  titleMode: 'image-only', // overlay-only | image-only | both; image-only per John: the overlay is dynamic data, not a second title   overlay: { pill: true, scores: true, author: true, slug: true },   gradAngle: 155,   guides: true,