Josh Puckett

4 min read Original article ↗

DialKit

A floating control panel for React, Solid, Svelte, and Vue: sliders, toggles, color pickers, spring editors, easing curves, and keyboard shortcuts wired directly to your UI values. Auto-detects control types from your config, fully typed, with built-in presets and JSON export.

DialKit demo showing a photo stack with a floating control panel

View Demo

Installation

Install DialKit and its animation dependency via npm:

Or just tell your agent to set it up:

If installing manually, add <DialRoot /> to your layout, and import the styles:

That's it. Now you can use the useDialKit hook in any component.

Prompts to get started

The easiest way to start using DialKit is to describe what you want and let your coding agent wire it up. Here are a few prompts to try.

Add DialKit to an existing animation:

Build something new with DialKit from scratch:

Tune layout and spacing:

Explore visual variations:

Usage

Call useDialKit with a name and config object. Each call creates a collapsible folder in the panel with controls auto-generated from your config.

Config Types

The config object determines what controls appear in the panel.

FormatControlDescription
[default, min, max, step?]SliderExplicit range slider with optional step size
numberSliderAuto-inferred range based on value
booleanToggleOn/off segmented control
"#ff5500"Color PickerAuto-detected from hex strings
"Hello"Text InputAuto-detected from non-hex strings
{ type: "select", ... }SelectDropdown with options array
{ type: "spring", ... }Spring EditorVisual spring curve with Time/Physics modes
{ type: "easing", ... }Easing EditorCubic bezier curve with duration and visual preview
{ type: "action" }ButtonTriggers onAction callback
{ nested: ... }FolderCollapsible group. Add _collapsed: true to start closed

API Reference

useDialKit

The main hook. Returns a reactive object with current parameter values.

PropTypeDescription
namestringPanel folder title
configDialConfigParameter definitions (see Config Types)
options.onAction(action: string) => voidCallback when action buttons are clicked
options.shortcutsRecord<string, ShortcutConfig>Keyboard shortcuts for controls

DialRoot

Renders the floating control panel. Mount once at your app root.

PropTypeDescription
position'top-right' | 'top-left' | 'bottom-right' | 'bottom-left'Panel corner position (default: 'top-right')
defaultOpenbooleanWhether the panel starts open (default: true)
mode'popover' | 'inline'Floating popover or embedded in layout (default: 'popover')
theme'light' | 'dark' | 'system'Color theme (default: 'system')
productionEnabledbooleanShow panel in production builds (default: false)

In popover mode, the collapsed bubble is draggable — drag it anywhere on screen, and the panel snaps to the nearest side when opened. Use mode="inline" to embed the panel directly in your layout instead of as a floating popover.

Toggle

Booleans create an on/off segmented control.

Spring Config

Spring configs get a visual editor with live curve preview. Two modes available:

Easing Config

Easing configs get a visual cubic bezier editor with a live curve preview.

The returned config is passed directly to Motion's transition prop, just like spring configs.

Color

Hex strings are auto-detected as color pickers with a swatch and editable hex value.

Text

Non-hex strings are auto-detected as text inputs. Use the explicit form for a placeholder.

Select

Dropdown control with an array of options. Supports plain strings or value/label objects.

Folders

Nested objects become collapsible folders in the panel. Add _collapsed: true to start a folder closed.

Actions

Add buttons to trigger callbacks from the panel.

Keyboard Shortcuts

Assign keyboard shortcuts to controls so you can adjust values without touching the panel. Pass a shortcuts map in the options object.

ShortcutConfig

PropTypeDescription
keystringTrigger key (e.g. "b", "s") — optional for scroll-only
modifier'alt' | 'shift' | 'meta'Optional modifier key
mode'fine' | 'normal' | 'coarse'Precision level (default: 'normal')
interaction'scroll' | 'drag' | 'move' | 'scroll-only'Input method (default: 'scroll')

Interaction types

InteractionDescriptionExample pill
scrollHold key + scrollB+Scroll
dragHold key + click dragS+Drag
moveHold key + move mouseO+Move
scroll-onlyScroll anywhere, no keyScroll

Each control with a shortcut shows a pill badge next to its label. The pill highlights when the shortcut key is held. Shortcuts are auto-disabled when a text input is focused.

Frameworks

DialKit supports React, Solid, Svelte 5, and Vue 3. Each framework has its own entry point with an identical API surface.

Solid

Import from dialkit/solid. Uses createDialKit which returns an accessor — call params() to read values.

Svelte

Import from dialkit/svelte. Works with Svelte 5 (≥5.8.0). Returns a reactive object — access values directly.

Vue

Import from dialkit/vue. Works with Vue 3 (≥3.3.0). Returns a reactive object.