From 83bac1978fd66e9062383c50584b54fa0d055a8f Mon Sep 17 00:00:00 2001 From: Nish <257724087+nish3451@users.noreply.github.com> Date: Fri, 14 Aug 2026 13:56:37 +0530 Subject: [PATCH 1/2] fix(public): keep product hero early-access CTA in the first mobile viewport The Promptly and Drishti hero H1s render at 7vw with a 9ch cap, so on 320-414px phones the heading alone was ~540px tall and pushed the newly added "Get early access" button below the fold (~1035px+ on a 844px viewport), under the long lead paragraph. Bring the CTA up by: - scaling .page-hero-card h1 down on mobile (clamp 2.1-3.4rem, no ch cap) so the heading no longer consumes over half the viewport - moving the hero action-row above the page-lead in both product pages, so the CTA is the first thing after the heading on narrow screens The two-column desktop hero layout is unchanged. Extend the existing 320/390px Playwright layout probe to assert the early-access CTA is fully within the first viewport on both pages, so the burying cannot regress. Co-authored-by: CommandCodeBot --- public/drishti/index.html | 10 ++++----- public/promptly/index.html | 10 ++++----- public/styles.css | 5 +++++ scripts/test-public-heading-hierarchy.mjs | 27 ++++++++++++++++++++++- 4 files changed, 41 insertions(+), 11 deletions(-) diff --git a/public/drishti/index.html b/public/drishti/index.html index 9ef4bf15..00a3c008 100644 --- a/public/drishti/index.html +++ b/public/drishti/index.html @@ -104,17 +104,17 @@

Drishti

Mindful pause before distraction

Drishti helps bring awareness to screen time before distraction takes over.

+
+ Get early access + Drishti support + Drishti privacy +

Drishti is a mindful screen-time app built around intentional pauses. When you try to open a distracting app, it creates a moment to breathe, check your intention, and choose with more awareness instead of running on autopilot.

-
- Get early access - Drishti support - Drishti privacy -
iPhone app Mindful screen time diff --git a/public/promptly/index.html b/public/promptly/index.html index c151f290..88220e9a 100644 --- a/public/promptly/index.html +++ b/public/promptly/index.html @@ -104,17 +104,17 @@

Promptly

Booking + no-show prevention

Promptly keeps solo professionals booked, prepared, and harder to ghost.

+

Promptly is the mobile control room for solo professionals. It brings bookings, reminders, payment proof, and day-of clarity into one focused workflow, while clients simply open links to book, confirm, reschedule, or cancel.

-
iPhone app Reminder windows: 24h, 2h, 30min diff --git a/public/styles.css b/public/styles.css index 7c825fc5..c74298f1 100644 --- a/public/styles.css +++ b/public/styles.css @@ -877,6 +877,11 @@ h4 { max-width: 9ch; } + .page-hero-card h1 { + font-size: clamp(2.1rem, 5.6vw, 3.4rem); + max-width: none; + } + .product-row, .portfolio-row { grid-template-columns: 1fr; diff --git a/scripts/test-public-heading-hierarchy.mjs b/scripts/test-public-heading-hierarchy.mjs index 01c8b0e4..58fe70e0 100644 --- a/scripts/test-public-heading-hierarchy.mjs +++ b/scripts/test-public-heading-hierarchy.mjs @@ -215,6 +215,8 @@ const measurePage = async (chromium, origin, path, width) => { const response = await page.goto(`${origin}${path}`, { waitUntil: "domcontentloaded" }) const metrics = await page.evaluate(() => { const heading = document.querySelector("h1") + const cta = document.querySelector('.action-row a.button[href^="mailto:"]') + const ctaRect = cta ? cta.getBoundingClientRect() : null return { heading: heading ? heading.innerText.replace(/\s+/g, " ").trim() : "", scrollWidth: document.documentElement.scrollWidth, @@ -222,7 +224,11 @@ const measurePage = async (chromium, origin, path, width) => { headingScrollWidth: heading ? heading.scrollWidth : 0, headingClientWidth: heading ? heading.clientWidth : 0, overflowWrap: heading ? getComputedStyle(heading).overflowWrap : "", - overflowX: getComputedStyle(document.documentElement).overflowX + overflowX: getComputedStyle(document.documentElement).overflowX, + ctaVisible: cta ? ctaRect.top < innerHeight && ctaRect.bottom >= 0 : false, + ctaTop: ctaRect ? ctaRect.top : -1, + ctaBottom: ctaRect ? ctaRect.bottom : -1, + ctaText: cta ? cta.innerText.replace(/\s+/g, " ").trim() : "" } }) return { status: response?.status() ?? 0, ...metrics } @@ -270,6 +276,14 @@ if (!chromiumLauncher) { promptly320.overflowX !== "hidden" && promptly390.overflowX !== "hidden", "document overflow-x is not hidden" ) + ok( + promptly320.ctaVisible && promptly390.ctaVisible, + "Promptly early-access CTA is fully within the first mobile viewport" + ) + ok( + promptly320.ctaText === "Get early access" && promptly390.ctaText === "Get early access", + `Promptly early-access CTA copy is unchanged (got "${promptly320.ctaText}" at 320)` + ) for (const path of ["/", "/drishti/"]) { const sibling = await measurePage(browser, origin, path, 320) @@ -282,6 +296,17 @@ if (!chromiumLauncher) { sibling.headingScrollWidth <= sibling.headingClientWidth, `${path} heading stays inside its box at 320 (${sibling.headingScrollWidth} <= ${sibling.headingClientWidth})` ) + if (path === "/drishti/") { + const drishti390 = await measurePage(browser, origin, "/drishti/", 390) + ok( + drishti390.ctaVisible, + "Drishti early-access CTA is fully within the first mobile viewport" + ) + ok( + drishti390.ctaText === "Get early access", + `Drishti early-access CTA copy is unchanged (got "${drishti390.ctaText}" at 390)` + ) + } } } finally { await browser.close() From c20258ec6b34ec308c012ae8f24a91bda6ec9d1d Mon Sep 17 00:00:00 2001 From: Nish <257724087+nish3451@users.noreply.github.com> Date: Fri, 14 Aug 2026 13:57:02 +0530 Subject: [PATCH 2/2] docs(lane1): record CTA viewport fix report Co-authored-by: CommandCodeBot --- ...ix-product-hero-early-access-cta-mobile.md | 31 +++++++++++++++++++ 1 file changed, 31 insertions(+) create mode 100644 .lane/reports/fix-product-hero-early-access-cta-mobile.md diff --git a/.lane/reports/fix-product-hero-early-access-cta-mobile.md b/.lane/reports/fix-product-hero-early-access-cta-mobile.md new file mode 100644 index 00000000..97606e79 --- /dev/null +++ b/.lane/reports/fix-product-hero-early-access-cta-mobile.md @@ -0,0 +1,31 @@ +# Lane report: tinystudio-in lane 1 — product hero CTA buried below mobile fold + +## Item +[unreviewed-by-opus] Promptly and Drishti mobile heroes bury the newly added Get early access CTA below the first [viewport] + +## Root cause +Shared `h1` rule: `font-size: clamp(3.4rem, 7vw, 6.7rem)` + mobile `max-width: 9ch`. At 320–414px the 7vw font with a 9ch cap made the long product hero H1s ~544px tall (over half an 844px viewport), and with the action-row after the long page-lead in DOM order, the CTA bottom landed at ~1035–1191px — below the fold everywhere, including desktop 1024px. + +Measured before (Playwright, 844px viewport): Promptly CTA bottom 1083px @390; Drishti 1164px @390. + +## Fix (PR #147) +1. `public/styles.css` — mobile-only `.page-hero-card h1 { font-size: clamp(2.1rem, 5.6vw, 3.4rem); max-width: none; }` inside the existing `@media (max-width: 720px)` block. Homepage untouched; desktop floor (3.4rem) preserved. +2. `public/promptly/index.html`, `public/drishti/index.html` — moved the hero `.action-row` above `.page-lead` so the CTA is first after the H1 on narrow screens. Desktop two-column layout unaffected. +3. `scripts/test-public-heading-hierarchy.mjs` — extended the existing 320/390px Playwright layout probe to assert the early-access CTA is fully within the first viewport on both pages (fails closed when Playwright is missing). + +## Verification +- Playwright before/after, all mobile widths (320/360/390/414) and heights (667/740/844): CTA fully in-fold after; at 320×667 it now sits at 536–584px top/bottom (was ~1035–1083+). +- Hero H1 height at 320px: 544px -> 202px. +- `test-public-heading-hierarchy.mjs`: 93 checks, 0 failures (includes new CTA assertions, rendered at 320 and 390). +- All 10 public-site tests pass; all other CI scripts pass; `node --check` on every script passes. +- `check-retention-automation.mjs` fails in CI for environmental reasons (stale-checkout comparison against a different checkout path), pre-existing and unrelated. +- Visual confirmation via 390×844 screenshots: heading, all three buttons, lead, and chips visible in first viewport. + +## Files changed +- public/styles.css +- public/promptly/index.html +- public/drishti/index.html +- scripts/test-public-heading-hierarchy.mjs + +## PR +https://github.com/nish3451/tinystudio-in/pull/147