feat(studio): GPU live gallery cards via a leased PreviewHost service#118
Open
Yona-Appletree wants to merge 1 commit into
Open
feat(studio): GPU live gallery cards via a leased PreviewHost service#118Yona-Appletree wants to merge 1 commit into
Yona-Appletree wants to merge 1 commit into
Conversation
Home gallery cards (Examples + Your projects) now render live GPU-rendered thumbnails through a reusable preview service, replacing CardThumb's static gradient. Consumes the lp-gfx M3 browser machinery (worker WebGPU device, tiered runtimes, OffscreenCanvas zero-readback surface path) that previously only the dev preview-lab exercised. ADR: docs/adr/2026-07-16-preview-host.md (PreviewHost — leased, pooled, budgeted project previews). - DestroyRuntime/RuntimeDestroyed worker envelopes + fw-browser runtime disposal (same-bundle wire, no WIRE_PROTO_VERSION bump); fixes a latent runtime-id reuse bug (len()+1 -> monotonic ids). - lpa-studio-core app::preview_host: pool of 2 explicit-tick preview workers (device-lost isolation, not CPU — GPU-bound per POC-A + preview-lab), slot leases over both content sources (embedded examples; library projects materialized by uid), one host-side deadline scheduler (per-slot ~12fps, in-flight backpressure, visibility suspend, live-slot cap with LRU eviction via DestroyRuntime), per-slot observable status, deliberate worker recycle with a 2-strike flap guard, PreviewProfile seam reserved for preview-mode customization (auto input playback, audio reactivity). 18 unit tests on the pure policy layer. - lpa-studio-web home: layered CardThumb (live canvas -> M6 snapshot seam (sourceless until primary-visual capture lands) -> gradient), use_thumb_preview hook (lazy app-lifetime host, canvas generation remounts, IntersectionObserver -> set_visible, error -> remount + re-lease), tier badges per the fidelity-tiers ADR, new live-thumb-states story. Story baselines: home-gallery overview + live-thumb-states (ours); 22 non-gallery PNGs re-rendered byte-different but verified visually identical (capture environment drift; nondeterminism filed as its own task). Verified live in-browser: example card boots the pool, deploys, and animates on the GPU tier with badge; zero console errors. just check / build-ci / test green; story-check green modulo the pre-existing capture nondeterminism. Plan: ~/.photomancer/planning/lp2025/2026-07-16-gpu-live-gallery-cards/ Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Home gallery cards now render live GPU thumbnails. This wires the lp-gfx M3 browser machinery (previously exercised only by the dev preview-lab) into the product through a new reusable PreviewHost service, per the plan + interactive design session (2026-07-16) and ADR
docs/adr/2026-07-16-preview-host.md.![verified live: example card animating on the GPU tier with badge]
Verified end-to-end in-browser: the example card boots the worker pool, deploys, crossfades from its gradient to a live animating GPU-tier frame with a visible GPU badge; zero console errors.
What's here
DestroyRuntime/RuntimeDestroyedworker envelopes + fw-browser runtime disposal (same-bundle wire → noWIRE_PROTO_VERSIONbump). Includes a latent-bug fix: runtime ids werelen()+1and would have re-issued a live id after a destroy — now monotonic.lpa-studio-core::app::preview_host— the service (see ADR): pool of 2 explicit-tick preview workers (device-lost isolation, not CPU parallelism), slot leases over both content sources (embedded examples; library projects materialized by uid), one host-side deadline scheduler (per-slot ~12 fps, in-flight backpressure, visibility suspend, live-slot cap with LRU eviction), per-slot observable status, deliberate worker recycle with a 2-strike flap guard, and the reserved PreviewProfile seam (future: auto input playback, audio-reactive preview, preview-mode authoring). 18 unit tests on the pure policy layer.CardThumb(live canvas → snapshot seam, sourceless until M6's save-time capture lands → gradient+initial),use_thumb_previewhook (lazy app-lifetime host; canvas generation remounts —transferControlToOffscreenis one-shot; IntersectionObserver →set_visible; error → remount + re-lease), tier badges per the fidelity-tiers ADR, newlive-thumb-statesstory.Review callouts
PreviewTierinstead of the wasm-gated lpa-link tier type;Example(String)ids;LibraryHostseam parameter; public policy layer (native dead-code avoidance);status_revision()/presented_frames()observational methods; recycle strike cap.studio-story-checkruns flag different stories with sub-1% pixel flicker — pre-existing capture nondeterminism, filed as its own task.visual.outis exactly M6's primary-visual contract; the snapshot layer awaits their save-time capture.Validation
just check/just build-ci/just testgreencargo test -p lpa-studio-core473 green (18 new); clippy-D warningsclean native + wasm32Plan:
~/.photomancer/planning/lp2025/2026-07-16-gpu-live-gallery-cards/(implementation log in_DONE.md)🤖 Generated with Claude Code