DevTools
@theme-kit/devtools
@theme-kit/devtools ships an inspector, a plugin, and a ready-made panel for debugging every theme change. It records lifecycle events, performance timings, state snapshots and the flattened CSS-variable output of the active theme.
1Quick start
Attach the plugin to your runtime and a panel to your page.
1import { createThemeRuntime } from "@theme-kit/core";
2import { createDevToolsPlugin, createDevToolsPanel } from "@theme-kit/devtools";
3
4const runtime = createThemeRuntime({
5 themes,
6 plugins: [createDevToolsPlugin()],
7});
8
9// Optional: mount the UI panel anywhere
10const panel = createDevToolsPanel(
11 runtime.plugins.get("devtools-inspector") as any,
12);
13document.body.appendChild(panel);2createDevToolsPlugin(options)
A Theme Kit plugin that instantiates an inspector, binds it to the runtime and exposes it on window.__THEME_KIT_DEVTOOLS__ so extensions can find it.
1const plugin = createDevToolsPlugin({ maxEntries: 200, maxPerfEntries: 100 });
2
3const runtime = createThemeRuntime({ themes, plugins: [plugin] });
4
5plugin.getInspector().getState();
6// {
7// currentTheme: ThemeDefinition,
8// selection: { mode, family },
9// history: [{ index, point: { theme, selection } }],
10// entries: [{ type, timestamp, label, data }],
11// performance: [{ duration, type, timestamp }],
12// cssVariables: { "--theme-color-primary": "#6366f1", ... },
13// }Internally it subscribes to
beforeThemeChange / afterThemeChange to record perf entries and emits a theme-change event entry on every switch.3createDevToolsInspector(options)
The standalone recorder — use it directly if you are not going through the plugin. Records theme-change entries, lifecycle performance events and state snapshots.
1const inspector = createDevToolsInspector();
2
3// Read what has happened
4inspector.getEntries();
5// [{ type: "theme-change", timestamp: 1712345678901, label: "Theme changed", data: {} }]
6
7inspector.getPerformance();
8// [{ duration: 0, type: "afterThemeChange", timestamp: 1712345678901 }]
9
10// Jump through history
11inspector.jump(0); // restores snapshot at index 0
12
13// Inspect live state
14inspector.getState();
15inspector.getCSSVariables();
16
17// Export
18inspector.exportState(); // JSON string of the full state
19inspector.exportCSS(); // { "--theme-color-primary": "#6366f1", ... }
20
21inspector.clearEntries();
22inspector.clearPerformance();
23inspector.destroy();Capped at
maxEntries (default 200) and maxPerfEntries (default 100).4createDevToolsPanel(inspector)
Renders a floating, framework-free panel (plain DOM, no dependencies) with five tabs.
const panel = createDevToolsPanel(inspector);
document.body.appendChild(panel);Panel tabs
I
InspectorThe current theme and selection as pretty-printed JSON
E
EventsChronological lifecycle event entries
P
PerfbeforeThemeChange / afterThemeChange timings as bars
C
CSS VarsThe flattened --theme-* variables with color swatches
H
HistoryEvery snapshot with a one-click Jump to restore it
Footer buttons clear events/perf and export the state to JSON or the CSS variables to a .css file.
5Global hook
Every inspector registered via the plugin is added to a Set on window.__THEME_KIT_DEVTOOLS__ so a browser extension or your own code can enumerate and inspect all live runtimes.
1declare global {
2 interface Window {
3 __THEME_KIT_DEVTOOLS__?: Set<{
4 getState(): unknown;
5 getEntries(): unknown[];
6 getPerformance(): unknown[];
7 }>;
8 }
9}
10
11for (const inspector of window.__THEME_KIT_DEVTOOLS__ ?? []) {
12 console.log(inspector.getState());
13}6Entry types
Every recorded entry has a type field.
| Type | Meaning |
|---|---|
theme-change | The active theme changed |
mode-change | The mode changed (light / dark / system) |
family-change | The family changed (e.g. plum → mint) |
persist | Selection was persisted to storage |
restore | A snapshot was restored (undo / redo / jump) |
batch | An atomic batched update ran |