Featured to top, centered, capped; banner ads capped 728px centered; slot CTA

- Featured card moved to the top of Overview, centered, max 760px; the rotating
  link is capped to 728px and centered (banner-sized, not a huge block).
- Served banner creatives cap at min(100%,728px), centered — kills the oversized
  sample banner; ad slots center their creative + label.
- Featured self-sell: shows "N of C slots open today" + "Feature your link →"
  that jumps to Campaigns with Featured preselected.
- Campaign target/image/video URL fields get autocomplete=off and clear when the
  Campaigns pane opens, so no residual (e.g. massifly) URL carries over.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
martbost
2026-09-07 08:08:47 -05:00
parent 3a6d9d037c
commit bc95965814
9 changed files with 34 additions and 17 deletions
+13
View File
@@ -46,6 +46,18 @@
renderOneFeatured(); // show ONE at a time (true rotation), cycle if more than one
clearInterval(featTimer);
if (featItems.length > 1) featTimer = setInterval(() => { featIdx++; renderOneFeatured(); }, 6000);
// self-sell: today's open slots + a CTA to feature your own link
try {
const st = await (await fetch('/api/featured/stats')).json();
const today = (st.occupancy || []).find(d => d.offset === 0);
const cta = $('featCta');
if (cta) {
cta.innerHTML = (today ? '<span class="muted">' + today.open + ' of ' + today.cap + ' featured slots open today. </span>' : '')
+ '<a href="#campaigns" id="featBuy" style="color:var(--mint);font-weight:700;text-decoration:none">Feature your link →</a>';
const fb = $('featBuy');
if (fb) fb.addEventListener('click', e => { e.preventDefault(); setPane('campaigns'); const ct = $('cType'); if (ct) { ct.value = 'featured'; ct.dispatchEvent(new Event('change')); } });
}
} catch (e) {}
} catch (e) {}
}
@@ -376,6 +388,7 @@
if (name === 'earn') setEarnSub(earnSub); // refresh whichever sub-tab is active
if (name === 'profile') loadLineBanner();
if (name === 'line') { loadLineage(); loadUplineMessages(); }
if (name === 'campaigns') ['cTarget', 'cImage', 'cVideoUrl'].forEach(id => { if ($(id)) $(id).value = ''; }); // no residual URL between visits
document.getElementById('memberArea').classList.remove('side-open'); // close mobile drawer
if (location.hash !== '#' + name) history.replaceState(null, '', '#' + name);
}