feat: auto-switch background effects on device graphics capability - #395
Open
QSchlegel wants to merge 1 commit into
Open
feat: auto-switch background effects on device graphics capability#395QSchlegel wants to merge 1 commit into
QSchlegel wants to merge 1 commit into
Conversation
The three decorative surfaces (CSS aurora, WebGL marble field, three.js globe) rendered unconditionally for everyone, which is what motivated removing them outright. Instead, detect what the device can afford and render that much. - src/lib/graphics-tier.ts: pure classification of CPU cores, device memory, unmasked GPU renderer, framebuffer size, handheld-ness, reduced-motion and data-saver into high/medium/low, plus the feature set each tier may render. Split from the browser reads so it is unit testable; `high` is never returned without a usable GPU. - src/hooks/useGraphicsTier.ts: shared runtime state — one detection pass, a post-load frame-rate probe that steps the tier down when the page is not keeping budget (cached per session), a battery cap below 20% discharging, and a live reduced-motion listener. Publishes data-gfx-tier on <html> so CSS keyframes degrade with it. - Aurora keeps its layers at every tier but stops animating at low; the marble field and globe only mount at high. api-docs now loads the globe dynamically instead of shipping three.js to every visitor, and drops its full-page backdrop-filter when there is nothing behind it. - Appearance setting becomes Auto / Full / Reduced / Off (persist v2 migration from the old on/off switch) and shows what was detected and why, including an automatic step-down. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
5 tasks
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.
Alternative to #390. That PR removes the aurora, the MarbleField shader and the three.js globe for everyone; this one keeps them and decides per device whether they run.
How it decides
src/lib/graphics-tier.tsscores the signals a browser actually exposes —hardwareConcurrency,deviceMemory, the unmasked WebGL renderer string, screen area × dpr², coarse-pointer/handheld,prefers-reduced-motion,saveData— into three tiers:Reduced-motion or data-saver short-circuit straight to
low, andhighis never returned when the GPU is missing or software-rasterized (SwiftShader / llvmpipe / Basic Render Driver), whatever the CPU and memory say. Integrated Intel parts land inweak: they run the CSS aurora fine and stutter on a full-viewport fragment shader plus a globe, which is the complaint behind #390.Heuristics can be wrong, so
src/hooks/useGraphicsTier.tsbacks them with measurements:low, and it re-probes once after a downgrade to see whether that was enough. The cap is cached insessionStorage, so later navigations start already capped.prefers-reduced-motionlistener.State lives at module scope, so layout, homepage, api-docs and the new-wallet flow share one detection pass, one probe and one answer. The effective tier is published as
data-gfx-tieron<html>so purely-CSS keyframes degrade with it instead of every component threading a class down.Other changes
api-docsimported the globe statically, shipping three.js + three-globe to every visitor. It is now adynamic()import, so devices that will not draw it never download it — and its full-pagebackdrop-filter: blur(16px)is dropped when there is nothing behind it to blur.version: 2, oldbackgroundEnabled: false→off,true→auto). Auto shows what was detected and why (8 CPU cores, discrete or modern GPU) and says so when the frame-rate probe stepped it down.Test plan
npm test— 1292 passed / 2 skipped, plus 87 in the ESM project. Includes a newsrc/__tests__/graphicsTier.test.tscovering renderer classification and the device profiles the weights are calibrated against (modern desktop → high, good-GPU phone → medium, old integrated laptop → low, software rasterizer → never WebGL).npm run build(webpack) clean.next start:data-gfx-tier="high", 10 animated aurora nodes, MarbleField canvas present, globe + backdrop-filter on/api-docsreduced→ tiermedium, 0 canvases, aurora still animatinglow, 0 animated nodes, background layers still paintedoff→ no background layers, no canvas, no backdrop-filter🤖 Generated with Claude Code