Theme Provider
Applies Creator's theme tokens as CSS variables for dynamic theming.
Import/Installation
import { ThemeProvider, useTheme } from "@lottiefiles/creator-plugins-ui";Dynamic theming
The theme provider lets you pass Creator's current theme styles, or your own custom themes, to automatically style your plugin.
Preview
Usage
<ThemeProvider tokens={tokens} themeName="default">
<App />
</ThemeProvider>You can pass any CSS variable as a token. See Theming for the full list of tokens the library consumes.
Match Creator's current theme
To automatically match Creator's current theme, your plugin can read Creator's current theme tokens and pass them to ThemeProvider.
Step 1: Add the head script
Add this <script> block inside <head> in your plugin's index.html. It catches theme tokens via postMessage before React mounts, eliminating an initial flash of default-themed content.
The vite-ignore attribute prevents Vite from stripping the inline script during production builds.
<script vite-ignore>
(() => {
function onTheme(event) {
const msg = event.data?.pluginMessage;
if (!msg || msg.type !== "change:theme") return;
const { tokens } = msg;
if (tokens && typeof tokens === "object") {
const root = document.documentElement;
for (const [key, value] of Object.entries(tokens)) {
root.style.setProperty(key, value);
}
document.body.setAttribute("data-theme-ready", "");
}
window.removeEventListener("message", onTheme);
}
window.addEventListener("message", onTheme);
if (window.parent !== window) {
window.parent.postMessage({ pluginMessage: { type: "ui-ready" } }, "*");
}
})();
</script>Step 2: Plugin sandbox (plugin.ts)
creator.ui.show({ width: 360, height: 500 });
// set the theme on plugin load
creator.ui.onMessage((msg) => {
if (msg.type === "ui-ready") {
const { tokens, themeName } = creator.ui.theme;
creator.ui.postMessage({ type: "change:theme", tokens, themeName });
}
});
// update the theme when Creator's theme changes
creator.on("change:theme", ({ tokens, themeName }) => {
creator.ui.postMessage({ type: "change:theme", tokens, themeName });
});Step 3: Plugin UI (app.tsx)
import { useState, useEffect } from "react";
import { ThemeProvider, Button } from "@lottiefiles/creator-plugins-ui";
function App() {
const [tokens, setTokens] = useState<Record<string, string>>();
const [themeName, setThemeName] = useState<string>();
useEffect(() => {
window.addEventListener("message", (e) => {
const msg = e.data?.pluginMessage;
if (msg?.type === "change:theme") {
setTokens(msg.tokens);
setThemeName(msg.themeName);
}
});
parent.postMessage({ pluginMessage: { type: "ui-ready" } }, "*");
}, []);
return (
<ThemeProvider tokens={tokens} themeName={themeName}>
<Button>Themed Button</Button>
</ThemeProvider>
);
}How it works
The head script applies Creator's theme tokens instantly when the first change:theme message arrives — before React mounts. Once React boots, ThemeProvider takes over for any subsequent theme changes. The data-theme-ready attribute on <body> coordinates the handoff so ThemeProvider doesn't reset the head script's tokens on mount.
Transparent background default
When ThemeProvider has no tokens (or tokens are cleared), it sets --background to transparent. This is intentional for Creator's iframe context — it lets the host page's background show through.
If you're using ThemeProvider outside of Creator's iframe, set --background explicitly in your tokens to avoid an invisible background.
Props
| Prop | Type | Default | Required | Description |
|---|---|---|---|---|
| children | ReactNode | — | Yes | Content to render inside the theme context. |
| tokens | Record<string, string> | — | No | Current theme tokens (CSS variable name → value). |
| themeName | string | — | No | Optional name of the active theme. Available via the `useTheme()` hook. |