Repository navigation
fix(ui-web): a lone delivery's preview keeps the shape of what is in it - #680
Conversation
A delivered deck's card drew the slide as a letterboxed strip with its own title cut in half: the picture box measured 688x98 -- a 7:1 box -- and `cover` fitted a 16:9 slide into it by keeping the middle quarter. The two arrangements want different things. In the grid a preview sits above its caption in a column of stated width, so the box states a ratio and the image fills it; a little crop is the price of a tidy grid. Alone, the preview stands beside the caption at a stated height and the column follows it. That last part has to be paid for. A column told to follow the picture needs the picture to state a width, and an image that fills a box states none -- it is `width: 100%` of whatever it is given. Given an auto column that resolved to the whole row, and the stated 98px height then made the box a strip. Sized from the height instead, the image resolves its own width from its own ratio, the column resolves from that, and the box ends up the shape of its contents. `contain` is stated anyway: with the box right there is nothing left to crop, and the rule should say what it means rather than rely on the box being right. Measured on a delivered deck, in both engines: the picture box was 688x98 against a 1280x720 picture, a 7.02 ratio holding a 1.78 one; it is now 173x98, a 1.77 ratio, and nothing is cropped. The picture still does not overlap the title beside it -- its right edge and the caption's left edge are the same 555, as they were -- which is the fault the auto column was introduced to fix, and the card is 124px tall rather than 137. Three assertions in a gate of its own, for the reason the other CSS gates give: happy-dom does no layout, so a picture cropped to a strip and one drawn whole are the same assertion in a DOM test. Retracting the rule fails the first, and so does putting the width back to 100%. Co-authored-by: Claude (claude-opus-5) <noreply@anthropic.com>
gloryfromca
left a comment
There was a problem hiding this comment.
No blockers; this can merge as far as I am concerned.
I reviewed the full github/main...HEAD diff and the surrounding delivery-tile component and stylesheet, traced the auto-column rule back to the prior lone-delivery fix, and checked loading, missing-file, image, deck/PDF thumbnail, and multi-delivery paths. I also checked the repository rules and Web UI context, backward compatibility, test strength, file naming, commit metadata, and architecture boundaries. The new override is scoped to lone shot previews, preserves the grid behavior, and the CSS gate pins all three coupled declarations without weakening existing coverage.
Verification: npm test -- --run scripts/gates/lone-delivery-css.test.mjs passed (3 tests); npm test passed (193 files, 2,661 tests); npm run type-check passed; npm run lint completed with 0 errors and 4 pre-existing warnings in untouched files; git diff --check github/main...HEAD passed. The live page-check CI job is also green.
…it (#680) ## Summary A delivered deck's card drew the slide as a letterboxed strip with its own title cut in half. Measured on the reported card: the picture box was **688x98** -- a 7.02 ratio -- holding a **1280x720** picture, a 1.78 one, under `object-fit: cover`. So `cover` filled the width and kept the middle quarter of the slide. The two arrangements of the tile want different things: - **In the grid**, a preview sits above its caption in a column of stated width. The box states a ratio and the image fills it (`width: 100%`, `cover`); a little crop is the price of a tidy grid, and that is unchanged. - **Alone**, the preview stands beside the caption at a stated height, and the column follows it -- `grid-template-columns: auto minmax(0, 1fr)`, which #624 introduced so a picture wider than the 92px document face stopped running over the title. That last part has to be paid for. A column told to follow the picture needs the picture to state a width, and an image that fills a box states none: it is `width: 100%` of whatever it is given. Given an auto column, that resolved to the whole row, and the stated 98px height then made the box a strip. Sized from the height instead, the image resolves its own width from its own ratio, the column resolves from that, and the box ends up the shape of its contents. `contain` is stated anyway: with the box right there is nothing left to crop, and the rule should say what it means rather than rely on the box being right. ## Type - [x] Fix - [ ] Feature - [ ] Docs - [ ] CI / tooling - [ ] Refactor - [ ] Other ## Verification - Measured on a real delivered deck, live, in **both** engines. Before: picture box 688x98, ratio 7.02 against the picture's 1.78, card 137px tall. After: 173x98, ratio 1.77 against 1.78, nothing cropped, card 124px tall. - The fault the auto column was introduced to fix stays fixed: the picture's right edge and the caption's left edge are both 555, so it does not run over the title. WebKit and Chromium agree on every number above. - Three assertions in `ui-web/scripts/gates/lone-delivery-css.test.mjs`: the lone arrangement sizes the image from its height and crops nothing; the grid arrangement still fills its stated box; the column still follows the picture. A gate rather than a DOM test for the reason the other CSS gates in that directory give -- happy-dom does no layout, so a picture cropped to a strip and one drawn whole are the same assertion there. - Falsifiable, by two mutations: retracting the rule fails the first assertion, and putting the width back to `100%` -- which is the fault exactly -- fails it too. Both restored green. - `npx vitest run` in ui-web: 193 files, 2661 tests, every gate included. `npm run type-check` clean, `npm run lint` 0 errors (the 4 warnings are main's), `npm run build` and `python ui-web/build.py` with both boot goldens matching. - [x] Relevant tests pass locally - [x] Relevant lint / type checks pass locally - [x] User-facing docs or screenshots are updated when needed ## Risk - [x] Security impact considered - [x] Backward compatibility considered - [x] Rollback path is clear for risky changes One rule, scoped to the lone arrangement by the selector it already had; the grid arrangement's own rule is untouched, so a row of tiles is drawn exactly as before. A tile whose preview is the generic document face is unaffected -- that face is not `.pic.shot`. Reverting the commit restores the strip. ## Related Issues N/A Co-authored-by: Claude (claude-opus-5) <noreply@anthropic.com>
Summary
A delivered deck's card drew the slide as a letterboxed strip with its own title cut in half. Measured on the reported card: the picture box was 688x98 -- a 7.02 ratio -- holding a 1280x720 picture, a 1.78 one, under
object-fit: cover. Socoverfilled the width and kept the middle quarter of the slide.The two arrangements of the tile want different things:
width: 100%,cover); a little crop is the price of a tidy grid, and that is unchanged.grid-template-columns: auto minmax(0, 1fr), which fix(*): draw the template covers at boot, fit a lone delivery, show a pdf's page #624 introduced so a picture wider than the 92px document face stopped running over the title.That last part has to be paid for. A column told to follow the picture needs the picture to state a width, and an image that fills a box states none: it is
width: 100%of whatever it is given. Given an auto column, that resolved to the whole row, and the stated 98px height then made the box a strip.Sized from the height instead, the image resolves its own width from its own ratio, the column resolves from that, and the box ends up the shape of its contents.
containis stated anyway: with the box right there is nothing left to crop, and the rule should say what it means rather than rely on the box being right.Type
Verification
Measured on a real delivered deck, live, in both engines. Before: picture box 688x98, ratio 7.02 against the picture's 1.78, card 137px tall. After: 173x98, ratio 1.77 against 1.78, nothing cropped, card 124px tall.
The fault the auto column was introduced to fix stays fixed: the picture's right edge and the caption's left edge are both 555, so it does not run over the title. WebKit and Chromium agree on every number above.
Three assertions in
ui-web/scripts/gates/lone-delivery-css.test.mjs: the lone arrangement sizes the image from its height and crops nothing; the grid arrangement still fills its stated box; the column still follows the picture. A gate rather than a DOM test for the reason the other CSS gates in that directory give -- happy-dom does no layout, so a picture cropped to a strip and one drawn whole are the same assertion there.Falsifiable, by two mutations: retracting the rule fails the first assertion, and putting the width back to
100%-- which is the fault exactly -- fails it too. Both restored green.npx vitest runin ui-web: 193 files, 2661 tests, every gate included.npm run type-checkclean,npm run lint0 errors (the 4 warnings are main's),npm run buildandpython ui-web/build.pywith both boot goldens matching.Relevant tests pass locally
Relevant lint / type checks pass locally
User-facing docs or screenshots are updated when needed
Risk
One rule, scoped to the lone arrangement by the selector it already had; the grid arrangement's own rule is untouched, so a row of tiles is drawn exactly as before. A tile whose preview is the generic document face is unaffected -- that face is not
.pic.shot. Reverting the commit restores the strip.Related Issues
N/A