Skip to content

feat(scenes): carry chromeTheme into the picture-in-picture window - #38

Merged
karngyan merged 1 commit into
mainfrom
feat/pip-window-chrome-theme
Jul 24, 2026
Merged

feat(scenes): carry chromeTheme into the picture-in-picture window#38
karngyan merged 1 commit into
mainfrom
feat/pip-window-chrome-theme

Conversation

@karngyan

Copy link
Copy Markdown
Collaborator

Follow-up to #36, which themed the in-page pip placeholder. This one covers the pip window itself, the piece I called out as out of scope there.

What was wrong

The pip window is a separate document that never loads kino.css, so mountPipOverlay styled everything with hardcoded dark literals (bar gradient to rgba(0,0,0,0.85), #fff icons, white progress) and the provider painted the window body #000. In light mode that read as a dark player bolted onto a light one, plus a black flash behind a light stage before the mirror painted.

The fix

  • The overlay injects a token sheet into the pip document: dark on the root, light overriding it under [data-kino-theme="light"], mirroring how .kino themes itself. Layout stays inline; every color is now a token, so a flip is one attribute change.
  • mountPipOverlay returns { setTheme, destroy } instead of a bare cleanup, so the theme can change while the window stays open. Internal API, not exported from the package.
  • createScenesProvider takes chromeTheme; ScenesProvider gains setChromeTheme. ScenesPlayer wires both to the chromeTheme prop it already had, mirroring how sceneTheme seeds the host then flips live.
  • The pip window backdrop follows sceneTheme, not chromeTheme: it is what shows before the mirrored stage paints, so it belongs to the stage. colorScheme on the pip document follows it too. pipStageBackdrop is opaque in both themes.

Defaults are unchanged: omit both props and dark chrome over a black backdrop is exactly what shipped.

Verification

  • pnpm test (210 passing, 6 new), pnpm typecheck, pnpm lint, pnpm format:check.
  • New tests cover the theme stamp and live flip on the overlay, the dark default, both token blocks existing for every color, the backdrop following setSceneTheme live, and a chrome flip outside pip seeding the next window.
  • Eyeballed both palettes in a browser against a light and a dark stage: light gets a white-glass bar, dark ink on the button and timecode, a light caption pill, and a dark progress line.

The pip window is a separate document that never loads kino.css, so its
controls kept a hardcoded dark palette and its body a hardcoded black, which
read as a dark player bolted onto a light one the moment a lesson ran in
light mode.

The overlay now injects a small token sheet into the pip document, dark on
the root with a light block keyed on data-kino-theme, so every color it
paints is themeable and a flip is one attribute change on a live window.
mountPipOverlay returns a handle ({ setTheme, destroy }) instead of a bare
cleanup so the theme can change while the window stays open.

createScenesProvider takes a chromeTheme option, ScenesProvider gains
setChromeTheme, and ScenesPlayer wires both to the chromeTheme prop it
already had, matching how sceneTheme rides the wire to the host.

The pip window backdrop follows sceneTheme rather than chromeTheme: it is
what shows before the mirrored stage paints, so it belongs to the stage.
colorScheme on the pip document follows it too.
@cloudflare-workers-and-pages

Copy link
Copy Markdown

Deploying with  Cloudflare Workers  Cloudflare Workers

The latest updates on your project. Learn more about integrating Git with Workers.

Status Name Latest Commit Preview URL Updated (UTC)
✅ Deployment successful!
View logs
kino 68ca82f Commit Preview URL

Branch Preview URL
Jul 24 2026, 07:25 PM

@karngyan
karngyan merged commit 5ee0a31 into main Jul 24, 2026
5 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant