fix(explore): scroll the album page as one on a phone #179

Merged
logan merged 1 commits from fix/66-album-page-scrolls-as-one into main 2026-08-21 14:36:20 +00:00
Collaborator

The issue. Opening an album on a phone, the header did not scroll — only the tracklist did — and the content was wider than the screen. Measured at the reference device's 424×439, with the two comments on #66 as the starting point:

box before after
explore-album-details scrollWidth 443 in a 424px box 424
.album-header height 253 of the panel's 318px 395, and it scrolls
.content clientHeight 64 256, and it is not a scroller
.album-info width 112 392
"Shuffle album" right edge 443 — clipped, unreachable 261
"Add to queue" right edge 440 — clipped, unreachable 164
album title G… Glass Harbour

What changed. One @media (max-width: 599px) block at the foot of the component's own stylesheet — a media query inside a shadow root is answered by the viewport, so the component states its phone layout rather than the shell reaching in.

  • The host becomes the scroller and .content stops being one, so the header scrolls away and the page moves as one. Available only because this tracklist is plain DOM rather than a virtualizer, and because .main-panel > * already gives the host a definite height.
  • The header's flex row stacks — art over info, art 200 → 140px, which is 45% of the reference device's height when it is the whole width budget.

Why not another min-width: 0. #66's Direction names one and the 2026-08-19 comment on the issue already ruled it out: .album-info carries min-width: 0 and was shrinking exactly as asked, to 112px beside a fixed 200px sibling. A row with a fixed-size sibling has to stack at that width, or the column that must shrink has nothing to be wide with.

Why the new spec measures per control. layout-overflow.spec.ts asserts the shell needs no sideways scrolling and was green throughout: body.scrollWidth === clientWidth === 424, because the overflow was inside a component and clipped by its own overflow: hidden. e2e/specs/phone-album-page.spec.ts measures each header control against the host's box, which is top-bar-fit.spec.ts's shape for the same reason.

Verification

  • make e2e --project=chromium224 passed (220 existing + 4 new). Checked the new spec fails on the pre-fix build: three of its four assertions fail there, the fourth being the desktop arrangement, which is meant to pass either way. WebKit is CI's half; Playwright's Linux WebKit does not run on Arch.
  • make ui-test984 passed. No new component test: this is a media query and that tier's viewport is fixed at 1280×800.
  • npx tsc --noEmit and make css-check — clean.
  • No Go changed, so make lint / make test were not run, and no binding changed.
  • Read screenshots, before and after at 424×439, scrolled with a real wheel gesture (overflow: hidden still permits scrollTop, so a probe that assigns it passes on the broken build), and at 1100×760 to confirm the desktop arrangement is untouched — art 200px, header flex-direction: row, .content still the scroller.

Deliberately not done

  • No device tier. Chrome 113 is unverified; a flex direction and a scroll container are nowhere near that engine's documented gaps (relaxed nesting, the Popover API, light-dark()), but "it renders at that size in Chromium" is not evidence about the phone, and I do not have the device.
  • No sticky compact title bar. #66 offers it as an "optionally"; the header scrolling away is what the report asks for, and the back button goes with it — the platform's back gesture and scrolling up are the routes back.
  • explore-artist-details is untouched, though it is the same shape one page over. That is a separate report if it measures broken, not a wider diff here.

Closes #66

**The issue.** Opening an album on a phone, the header did not scroll — only the tracklist did — and the content was wider than the screen. Measured at the reference device's 424×439, with the two comments on #66 as the starting point: | box | before | after | |---|---|---| | `explore-album-details` `scrollWidth` | **443** in a 424px box | 424 | | `.album-header` height | 253 of the panel's 318px | 395, and it scrolls | | `.content` `clientHeight` | **64** | 256, and it is not a scroller | | `.album-info` width | **112** | 392 | | "Shuffle album" right edge | **443** — clipped, unreachable | 261 | | "Add to queue" right edge | **440** — clipped, unreachable | 164 | | album title | `G…` | *Glass Harbour* | **What changed.** One `@media (max-width: 599px)` block at the foot of the component's own stylesheet — a media query inside a shadow root is answered by the viewport, so the component states its phone layout rather than the shell reaching in. - The **host** becomes the scroller and `.content` stops being one, so the header scrolls away and the page moves as one. Available only because this tracklist is plain DOM rather than a virtualizer, and because `.main-panel > *` already gives the host a definite height. - The header's flex row **stacks** — art over info, art 200 → 140px, which is 45% of the reference device's height when it is the whole width budget. **Why not another `min-width: 0`.** #66's Direction names one and the 2026-08-19 comment on the issue already ruled it out: `.album-info` carries `min-width: 0` and was shrinking exactly as asked, to 112px beside a fixed 200px sibling. A row with a fixed-size sibling has to stack at that width, or the column that must shrink has nothing to be wide with. **Why the new spec measures per control.** `layout-overflow.spec.ts` asserts the *shell* needs no sideways scrolling and was green throughout: `body.scrollWidth === clientWidth === 424`, because the overflow was inside a component and clipped by its own `overflow: hidden`. `e2e/specs/phone-album-page.spec.ts` measures each header control against the host's box, which is `top-bar-fit.spec.ts`'s shape for the same reason. **Verification** - `make e2e --project=chromium` — **224 passed** (220 existing + 4 new). Checked the new spec **fails on the pre-fix build**: three of its four assertions fail there, the fourth being the desktop arrangement, which is meant to pass either way. WebKit is CI's half; Playwright's Linux WebKit does not run on Arch. - `make ui-test` — **984 passed**. No new component test: this is a media query and that tier's viewport is fixed at 1280×800. - `npx tsc --noEmit` and `make css-check` — clean. - No Go changed, so `make lint` / `make test` were not run, and no binding changed. - **Read screenshots**, before and after at 424×439, scrolled with a real wheel gesture (`overflow: hidden` still permits `scrollTop`, so a probe that assigns it passes on the broken build), and at 1100×760 to confirm the desktop arrangement is untouched — art 200px, header `flex-direction: row`, `.content` still the scroller. **Deliberately not done** - **No device tier.** Chrome 113 is unverified; a flex direction and a scroll container are nowhere near that engine's documented gaps (relaxed nesting, the Popover API, `light-dark()`), but "it renders at that size in Chromium" is not evidence about the phone, and I do not have the device. - **No sticky compact title bar.** #66 offers it as an "optionally"; the header scrolling away is what the report asks for, and the back button goes with it — the platform's back gesture and scrolling up are the routes back. - **`explore-artist-details` is untouched**, though it is the same shape one page over. That is a separate report if it measures broken, not a wider diff here. Closes #66
logan added 1 commit 2026-08-21 08:41:15 +00:00
fix(explore): scroll the album page as one on a phone
CI / check (push) Skipped
CI / e2e (push) Skipped
CI / check (pull_request) Successful in 2m28s
CI / e2e (pull_request) Successful in 9m8s
ea3edde697
`explore-album-details` was a fixed header over a scrolling tracklist,
which is the desktop arrangement. At the reference device's 424x439 the
header owned 253 of the panel's 318px and the list scrolled inside the
64 that were left, and the header's flex row squeezed `.album-info` to
112px beside a 200px cover -- so the title drew as one ellipsised glyph
and two of the album's three primary actions were clipped by the
component's own `overflow: hidden`: "Shuffle album" ended at x=443 in a
424px box, reachable by no gesture.

Below 600px the host is the scroller and `.content` stops being one, so
the header scrolls away and the page moves together; the header stacks
art over info, so the info column has the row's whole width. The
tracklist is plain DOM rather than a virtualizer, so nothing inside
wants a scroll window of its own.

Another `min-width: 0` was not the fix and the issue's own measurement
says so: `.album-info` carries one and was shrinking as asked. Nor
could `layout-overflow.spec.ts` see any of this -- `body.scrollWidth`
equalled the viewport throughout, because the overflow was inside a
component -- so the new spec measures each header control against the
host's own box, which is `top-bar-fit.spec.ts`'s shape for the same
reason.

The phone block is last in the stylesheet on `index.css`'s rule: a
media query adds no specificity, so above the rules it overrides every
declaration in it would be silently dead.

Closes #66
Author
Collaborator

CI is green on both engines — run 17385.

  • check: commit messages, lint, test (three build configurations), tsc --noEmit, css-check, the 984-test component suite, bindings-check, skill-check.
  • e2e: chromium and webkit both success. Worth saying explicitly, since the WebKit step has silently skipped on this repo before when a chromium failure cancelled it — it ran here.

Nothing was retried; this is the first run on the branch.

**CI is green on both engines** — run 17385. - `check`: commit messages, lint, test (three build configurations), `tsc --noEmit`, `css-check`, the 984-test component suite, `bindings-check`, `skill-check`. - `e2e`: **chromium** and **webkit** both `success`. Worth saying explicitly, since the WebKit step has silently *skipped* on this repo before when a chromium failure cancelled it — it ran here. Nothing was retried; this is the first run on the branch.
logan merged commit 6cca57f229 into main 2026-08-21 14:36:20 +00:00
Sign in to join this conversation.