evidence · 5.2 KiB

README.md

Committed at docs/evidence/coherent-shell/icons/README.md. This is what grounds the requirements that cite it.

Open raw source

Icon resolution checkpoint for the existing launcher

This is host/source evidence for part of task 1.4 of the-handheld-presents-a-coherent-shell, based on a7c7a2af. It changes the installed development Apps surface’s rows; it does not claim that the proposed bar-free drawer, live-card headers, or notification center are installed. Task 1.4 remains unchecked because the latter two consumers do not exist in this path yet. No board, Nix cross-build, image integration, or real-finger verification was run for the initial checkpoint. A subsequent narrow cross-build is recorded below; physical verification remains open.

The launcher now reads each installed desktop entry’s GAppInfo/GIcon, including absolute GFileIcon paths and themed names. The resolver searches K230_ICON_THEME when set, follows index.theme inheritance to a bounded depth, then tries hicolor and XDG pixmaps. Its fixed sizes are 48 px for drawer rows, 32 px for eligible cards, and 24 px for trusted notifications. The existing app name stays text beside a same-sized neutral fallback. The current built-in Terminal/New terminal and Monitor rows request the installed Foot and htop themed icons. The image’s Video desktop entry now declares Icon=mpv; Editor declares Icon=accessories-text-editor and falls back when that theme glyph is not installed. nix/shell.nix puts the actual Foot, htop, and Video-player package share trees on the launcher’s XDG_DATA_DIRS path before profile paths, so their Nix store icons can be resolved by name. The theme name is configurable; this does not assume that a proposed theme clone has been installed or selected.

PNG decoding uses Cairo, and SVG decoding uses librsvg rather than a homemade SVG parser or an implicit gdk-pixbuf loader cache. The launcher derivation declares and links librsvg. Files over 512 KiB, unreadable files, unknown icon types, and unsafe themed path components take the named fallback. The single-threaded cache holds at most 12 fixed-size Cairo image surfaces (at most about 108 KiB of decoded pixel data at 48×48, plus small metadata), with LRU eviction. A changed file stamp or changed XDG/theme environment replaces cached entries; k230_icon_cache_invalidate() is available for a future app-catalog/theme refresh. A newly created file for a previously missing name needs that explicit invalidation in the same process. Decoding is lazy; first appearance cost on a new page is not yet measured on the board.

K230_ICON_PRIVATE_CARD and K230_ICON_PRIVATE_NOTIFICATION return a neutral glyph before inspecting the supplied GIcon. Host tests verify no identity-bearing cache entry or decode is created. This is an API contract for future card/notification clients, not a claim that their production privacy state has been wired to it. The private card’s title must separately be redacted by the owning compositor scene before display.

Host verification

Run from the repository root:

python3 tests/test_shell_icons.py --case theme --case missing \
  --case cache-bound --case notification-icon --case private-no-identity
python3 tests/test_shell_icons.py --case absolute --case svg
python3 tests/test_desktop_catalog.py
python3 tests/test_launcher_navigation.py
nix-instantiate --parse nix/shell.nix >/dev/null
nix-instantiate --parse nix/touch-launcher/default.nix >/dev/null

All seven icon fixtures passed on the host. The theme case exercised custom theme inheritance and, where present, the actual Foot, htop and mpv SVGs from the image’s Nix packages. The absolute-path and SVG cases passed. The cache case verified reuse, the 12-entry ceiling, eviction and explicit invalidation. The private case compared rendered pixels with and without an identifying icon and observed zero decodes/cache entries. The isolated 64×64 rendered theme, SVG, fallback and private samples were visually inspected; they show distinct artwork, a legible generic person glyph and a neutral lock glyph. The three desktop-catalog tests and three launcher-navigation tests pass. The production launcher compiled against host-generated Wayland protocol bindings and its --layout command returned normally. Nix parsing passed; that is syntax only, not a cross-build.

Narrow cross-build after integration

On 2026-09-23, from integrated source fd8fcf326f3b7c42d5e07715999426695cad5a24:

nix build .#touch-launcher --max-jobs 1 --cores 4 --no-link --print-out-paths

PASS: /nix/store/xarb3m3r8drh69wz91il23l1xh6n9y0k-k230-touch-launcher. The wrapper references target binary package /nix/store/bir1a5d1fyx58z3isjg1pk0069p8w28h-k230-touch-launcher-riscv64-unknown-linux-gnu-0.1 and the explicit Foot/htop/mpv icon roots. Only the two launcher derivations needed building. The root coordinator reran seven icon and three launcher navigation host tests successfully; CI now installs librsvg2-dev and runs the icon suite. No launcher deployment, full-image build, or board action was performed for this result.

Remaining gate: inspect installed rows and cache cost on the physical 568×1232 screen. The final task 1.4 gate additionally needs actual live-card and trusted-notification consumers, private title redaction, and its named five-case test command to pass against those consumers. No checkbox was changed for this partial implementation.