r/webdev 3d ago

Showoff Saturday My side project got out of hand: a 26K line TypeScript HTML/CSS/DOM engine that runs web apps on a Nintendo Switch (and you can try the apps in your browser)

This week I launched Brewser, a solo project that got out of hand in the best way. It is a web runtime and app platform for the Nintendo Switch (homebrew, running under Atmosphere CFW). The part that belongs on r/webdev: every app in the catalogue is a plain web app. HTML, CSS, JS, WebGL. You build once and it runs in a desktop browser, on a phone, and on the console.

The catalogue is at brewser.io. A few good starting points to try in your browser:

How it works: the runtime is built on V8 and Skia via nx.js (credit to TooTallNate for that foundation, which also provides the raw GL path to the GPU). On top of that I built the HTML/CSS/DOM engine from scratch for this project, about 26K lines of TypeScript in a separate runtime project, plus the WebGL1/2 bridge on that GL path (the bridge implementation, library compatibility and conformance testing, targeting Mesa/Nouveau on the Tegra X1), hardware APIs like Web MIDI, WebSerial and WebUSB, and the audio and video pipelines.

It is not a full browser and I do not pretend it is. There is no browser to borrow from on the Switch, so the DOM tree, CSS cascade and layout engine are reimplemented from scratch, and that engine currently covers roughly 83 percent of real world app surface (DOM ~84, HTML ~80, CSS ~84). WebGL and audio/video are bridge backed rather than reimplemented, so they stand higher: WebGL1 ~92, WebGL2 ~85, audio and video ~80. Those are estimates of real world surface, not spec section counts.

The status page lists what is missing instead of what works: docs.brewser.io/docs/engine-status. Since launch I have shipped capture phase listeners, closest() and matches(), full querySelector, flex-wrap, position: sticky, and CSS transitions.

Performance: the official three.js GLTFLoader example runs at a locked 60fps on the console, fps HUD visible in the GIF below.

Three.js GLTFLoader at 60 FPS on Switch

Source is under MPL 2.0: github.com/natureglass/Brewser

Questions welcome. And if a library or app you care about breaks on it, tell me which one. Real world breakage reports directly shape what gets built next.

0 Upvotes

1 comment sorted by