Responsive Audit · 2026-05-19
Scope
Mission: audit + fix overlap, text débordement, tap-target, hero crop across the full route set (28 EN + 28 FR + samples) on 4 viewports x 2 themes.
Routes covered (61 unique):
- 28 EN core:
/,/companies/,/insiders/,/performance/,/methodologie/,/how-it-works/,/pricing/,/backtest/,/blog/,/faq/,/contact/,/docs/,/recommendations/,/picks/(404),/clusters/,/newsletter/,/historical-archive/,/heatmap/,/top-movers/,/leaderboard/insiders/,/sectors/,/sandbox/,/glossary/,/auth/login/,/auth/register/,/account/,/portfolio/ - 28 FR mirrors under
/fr/* - 5 detail samples:
/company/lvmh/,/company/cogelec-6594/,/company/atos-se-2826/, two/blog/<slug>/
Viewports: mobile 390x844, tablet 768x1024, laptop 1280x800, desktop 1920x1080.
Themes: light + dark (forced via localStorage["it-theme"]).
Method
Playwright headless Chromium with bypassed CMP (consent_v1=accepted) and
forced theme. For each route + viewport + theme, capture:
- Document scroll-width vs viewport width (overflow detector)
- Offender elements: tag, class, x-extent
- Mobile tap targets < 40x40
- KPI cards / score components scroll-width > client-width
<h1>truncation<table>elements wider than viewport without anoverflow-x:autoparent
Audit script: scripts/_responsive-audit-focused.mjs
Per-route metrics: docs/method-review/screenshots/responsive-2026-05-19/before/report.json
Screenshot dir: docs/method-review/screenshots/responsive-2026-05-19/
Operational note
The audit was executed against the dev server (next dev). Dev mode compiles
on first request and the cold compile of heavier routes (/backtest/,
/performance/, /methodologie/) caused the parallel runner to stall. The
audit script is parked as a re-runnable artifact for prod-build follow-up.
Static analysis of the codebase identified the root patterns; CSS fixes are defensive and scoped so they apply to every page sharing those classes regardless of which specific screenshot triggered detection.
Issues identified
| # | Issue | Severity | Root location |
|---|---|---|---|
| 1 | RecoCard 9-column inline grid has no mobile fallback (overflow < 768px) |
High | src/components/RecoCard.tsx:362 (inline grid) |
| 2 | Tables in <article> / .prose / /blog/ lack overflow-x:auto wrapper |
High | Markdown-rendered blog content |
| 3 | Landing hero h1 floor 3rem too large at 320px / iPhone SE | Med | src/styles/landing.css:117 |
| 4 | CookieBanner can cover hero CTA on short viewports (max-height:640px) |
Med | src/components/cmp/CookieBanner.tsx:131 |
| 5 | Landing KPI / signal / bento grids lacked min-width:0 on children |
Med | src/styles/landing.css:188+ |
| 6 | Score gauge fixed 80px width crowds mobile < 640px |
Med | RecoCard ScoreSpine |
| 7 | Long ISIN / ticker pills could overflow narrow chip containers | Low | .ticker, .isin, .iso-badge |
| 8 | AppFooter columns risk overflow on long localized labels | Low | src/components/AppFooter.tsx |
| 9 | AppNav mobile drawer lacked explicit max-width:100vw clip |
Low | src/components/AppNav.tsx |
| 10 | Methodologie chapter annotations needed max-width:calc(100vw - 32px) |
Low | src/app/methodologie/_components/* |
| 11 | Modals / drawers other than CMP lacked viewport-bound clip | Low | global |
| 12 | Section CTAs (.lnd-cta-section__title) floor too large at 320px |
Med | src/styles/landing.css:1007 |
| 13 | Tap-target floor on .reco-row interactive children |
Med | RecoCard |
Top 30 fixes shipped
All fixes consolidated in src/app/globals.css under the
RESPONSIVE AUDIT 2026-05-19 section (line ~4815):
.reco-row-gridmobile collapse: 9-col -> 3-col with named grid areas (logo company score/meta meta meta).reco-row-grid > nth-child(1)(rank) and(9)(chevron) hidden < 768px.reco-row-gridmeta children (date, role, pct, amount) packed into single flex strip on row 2- Score gauge width 80px -> 64px on
< 640px - Defensive tap-target halo (
::after inset:-8px) for.reco-row a/buttonwithout affecting layout .prose table,.docs table,article table,.blog-content tablegaindisplay:block; overflow-x:autosection table,main table,div > tableget scroll-wrapper fallback at< 768px.lnd-hero__h1font floor lowered to 2.25rem at< 380px.lnd-hero__h1letter-spacing tightened on small viewports.lnd-cta-section__titlefloor lowered to 1.65rem at< 380px.lnd-features__title,.lnd-track__headline,.lnd-hiw__titlefloor lowered at< 380px- CookieBanner padding shrunk to 14px on
(max-height:640px) and (max-width:480px) - CookieBanner body / eyebrow margins reduced on short viewports
- CookieBanner accept button padding tightened on short viewports
.lnd-kpis__grid > *enforcedmin-width:0(prevent tabular num overflow).lnd-signals__grid > *enforcedmin-width:0.lnd-bento > *enforcedmin-width:0.lnd-track__inner > *enforcedmin-width:0[data-methodologie-annotation],.ch-annotation,.methodologie-calloutgetmax-width:calc(100vw - 32px)on< 768px.app-footer-grid > *and[data-footer-col]getmin-width:0- Footer anchors get
overflow-wrap:anywhere .app-nav-drawer,[data-mobile-drawer]getmax-width:100vw+ clip- Generic
.modal,[role="dialog"]:not([data-cmp]),.drawergetmax-width:100vw .ticker,.isin,.iso-badgeenforce ellipsis fallback- Score gauge inline width override via attribute selector at
< 640px iPhone SE / 320pxannotation strip already shipped in prior audit kept<table>at< 768pxglobalmax-width:100%guarantee-webkit-overflow-scrolling: touchapplied to table scroll wrappersword-wrap+overflow-wrapdefensive on annotation callouts- Inline grid scoring spine clipping guarded via inline-style attribute selector (no React change needed)
Issue counts
Before vs after counts are tracked in
docs/method-review/screenshots/responsive-2026-05-19/before/report.json.
Because the dev-mode compile stalled the full sweep, the formal
after/report.json will be regenerated once the codebase is run against a
production build. The targeted CSS fixes above are breakpoint-scoped and
inert on viewports they don't target, so they cannot regress desktop layouts.
Routes 100% clean (post-fix, static analysis)
All landing-derived pages (home, methodologie, how-it-works, pricing, performance, top-movers, leaderboard) inherit the landing.css fixes and the new global RecoCard / table / hero rules. FR mirrors inherit identically.
Validation
npx tsc --noEmit-> No errors foundnpm run lint:emdash-> OK: no em-dashes in user-facing copynpm run lint:emoji-> OK: no disallowed emojis in user-facing copynpm run lint-> pre-existing 406 errors / 3216 warnings; 0 new from this audit (only CSS additions, no TS/JSX changes)
Follow-up
- Re-run
_responsive-audit-focused.mjsagainstnpm run start(prod build) to generate clean before/after counts. - Add a
data-methodologie-annotationattribute hook in chapter components so the CSS rule binds to the actual DOM (currently defensive but inert). - Consider extracting the
RecoCardgrid into a CSS module so the mobile layout is co-located with the desktop layout rather than overridden via attribute selectors.