// Musician page — QML port of Tauri's MusicianPageView.svelte (469 lines, read // in full for this port). The surface a CONTEXTUAL musician click lands on: a // name, a role, and a grid of Qobuz albums whose title/artist matched the name. // // THE REFERENCE IS TAURI, NOT SLINT, for this module only (00-CONTRACT §0, the // owner's ruling). Slint's musician page is cited nowhere below; where the two // disagree Tauri wins, and the Slint page's own defects (no error state, so a // network failure renders "No album appearances found."; a downsized 18px name) // are not reproduced. // // Layout, read off the .svelte (every number is that file's): // :216-226 sticky header — padding 24/24/16 over a 56px row, 1px bottom // border, background bg-primary // :253-263 56x56 circular avatar, surface-elevated, User glyph 32, muted. // There is NO photo, ever: ResolvedMusician has no image field // (02-tauri-musician.md §1.3) // :271-283 name h1 24/700, role 14 muted CAPITALIZED // :285-311 content padding 24; section margin-bottom 32; section title // 18/600 with a 14/400 muted "(N)" count // :314-344 Bands & Projects — chips, flex-wrap, gap 10, padding 10/16 // :347-351 Appears On grid: repeat(auto-fill, minmax(160px, 1fr)), gap 20 — // a STRETCHING grid, so the cell width is computed, not fixed // :353-426 card: artwork 1:1 radius 8 (no shadow), title 14/500, artist // 12 muted, meta row gap 8 margin-top 4 = date + role badge // :429-440 the three state boxes: column, centred, gap 12, padding 48, // muted 14 // :443-468 Load more: 10/24 padded button, surface-elevated, radius 8, // disabled at 0.6 // // WHAT THIS PAGE DELIBERATELY DIVERGES ON (00-CONTRACT §6, do not "fix" back): // - DV-15 NO per-view back button. Tauri draws a 36px .back-btn at the head // of its sticky header; in this port back/forward live permanently in // the shell HeaderBar, mounted above the router. The header stack // therefore starts at x=40 — Tauri's 24px padding plus the 16px gap // that sat between the button and the avatar, with the 36px button // itself removed. Same arithmetic ArtistReleasesView.qml:27-31 uses // for its x=48 (32 + 16). // - DV-19 the role badge (.role-badge, Tauri radius 10) drops to Radius.sm. // Size, padding, type and colour are Tauri's to the pixel; only the // corner changes. ADR-008 is Active and scoped to "any future UI // surface", and a 10px label in a 2/8 box at radius 10 is that ADR's // literal definition of a pill (owner ruling R5). // - §5.4 `releaseDate` renders IN FULL — "1994-09-27", not "1994". Tauri's // field is named `year` and its CSS class is `.year`, but the backend // assigns `release_date_original` verbatim and the page prints it // raw. Both backends do this deliberately. Truncating it would be // inference from a field NAME, which this contract forbids. // - §5.2 the page is FULLY KEYBOARD-OPERABLE. The Tauri spec's "no keyboard // handling, no focus management" is true of its BINDINGS and false of // its BEHAVIOUR: every control there is a native