readout Modules
readout can load user modules — small web apps that add widgets, windows, and settings sections to the in-game overlay. A module is a sandboxed frontend bundle that talks to readout through a permissioned bridge, so anyone can extend the app without access to its source, and without weakening the app's security model.
These docs are the complete reference for building one.
Quick start
A module is a folder with a manifest.json and your built static assets:
my-module/
manifest.json
index.html ← the entry; loads your JS
index.js ← calls activate(...) from @readout/sdk
... ← any other assets (css, images)
A minimal index.html:
<!doctype html>
<html>
<head><meta charset="utf-8" /></head>
<body>
<script type="module" src="./index.js"></script>
</body>
</html>
And index.js:
import { activate } from '@readout/sdk'
activate((ps) => {
ps.registerWidget({
id: 'badge',
gated: false,
render(root) {
root.textContent = 'Hello from my module'
// ps.host.* needs the matching permission; subscribe() returns an unsubscribe.
return ps.host.nowPlaying.subscribe((t) => {
root.textContent = t ? `${t.title} — ${t.artist}` : 'Nothing playing'
})
},
})
})
No build step is required: the host injects an import map so @readout/sdk resolves at runtime. To get
types and editor help, install the SDK as a dev dependency and keep it external in your bundler.
Where to next
- Installing modules — drop-in folder vs.
.zip, and the consent prompt. - manifest.json — every field, with validation rules.
- Permissions — what each capability unlocks.
- Surfaces — widgets, windows, settings.
- SDK API — the full
@readout/sdkreference. - Styling — theme variables and the base stylesheet.
- Examples — complete, copy-pasteable modules.
- Security model — how a module is sandboxed.