home3: small-joys rail -> rotating two-up shelf (option A: label + dots + arrows)
Two jewel cards at a time, reader-advanced (no auto-motion); 3 cells total, wraps. Keeps each card at generous size instead of cramming three. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -17,6 +17,12 @@
|
||||
}
|
||||
let headline = $derived(clampWords(news?.title ?? 'What went right this week: the good news that actually matters'));
|
||||
|
||||
// small-joys shelf: 3 cells shown two at a time, rotated by the reader (no auto-motion)
|
||||
const JOY_ACCENTS = ['#D2861B', '#8857C2', '#3F9A66'];
|
||||
let joyIdx = $state(0);
|
||||
const prevJoy = () => (joyIdx = (joyIdx + 2) % 3);
|
||||
const nextJoy = () => (joyIdx = (joyIdx + 1) % 3);
|
||||
|
||||
onMount(async () => {
|
||||
try {
|
||||
const a = await getJSON('/api/art/today');
|
||||
@@ -42,6 +48,40 @@
|
||||
<meta name="description" content="A calmer, brighter corner of the internet: good news, daily art, small games, and little resets." />
|
||||
</svelte:head>
|
||||
|
||||
{#snippet joyCard(i)}
|
||||
{#if i === 0}
|
||||
<div class="joy joy-word">
|
||||
<span class="wm" aria-hidden="true">S</span>
|
||||
<div class="joy-in">
|
||||
<div class="tag"><span class="rule"></span><span class="tag-label">Word of the day</span></div>
|
||||
<p class="word-line"><span class="word">Serene</span> <span class="word-pos">adj.</span></p>
|
||||
<p class="word-pron">/səˈriːn/</p>
|
||||
<p class="def">Calm, peaceful, and untroubled. The quiet after a storm passes.</p>
|
||||
</div>
|
||||
</div>
|
||||
{:else if i === 1}
|
||||
<div class="joy joy-quote">
|
||||
<span class="wm wm-q" aria-hidden="true">“</span>
|
||||
<div class="joy-in">
|
||||
<div class="tag"><span class="rule"></span><span class="tag-label">Quote of the day</span></div>
|
||||
<p class="quote">Very little is needed to make a happy life.</p>
|
||||
<div class="attrib"><span class="attrib-rule"></span><span class="attrib-by">Marcus Aurelius</span></div>
|
||||
</div>
|
||||
</div>
|
||||
{:else}
|
||||
<div class="joy joy-fact">
|
||||
<div class="joy-in">
|
||||
<div class="joy-top">
|
||||
<div class="tag"><span class="rule"></span><span class="tag-label">A good thing today</span></div>
|
||||
<span class="soon">SOON</span>
|
||||
</div>
|
||||
<p class="fact-hero"><span class="year">1928</span> <span class="onthis">ON THIS DAY</span></p>
|
||||
<p class="fact">Penicillin was discovered by a happy accident.</p>
|
||||
</div>
|
||||
</div>
|
||||
{/if}
|
||||
{/snippet}
|
||||
|
||||
<div class="page">
|
||||
<header class="bar">
|
||||
<a class="brand" href="/home3" aria-label="upbeatBytes home">
|
||||
@@ -145,35 +185,26 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- "small joys" rail — little jewels: focal point + watermark + tag + soft gradient -->
|
||||
<div class="joys">
|
||||
<div class="joy joy-word">
|
||||
<span class="wm" aria-hidden="true">S</span>
|
||||
<div class="joy-in">
|
||||
<div class="tag"><span class="rule"></span><span class="tag-label">Word of the day</span></div>
|
||||
<p class="word-line"><span class="word">Serene</span> <span class="word-pos">adj.</span></p>
|
||||
<p class="word-pron">/səˈriːn/</p>
|
||||
<p class="def">Calm, peaceful, and untroubled. The quiet after a storm passes.</p>
|
||||
</div>
|
||||
</div>
|
||||
<div class="joy joy-quote">
|
||||
<span class="wm wm-q" aria-hidden="true">“</span>
|
||||
<div class="joy-in">
|
||||
<div class="tag"><span class="rule"></span><span class="tag-label">Quote of the day</span></div>
|
||||
<p class="quote">Very little is needed to make a happy life.</p>
|
||||
<div class="attrib"><span class="attrib-rule"></span><span class="attrib-by">Marcus Aurelius</span></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="joy joy-fact">
|
||||
<div class="joy-in">
|
||||
<div class="joy-top">
|
||||
<div class="tag"><span class="rule"></span><span class="tag-label">A good thing today</span></div>
|
||||
<span class="soon">SOON</span>
|
||||
<!-- "small joys" — two jewels at a time, rotated by the reader (3 cells total) -->
|
||||
<div class="joys-shelf">
|
||||
<div class="joys-head">
|
||||
<div class="joys-title"><span class="jt-label">Small joys for today</span><span class="jt-count">· {joyIdx + 1} of 3</span></div>
|
||||
<div class="joys-nav">
|
||||
<div class="joys-dots" aria-hidden="true">
|
||||
{#each [0, 1, 2] as d}
|
||||
<span class="dot" class:on={d === joyIdx} style={d === joyIdx ? `background:${JOY_ACCENTS[joyIdx]}` : ''}></span>
|
||||
{/each}
|
||||
</div>
|
||||
<div class="joys-arrows">
|
||||
<button class="arrow" onclick={prevJoy} aria-label="Previous small joys">‹</button>
|
||||
<button class="arrow" onclick={nextJoy} aria-label="More small joys">›</button>
|
||||
</div>
|
||||
<p class="fact-hero"><span class="year">1928</span> <span class="onthis">ON THIS DAY</span></p>
|
||||
<p class="fact">Penicillin was discovered by a happy accident.</p>
|
||||
</div>
|
||||
</div>
|
||||
<div class="joys">
|
||||
{@render joyCard(joyIdx)}
|
||||
{@render joyCard((joyIdx + 1) % 3)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
@@ -327,7 +358,23 @@
|
||||
|
||||
/* "small joys" rail — little jewels: one big focal point per card, a faint oversized
|
||||
watermark glyph, an accent-tag label, soft diagonal gradient + long low shadow. */
|
||||
.joys { flex: none; display: grid; grid-template-columns: 1fr 1fr 1fr; gap: 16px; }
|
||||
.joys-shelf { flex: none; }
|
||||
.joys-head { display: flex; align-items: center; justify-content: space-between; margin-bottom: 12px; }
|
||||
.joys-title { display: flex; align-items: baseline; gap: 8px; }
|
||||
.jt-label { font-family: 'Newsreader', Georgia, serif; font-style: italic; font-size: 17px; color: #7a6f5b; }
|
||||
.jt-count { font-size: 12px; color: #b3a890; }
|
||||
.joys-nav { display: flex; align-items: center; gap: 14px; }
|
||||
.joys-dots { display: flex; align-items: center; gap: 6px; }
|
||||
.dot { width: 6px; height: 6px; border-radius: 50%; background: #d9cdb8; transition: width 0.2s ease, background 0.2s ease; }
|
||||
.dot.on { width: 18px; border-radius: 3px; }
|
||||
.joys-arrows { display: flex; gap: 8px; }
|
||||
.arrow {
|
||||
width: 30px; height: 30px; border-radius: 50%; border: 1px solid #e0d3b8; background: transparent;
|
||||
color: #b09a6e; font-size: 14px; cursor: pointer; display: flex; align-items: center; justify-content: center;
|
||||
padding: 0; line-height: 1; transition: background 0.15s ease, color 0.15s ease;
|
||||
}
|
||||
.arrow:hover { background: #fff; color: #9a7b3e; }
|
||||
.joys { display: grid; grid-template-columns: 1fr 1fr; gap: 16px; }
|
||||
.joy { position: relative; overflow: hidden; border-radius: 20px; padding: 22px 24px; }
|
||||
.joy-in { position: relative; } /* content sits above the watermark */
|
||||
.wm { position: absolute; font-family: 'Newsreader', Georgia, serif; line-height: 1; pointer-events: none; }
|
||||
|
||||
Reference in New Issue
Block a user