From 863b1195280d50b05c7abdea60de07a66d2d03c3 Mon Sep 17 00:00:00 2001
From: Abdessamad Derraz <3028866+Abdess@users.noreply.github.com>
Date: Fri, 23 Oct 2026 10:56:35 +0200
Subject: [PATCH] feat: load tile logos past the first row lazily
Home on a phone over 4G: 217.3 KiB to 134.5 KiB on first load, 19 images to 10.
---
scripts/generate_site.py | 14 +++++++++-----
scripts/sitemarkup.py | 22 ++++++++++++++++------
tests/test_site_r3_entry.py | 18 ++++++++++++++++++
3 files changed, 43 insertions(+), 11 deletions(-)
diff --git a/scripts/generate_site.py b/scripts/generate_site.py
index b620a626..441ce1ea 100644
--- a/scripts/generate_site.py
+++ b/scripts/generate_site.py
@@ -455,7 +455,7 @@ def _next_block(links: list[str]) -> list[str]:
def _tiles(registry: dict, members: list[str], display: dict[str, str], prefix: str = "",
- group: str = "") -> list[str]:
+ group: str = "", eager: int = 0) -> list[str]:
"""The setup tiles of one device group: logo, name and the hardware it
runs on, then the group's other tiles: a kind of device that runs one of
the setups (Android handhelds, Linux handhelds)."""
@@ -465,13 +465,14 @@ def _tiles(registry: dict, members: list[str], display: dict[str, str], prefix:
GUIDES[name].runs_on or _runs_on(registry.get(name, {}), GUIDES[name]))
for name in members),
*((tile.name, f"{prefix}{tile.link}", "", tile.text) for tile in GROUP_TILES.get(group, ())),
- ])
+ ], eager=eager)
def setup_picker(registry: dict, display: dict[str, str], prefix: str = "") -> list[str]:
"""Every setup as a tile, under the device group it belongs to. The
setups alone in their group share one row: "MiSTer FPGA" above
- "MiSTer FPGA" said nothing."""
+ "MiSTer FPGA" said nothing. Only the first row of logos loads with the
+ page: the 19 logos were most of the bytes of the home page."""
lines: list[str] = []
alone: list[str] = []
for group, (label, _description) in DEVICE_GROUPS.items():
@@ -479,9 +480,12 @@ def setup_picker(registry: dict, display: dict[str, str], prefix: str = "") -> l
if len(members) == 1 and not GROUP_TILES.get(group):
alone += members
elif members:
- lines += [f"**{label}**", "", *_tiles(registry, members, display, prefix, group)]
+ eager = 0 if lines else markup.FIRST_ROW_TILES
+ lines += [f"**{label}**", "",
+ *_tiles(registry, members, display, prefix, group, eager)]
if alone:
- lines += ["**Other setups**", "", *_tiles(registry, alone, display, prefix)]
+ eager = 0 if lines else markup.FIRST_ROW_TILES
+ lines += ["**Other setups**", "", *_tiles(registry, alone, display, prefix, eager=eager)]
return lines
diff --git a/scripts/sitemarkup.py b/scripts/sitemarkup.py
index 207636bf..f6ae72a8 100644
--- a/scripts/sitemarkup.py
+++ b/scripts/sitemarkup.py
@@ -190,27 +190,37 @@ def initials(name: str) -> str:
return "".join(capitals[:2]) or name[:2].upper()
-def _tile_mark(name: str, logo: str) -> str:
+def _tile_mark(name: str, logo: str, lazy: bool = False) -> str:
+ """A tile's logo, or its initials. *lazy* for a tile below the first
+ screen: the browser fetches its logo when the reader scrolls near it."""
if logo:
- return f''
+ loading = ' loading="lazy"' if lazy else ""
+ return (f'
')
# The same square as a logo, drawn on white like the logos are.
return ('')
-def platform_tiles(tiles: list[tuple[str, str, str, str]]) -> list[str]:
+# Tiles in the first row of a grid at its widest, two columns of 15rem in
+# the content column: the logos the reader may see without scrolling.
+FIRST_ROW_TILES = 2
+
+
+def platform_tiles(tiles: list[tuple[str, str, str, str]], eager: int = 0) -> list[str]:
"""One link per setup: its logo (or its initials), its name and where it
- runs. *tiles* are (name, target, logo, runs_on).
+ runs. *tiles* are (name, target, logo, runs_on). The first *eager*
+ logos load with the page, the others when the reader scrolls to them.
One HTML line: a grid of links is a menu, not prose, and the Markdown
around it reads none of it."""
links = "".join(
f''
- f"{_tile_mark(name, logo)}"
+ f"{_tile_mark(name, logo, lazy=index >= eager)}"
f'{html.escape(name)}'
f'{inline_html(runs_on)}'
- for name, target, logo, runs_on in tiles
+ for index, (name, target, logo, runs_on) in enumerate(tiles)
)
return [f'