Saltar al contenido principal

Theming and dark mode

The Appilot Widget renders in a closed Shadow DOM, so it never inherits your page's styles by accident, and your page never inherits the widget's. You stay in control of its appearance through configuration.

This page covers light/dark theming and brand color, both fully supported today. Layout modes beyond the floating bubble are tracked separately (see Layout modes).

Theme modes

Set the theme policy with the data-theme attribute (or the theme option in the JS API). Four values:

ValueBehavior
autoDefault. Follows the visitor's operating-system preference (prefers-color-scheme), and updates live if they change it.
lightAlways light.
darkAlways dark.
hostFollows your site's own light/dark state, live. See Match your site's theme.
<script
type="module"
src="https://cdn.appilot.com/widget/v1/appilot.esm.js"
data-theme="auto"
async
></script>
import { initAppilot } from '@appilot/widget';

initAppilot({ theme: 'auto' });
Default changed in widget v0.8.0

The default is now auto (it used to be light). If you relied on the widget always rendering light regardless of the visitor's OS, set data-theme="light" explicitly.

Match your site's theme

Most applications already have their own light/dark toggle. You have two ways to keep the assistant in lockstep with it.

Option A: data-theme="host" (no code)

Set data-theme="host" and the widget mirrors your page's own theme signal, live, with no JavaScript on your side. It reads, in order:

  1. <html data-theme="dark"> or <html data-theme="light">
  2. <html data-color-scheme="dark|light">
  3. a dark / theme-dark / dark-mode class on <html> (and the light twins)
  4. otherwise, the OS preference

It watches those with a MutationObserver, so the instant your toggle flips the attribute or class, the widget flips too. This is the recommended approach if your site advertises its scheme on the <html> element (the common convention, including Tailwind's dark class and the data-theme attribute pattern).

<!-- Your site sets <html data-theme="dark"> when the user picks dark mode -->
<script
type="module"
src="https://cdn.appilot.com/widget/v1/appilot.esm.js"
data-theme="host"
async
></script>

Option B: Appilot.setTheme() (explicit)

If your theme state does not live on <html> (for example it is held in a framework store), drive the widget explicitly from your own toggle:

// Whenever your app's theme changes:
window.Appilot.setTheme('dark'); // 'light' | 'dark' | 'auto' | 'host'

setTheme takes effect immediately and does not re-mount the widget, so the open conversation is preserved. It is available as soon as the bundle has loaded.

Which option?

Use data-theme="host" when your scheme is reflected on <html> (most sites). Use Appilot.setTheme() when it is not, or when you want full programmatic control. They are interchangeable, not exclusive.

Built-in palettes

Each mode uses Appilot's built-in palette, tuned for contrast and consistency with the rest of the assistant UI (the same design tokens the Chrome extension uses). Light renders on a white surface with a cyan accent; dark renders on a near-black surface with a brighter cyan accent. You do not need to define any colors to get a polished result in either mode.

Brand color

By default the assistant uses Appilot's cyan accent. To make it adopt your brand color, set --appilot-brand (and, optionally, a dark-mode variant --appilot-brand-dark). The accent recolors the primary surfaces (the header, the send button, selection highlights) in both themes.

There are two equivalent ways to set it.

data-accent (no CSS)

<script
type="module"
src="https://cdn.appilot.com/widget/v1/appilot.esm.js"
data-accent="#e0457b"
data-accent-dark="#ff7aa8"
async
></script>

data-accent applies to both light and dark. Add data-accent-dark only when you want a distinct (usually lighter) accent in dark mode; if you omit it, the single data-accent is used in both.

CSS custom property

The channel is a CSS custom property, and custom properties DO inherit through the Shadow DOM boundary, so you can also set it from your own stylesheet on the appilot-assistant element, including per-theme:

appilot-assistant { --appilot-brand: #e0457b; }
html[data-theme="dark"] appilot-assistant { --appilot-brand-dark: #ff7aa8; }

This is the supported brand channel. (Setting --appilot-primary directly still has no effect: the widget defines that token inside its Shadow DOM :host, which out-specifies an inherited value. --appilot-brand is read by the widget precisely so the inheritance works.)

Contrast

The accent sits behind white text in the header and on the primary button. Pick a color with enough contrast against white (a mid-to-dark tone). If your brand color is very light, use a darker data-accent and reserve the light tone for data-accent-dark.

Bubble size

The floating bubble defaults to 400px wide and up to 680px tall (capped to the viewport). Override with data-width / data-height. A bare number is treated as pixels; any CSS length (px, vh, min(...)) is accepted:

<script
type="module"
src="https://cdn.appilot.com/widget/v1/appilot.esm.js"
data-width="420"
data-height="90vh"
async
></script>

On small screens the bubble is automatically capped to the viewport regardless of these values.

Brand name

The header shows your organization's name by default. Override the displayed text with data-brand-name:

<script
type="module"
src="https://cdn.appilot.com/widget/v1/appilot.esm.js"
data-brand-name="Acme Support"
async
></script>

Layout modes

Layout modes beyond the floating bubble (a docked sidebar, an inline embed) are on the roadmap and not yet available. The bubble is the supported placement today; position it with data-position="bottom-left" / "bottom-right".