From 1ca77a5999bc546f92ec7189acfba1dc8088a2a7 Mon Sep 17 00:00:00 2001 From: Adam Soltys Date: Sat, 12 Sep 2026 09:52:06 -0700 Subject: Every answer to a post lives in one row beneath it. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reply and zap have come down from the header to join boost, quote and the heart, spread across the post's full width so each is a comfortable target instead of five buttons huddled in a corner. Only the ellipsis stays up top. Proper icons at a readable size, all the same weight: a speech bubble for reply (a return arrow is what a keyboard does, not what a person does), the repeat arrows for boost, quote marks, a heart, a bolt. Counts sit beside the icon they count. And the heart asks which feeling: tapping it opens the same six emoji the chat sheet offers, and the one you pick is the one the post then shows — NIP-25 takes any content, so there was never a reason to assume a heart. Tapping your own reaction still takes it back. Co-Authored-By: Claude Opus 5 (1M context) Claude-Session: https://claude.ai/code/session_019mrt228Upn9nNCwGixzSLx --- tools/post-actions-test.js | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) (limited to 'tools') diff --git a/tools/post-actions-test.js b/tools/post-actions-test.js index c1126ef..e6d6c9f 100644 --- a/tools/post-actions-test.js +++ b/tools/post-actions-test.js @@ -61,14 +61,19 @@ try { await sleep(2500); const acts = await page.evaluate(() => [...document.querySelectorAll('.note-act')].map((b) => b.getAttribute('aria-label'))); - check('a post carries like, boost and quote', acts.join(',') === 'Like,Boost,Quote', acts.join(',') || 'none'); + check('every action sits under the post', acts.slice(0, 4).join(',') === 'Reply,Boost,Quote,Like', acts.join(',') || 'none'); - // a like paints before any relay answers, and counts itself - const before = await page.evaluate(() => Number(document.querySelector('.note-act').textContent.replace(/\D/g, '') || 0)); - await page.evaluate(() => document.querySelector('.note-act').click()); - await sleep(900); - const liked = await page.evaluate(() => { const b = document.querySelector('.note-act'); return { on: b.className.includes('on'), n: Number(b.textContent.replace(/\D/g, '') || 0) }; }); - check('liking shows immediately, with a count', liked.on && liked.n === before + 1, JSON.stringify(liked) + ' was ' + before); + // the heart opens the emoji row; picking one paints before any relay answers + const likeBtn = () => page.evaluate(() => { const b = [...document.querySelectorAll('.note-act')].find((x) => x.getAttribute('aria-label') === 'Like'); return b ? { on: b.className.includes('on'), n: Number(b.textContent.replace(/\D/g, '') || 0), emoji: b.textContent.replace(/[\d\s]/g, '') } : null; }); + const before = (await likeBtn()).n; + await page.evaluate(() => { const b = [...document.querySelectorAll('.note-act')].find((x) => x.getAttribute('aria-label') === 'Like'); b.click(); }); + await sleep(600); + const emojis = await page.evaluate(() => [...document.querySelectorAll('.msg-sheet-emojis button')].map((b) => b.textContent)); + check('the heart offers a choice of emoji', emojis.length >= 5, emojis.join(' ')); + await page.evaluate(() => { const b = [...document.querySelectorAll('.msg-sheet-emojis button')].find((x) => x.textContent === '🔥'); b.click(); }); + await sleep(1200); + const liked = await likeBtn(); + check('the one you picked is the one it shows', liked.on && liked.n === before + 1 && liked.emoji.includes('🔥'), JSON.stringify(liked) + ' was ' + before); // quoting carries the post into the composer as a nostr: reference await page.evaluate(() => { const b = [...document.querySelectorAll('.note-act')].find((x) => x.getAttribute('aria-label') === 'Quote'); b.click(); }); -- cgit v1.2.3