diff options
| author | Paul Buetow <paul@buetow.org> | 2026-06-25 12:16:17 +0300 |
|---|---|---|
| committer | Paul Buetow <paul@buetow.org> | 2026-06-25 12:16:17 +0300 |
| commit | 964901d672d8e12baf4ac0eb29821d670ae15eb8 (patch) | |
| tree | dea3e16972b0d6caa9bfbf2aa063d8c3fdb88cab /share | |
| parent | 3377635c88a6a2f6631a4c416c32f0d57ec05ccd (diff) | |
Flush preview-grid rows: fixed breakpoint columns + multiple-of-12 pages
The overview grid used auto-fill columns (an unpredictable count at view
time) while tiles per page were fixed at generation, so the last row was
ragged -- an empty, cut-off bottom-right corner, made worse by a 2x2
feature tile.
CSS (header.tmpl): replace auto-fill with a FIXED column count per width
breakpoint -- 2 (phone) / 3 / 4 / 6 -- all divisors of 12. THUMBHEIGHT no
longer drives the grid (it only sizes the thumbnail files), so its
obsolete render-var is dropped (template.source.sh).
Generator (album-tile-layout, album-thumbnail-html): append_preview_grid
now decides a page's tiles, then snaps the grid-cell total onto a multiple
of 12 before emitting, via two photo-preserving levers --
_grid_split_subdivides_to_add (round up: split subdivided tiles into
singles; preferred, abundant) and _grid_merge_singles_to_remove (round
down: merge adjacent singles). Because 2/3/4/6 all divide 12, a
multiple-of-12 page tiles into a COMPLETE rectangle at every breakpoint:
a flush last row at any window width, with no image distortion
(object-fit: cover). Per-photo preview numbers and all navigation
redirects are unchanged. Tiny pages (a short final page or small stats
mini-album) are left as-is.
Decrements use assignment, not bare "(( --k ))": under set -euo pipefail
an arithmetic command evaluating to 0 returns status 1 and would abort
generate. Helper namerefs are uniquely named and arrays are forwarded by
name to avoid bash circular-nameref errors.
Tests: add test_album_grid_cells_align_to_multiple_of_12 (both levers);
update the two tests that pinned the old auto-fill CSS / render-var list.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Diffstat (limited to 'share')
| -rw-r--r-- | share/templates/default/header.tmpl | 44 |
1 files changed, 27 insertions, 17 deletions
diff --git a/share/templates/default/header.tmpl b/share/templates/default/header.tmpl index d5d1648..c0a0fac 100644 --- a/share/templates/default/header.tmpl +++ b/share/templates/default/header.tmpl @@ -197,27 +197,37 @@ cat <<END vertical-align: top; } - /* The album overview is a CSS grid. THUMBHEIGHT is the MINIMUM cell - width: columns grow (1fr) to fill the row, so the thumbnails use the - full window width instead of leaving big margins left and right, and - there is no centred leftover. Each 1x1 grid item is kept square with - aspect-ratio, so the auto-sized rows are square too; a "feature" tile - then spans a 2x2 block (a large hero image) and a subdivided tile packs - several smaller thumbnails into one cell. grid-auto-flow: dense lets - the smaller tiles backfill the holes a 2x2 feature would otherwise - leave. Spacing comes from the grid gap, so images carry no padding. */ + /* The album overview is a CSS grid with a FIXED column count chosen by + width breakpoints (not auto-fill). The counts are 2 / 3 / 4 / 6 -- all + divisors of 12 -- so a page whose tile-cell total is a multiple of 12 + (the generator guarantees this, see append_preview_grid) forms a + COMPLETE rectangle at every breakpoint: no ragged, cut-off last row at + any window width. Columns are 1fr, so the thumbnails grow to fill the + full window width instead of leaving margins. Each 1x1 grid item is + kept square with aspect-ratio; a "feature" tile spans a 2x2 block (a + large hero image) and a subdivided tile packs several smaller + thumbnails into one cell. grid-auto-flow: dense lets the smaller tiles + backfill the holes a 2x2 feature would otherwise leave. Spacing comes + from the grid gap, so images carry no padding. Mobile-first: the base + rule is the 2-column phone layout; min-width breakpoints widen it. */ div.thumbs-grid { display: grid; - /* min(THUMBHEIGHT, 100%) keeps a column from ever exceeding the - viewport width, so narrow phones never scroll sideways; on wide - screens the columns are >= THUMBHEIGHT and grow (1fr) to fill. */ - grid-template-columns: - repeat(auto-fill, minmax(min(${render_thumbheight_html}px, 100%), 1fr)); + grid-template-columns: repeat(2, 1fr); grid-auto-flow: dense; gap: 10px; margin: 0 4px; } + @media (min-width: 700px) { + div.thumbs-grid { grid-template-columns: repeat(3, 1fr); } + } + @media (min-width: 1100px) { + div.thumbs-grid { grid-template-columns: repeat(4, 1fr); } + } + @media (min-width: 1600px) { + div.thumbs-grid { grid-template-columns: repeat(6, 1fr); } + } + div.thumbs-grid img { padding: 0; } @@ -385,11 +395,11 @@ cat <<END } } - /* Phone layout: a 2-column square grid, and the navigator/footer/splash - links become large, well-spaced tap targets (~44px). Pure CSS. */ + /* Phone layout: the base rule already gives a 2-column grid; here we just + tighten the gap/margin, and the navigator/footer/splash links become + large, well-spaced tap targets (~44px). Pure CSS. */ @media (max-width: 700px) { div.thumbs-grid { - grid-template-columns: 1fr 1fr; gap: 6px; margin: 0 2px; } |
