Skip to content
Mlola UI
  • Introduction
  • Theming
  • Quality
  • Versions
  • Coding agents
  • Mlola Render
  • AI integration
  • All components
  • Migrate from shadcn/ui
  • Workbench
  • Icons
  • AccordionA collapsible content panel supporting single and multiple open modes
  • Activity HeatmapActivity by day in GitHub's calendar grid, with quantile shading, a keyboard grid and hover detail
  • AlertA status banner with variants, dismiss action, and optional action slot
  • App ShellA resizable, foldable sidebar with sections and items that becomes a drawer on small screens
  • AvatarUser avatar with image, initials fallback, and status indicator
  • BadgeA small status or label badge with color variants, dot indicator, and removal
  • Bar ChartBars per category, grouped or stacked, standing up or lying across, with rounded ends and keyboard reading
  • Block EditorA block editor: slash commands, Markdown shortcuts, to-dos, callouts, drag to reorder, a selection bubble and AI that streams into the page
  • BotAn expressive companion whose body morphs between shapes on springs and whose face carries the assistant's state
  • BreadcrumbNavigation breadcrumb trail with custom separators and responsive collapse
  • ButtonA versatile button component with multiple variants, sizes, and states
  • CalendarA month grid for one date, a range or several, with min and max, blocked days, two-month view and full keyboard paging
  • CanvasAn infinite surface to pan and zoom, with a dotted grid, zoom controls, floating panels and collaborators' cursors
  • Canvas ToolbarA floating tool palette with single-key shortcuts, roving focus and room for undo and redo
  • CardA compound card with header, content, and footer slots in four surface variants
  • CarouselOne slide at a time with previous/next controls and a roving dot group
  • ChartThe shared chart frame: scales, nice ticks, monotone curves, stacking, legend, tooltip and an accessible data table
  • CheckboxAn accessible checkbox with label, description, error, and indeterminate state
  • CitationNumbered inline sources with hover previews and a matching source list
  • Code BlockHighlighted code with a filename, line numbers, marked lines and copy; its palette is Mlola's contrast-solved text roles
  • Color PickerA color field with a saturation area, hue and opacity, hex, rgb or oklch, an eyedropper, presets and a contrast check
  • ComboboxA text field that filters a long list as you type, with grouping, descriptions and creating what is missing
  • Command MenuThe ⌘K palette: ranked commands with shortcuts, keyboard navigation and matched letters bolded
  • Commit HistoryA git log with a branch graph, refs, CI checks, authors and relative times
  • Confidence TextAn answer that marks where the model is unsure, with the confidence spoken to screen readers
  • Context CardsThe passages a model retrieved before answering, with source, location, relevance and the query's words marked
  • Context MenuA right-click menu built for what was clicked, with shortcuts, typeahead, long-press on touch and Shift+F10
  • Context MeterHow full the context window is and on what, warning before answers get cut short
  • ConversationA message log that follows new content and offers a way back when the reader scrolls up
  • Copy ButtonCopies a value to the clipboard and confirms it, with the outcome spoken to screen readers and a refusal explained
  • Data GridA spreadsheet-grade table: virtualized rows, pinned and resizable columns, sorting, cell ranges, inline editing, copy and paste, totals
  • Date PickerA date field that opens a calendar, for one date or a range with presets, shown in the reader's format and stored as ISO
  • DialA value chosen by turning a knob, with a press on the ring to jump, a hold to turn by finger, Escape to undo a turn and the keys of a slider
  • Diff ViewUnified or split file diffs from before/after text or a patch, with in-line change marks and folded unchanged lines
  • Donut ChartParts of a whole as a ring whose center reads the slice you point at
  • Dropdown MenuA keyboard-navigable dropdown menu with icons, shortcuts, and danger items
  • DropzoneDrop, choose or paste files; checked for type, size and count before they are handed over
  • Editor TabsOpen files across an editor: unsaved dots, git status, preview tabs and names that disambiguate twins
  • Empty StateWhat a screen says when there is nothing to show yet, and the way forward
  • Eval GridTest cases against model and prompt variants: pass rates, scores, latency and cost, disagreements, and each answer diffed against the expected one
  • File ChangesAn agent's changed files as one summary line that opens into each file's status and size of change
  • File TreeA project's files as a keyboard-first tree with folder guides, file-type badges and git status
  • Filter BarFilters as editable sentences, "Status is In progress", with an applyFilters helper
  • Funnel ChartStages of a funnel with step conversion and drop-off between each
  • GanttA roadmap timeline: grouped bars you drag and resize, milestones, dependency arrows, today and three zoom levels
  • Hover CardA preview card that opens when the pointer rests on a link or name, and on keyboard focus
  • InputText input with variants, sizes, label, hint, and error states
  • KanbanColumns of cards that move by drag or keyboard, with room-making drops, edge scrolling, folding columns and limits
  • KbdKeys and platform-aware shortcuts: mod+k reads ⌘K on a Mac and Ctrl K elsewhere, spoken as words
  • Line ChartLines and areas over a sequence, stacked or overlaid, with a crosshair, keyboard reading and dashed targets
  • MessageOne conversation turn with actions, feedback, answer versions and a facts line
  • MinimapThe whole canvas in miniature, with the view outlined; press or drag to move there
  • ModalAccessible dialog overlay with focus trap, escape handling, and scroll lock
  • Model CompareThe same prompt streamed to several models side by side, blind by default, with time to first token, speed and a vote
  • Model PickerChoose a model by speed, reasoning depth and context window, built on Select
  • Node GraphA node editor for agent workflows: drag nodes, connect ports, refuse loops and watch a run flow through the edges
  • Number InputA number field formatted at rest in the reader's locale, with steppers you can hold, arrows, bounds and precision
  • OrbThe assistant's presence: idle, listening, thinking and speaking, colored by the theme and driven by live audio
  • OTP InputA one-time code as separate boxes that type, delete, paste and autofill like one field
  • PaginationPage navigation with prev/next, page numbers, and ellipsis for large ranges
  • Password InputA password field with a show and hide toggle and, when choosing a new password, a meter that says how strong it is and what would make it stronger
  • PopoverA non-modal layer anchored to its trigger that flips and shifts to stay on screen
  • Priority IconA work item priority as signal bars, with a filled alert for urgent
  • ProgressHorizontal and circular progress indicators with variants and indeterminate mode
  • Prompt InputA growing composer that sends on Enter, never mid-IME, with attachments, tools and a stop button
  • Prompt PlaygroundA system prompt and a template whose variables become fields, with model settings, saved versions and a run history
  • Property PickerA small trigger that opens a searchable menu to set a property: status, priority, assignee or labels, one or many
  • Radar ChartSeveral series compared across the same qualities on a spider web, with highlighting and a tooltip
  • Radio GroupA native radio group with vertical and horizontal orientations
  • RatingStar rating with exact fractional fill and optional review count
  • Render ProDraws the interface an agent composed from the Mlola Render Pro catalog: every free component, plus charts and a data grid a person can edit
  • Render SurfaceDraws the interface an agent composed as A2UI messages, checked against the Mlola Render catalog and built from Mlola components
  • ResizableTwo panes and a keyboard-accessible handle between them
  • Rich Text EditorA modern rich text editor: headings, marks, lists, quotes, code and links, with Markdown shortcuts as you type and paste cleaned to what it owns
  • Scatter ChartPoints or bubbles on two measures, with series, keyboard stepping and a tooltip
  • SchedulerA day, three-day and week calendar where events are drawn, moved and resized by pointer or keyboard, with overlaps laid out side by side
  • Segmented ControlSingle-choice control that swaps between a small set of options
  • SelectCustom searchable dropdown with option groups, keyboard navigation, and clearing
  • Selection ActionsSelect text and AI actions appear above it: rewrite, explain, shorten
  • SheetA slide-over panel from any screen edge with header, body, and footer sections
  • SkeletonShimmering loading placeholders for text, avatars, and cards
  • SliderAn accessible single-value slider with keyboard support and pointer dragging
  • Source ControlBranch sync state, staged and unstaged changes, and a commit box whose message a model can stream in
  • SparklineA tiny axis-free trend line for stat cards, tables and lists
  • SpinnerWork in progress whose end is unknown, drawn in the color of the text around it and named for screen readers when it stands alone
  • StatOne number with what it measures, how it moved and a small trend line, for the top of a dashboard
  • Status IconA work item status as one glyph: backlog, todo, in progress, in review, done and canceled, readable without color
  • StepperProgress through a flow of steps, horizontal or vertical, clickable, condensing to "Step 2 of 4" when narrow
  • Streaming TextText that arrives in pieces, revealed at a steady reading rate that catches up on bursts, with fresh runs fading in
  • Suggested EditAn AI rewrite shown as word-level tracked changes, each accepted or rejected on its own or all at once
  • SuggestionsPrompt starters and follow-ups as a wrapping or swipeable row
  • TableA compositional data table with sortable columns, striped rows, density sizes, and footer totals
  • TabsTabbed interface with underline, pills, and enclosed variants
  • Tag InputMany short values in one field: add with Enter or a comma, paste lists, remove with Backspace, with suggestions and validation
  • Task ListAn agent's plan as it runs: status per step, nested subtasks, progress announced as it changes
  • TerminalCommand output with ANSI colors mapped to theme roles, exit status, follow-on-output scrolling and an optional input with history
  • TextareaMulti-line text that grows as it is written, with a counter near its limit
  • ThinkingA model's reasoning with a live timer that folds into “Thought for 8s”, plus shimmer, dots and orbit indicators
  • Time PickerA time field of typeable spinbuttons in 12- or 24-hour time, with a quick list; the value is always HH:MM
  • TimelineA vertical event timeline with status dots, timestamps, and custom icon nodes
  • ToastToast notification system with an imperative API, auto-dismiss, and stacking
  • ToggleiOS-style switch and button-style toggle with controlled and uncontrolled modes
  • Tool CallA model's tool use as an expandable card, with input, output, timing and human approval
  • TooltipHover and focus tooltip with four placements, delay, and arrow
  • TourA guided product tour that spotlights parts of the page step by step, with keyboard control and a focus trap
  • Trace ViewerOne agent run span by span: a tree on a timeline with the slow and failing steps marked, totals for time, tokens and cost, and each span's input and output
  • TranscriptA call or meeting transcript that follows playback word by word, with speakers, search and a summary
  • TreemapNested rectangles sized by value, laid out as squares as far as possible
  • Virtual ListA long list that renders only what is on screen, measures rows of any height and loads more near the end
  • Voice WaveMirrored audio bars for microphone input or the assistant's voice, fed by a live meter
  • WhiteboardShapes, arrows, freehand, text and sticky notes on an infinite canvas, with selection, resize, color, undo and presence
GitHubv1.15.2Studio

Coding agents

Most UI is now written with a model at the keyboard. Left alone, it recalls the utility classes it was trained on. One command tells it this UI is Mlola, and an MCP server answers its questions from the same registry the CLI installs from, so what it writes is what exists.

One command

Initializing a project also writes the instructions its agents read. Every file is merged: anything already in AGENTS.md, CLAUDE.md or .mcp.json stays as it was, and the Mlola section sits between markers so a later run replaces only that. Pass --no-agents to init to skip them.

Terminal
npx mlola-ui init      # a new project: config, styles and agent instructions
npx mlola-ui agents    # an existing project: agent instructions only, refreshed
FileWhat it does
mlola.agents.mdThe design guide: every class and data-* value, every token by purpose, and the rules for new UI. Generated from the stylesheet, refreshed by each run.
AGENTS.mdA short section between markers, read by Codex, Cursor and most agents: this UI is Mlola, read the guide, compose first, never write a color by hand.
CLAUDE.mdImports AGENTS.md, so Claude Code reads the same section.
.mcp.jsonStarts the Mlola MCP server for Claude Code and other agents that read it.
.claude/settings.jsonA hook for Claude Code: after it edits a file, the check runs on that file and what it finds goes back to the agent to fix. Pass --no-hooks to leave it out.
.cursor/mcp.json and .cursor/rules/mlola.mdcWhen the project uses Cursor: the server and an always-on rule.
.vscode/mcp.jsonWhen the project uses VS Code: the server.
.github/workflows/mlola-check.ymlWith --ci only: the check on every pull request.

The MCP server

npx mlola-ui mcp speaks the Model Context Protocol over stdio. It needs no key and no network: every answer comes from the registry bundled with the CLI, so it always matches what add installs. Your agent starts it from the project folder, since installing writes there. Run by hand, it says so on one line and then waits quietly for an agent to talk to it; Ctrl+C stops it.

It is listed in the official MCP Registry as io.github.mlolahq/mlola-ui, local and remote, so clients that browse the registry find it by name. Each release updates the listing.

Claude Code, when you did not run init:

Terminal
claude mcp add mlola --scope project -- npx -y mlola-ui mcp

Cursor (.cursor/mcp.json), Claude Code (.mcp.json) and other agents that read the same shape:

JSON
{
  "mcpServers": {
    "mlola": { "command": "npx", "args": ["-y", "mlola-ui", "mcp"] }
  }
}

VS Code (.vscode/mcp.json):

JSON
{
  "servers": {
    "mlola": { "type": "stdio", "command": "npx", "args": ["-y", "mlola-ui", "mcp"] }
  }
}

Codex:

Terminal
# ~/.codex/config.toml
[mcp_servers.mlola]
command = "npx"
args = ["-y", "mlola-ui", "mcp"]

The remote server

For an agent that cannot run a command in your project, such as a chat app or a hosted editor, the same server answers at https://ui.mlola.com/mcp over Streamable HTTP. It needs no account. It has the same search, component, token, rule and markup-check tools, and gives the install commands to run instead of installing, since it cannot write to your project. Mlola Pro items are described there; their source arrives with a license through npx mlola-ui add.

In a chat app that takes custom MCP connectors, such as claude.ai or ChatGPT, add a connector with this address. The server reads only the public registry, so it asks for no sign-in. It answers up to 10 requests a second from one address, with room for a burst of 100, far more than an agent sends; past that it replies 429 for a moment. In Claude Code, or in any client that takes an HTTP server:

Terminal
claude mcp add --transport http mlola https://ui.mlola.com/mcp
JSON
{
  "mcpServers": {
    "mlola": { "type": "http", "url": "https://ui.mlola.com/mcp" }
  }
}

What it answers

ToolForServer
get_design_rulesHow to build UI the Mlola way: compose first, color by role, measure with the scales, shared state words, touch and focus. Also the project setup (the theme on <html>, every theme's fonts, the Next.js root layout), what each layout primitive does, and the stylesheet link and script for a page with no build step.Both
search_componentsComponents, blocks, pages and templates by what they do, free and Mlola Pro.Both
get_componentThe import, every prop with fixed values and its default, the classes it styles and the data-* values each reacts to, and the install command. Optionally the source of a free component.Both
get_tokensThe --ml-* tokens grouped by purpose: planes, color roles, spacing, type, density, shape, depth, motion, layers.Both
check_markupClasses and tokens that do not exist, with the closest that do; variant classes; data-* values and React props a component does not take; a control's class on an element that cannot be operated; buttons, links, fields and images with no name; utility classes; a borrowed data-mode. In style attributes, <style> blocks and utility classes, what is typed by hand: colors, spacing, type sizes, radii, shadows, durations and layers, overridden theme tokens and text faded with opacity. Each issue names its line and the fix.Both
get_render_catalogThe Mlola Render catalog: the components an agent may compose at runtime as A2UI messages, each prop and value, and examples. Or the A2UI catalog itself.Both
check_renderChecks A2UI messages before they render: components, props and values that do not exist, colors set by hand, fields without a name, a broken tree, headings that skip a level. Each error names its path and the fix.Both
render_uiShows a checked surface in the conversation as an MCP App, where the host shows apps; a pressed button comes back as the person's next message. Elsewhere it answers with the check's report.Both
audit_pageOpens a page of the running app, or an HTML file, on a desktop and a phone, light and dark, and reports what only shows once it is drawn: text cut off, a control over text, fields that do not line up, sideways scroll, a menu past the window's edge, text below the contrast floor, an error the page threw.Local
add_componentsInstalls components with the CLI, dependencies and styles included.Local
init_projectSets the project up, agent instructions included.Local
get_install_commandThe commands to run in the project, with the license step for Mlola Pro items, and the link and script for a page with no build step.Remote

The local server also serves the guide as the resource mlola://guide (and mlola://guide/pro once Pro items are installed), and a build_ui prompt that walks an agent through the rules, the components and the check. The remote server serves mlola://guide. The two render tools are for showing interface at runtime instead of writing code, and render_ui serves its view as the resource ui://mlola/render: see Mlola Render.

Check before finishing

The instructions ask every agent to run check_markup on what it wrote. It reads classes, data-* values and inline styles against the contract generated from the stylesheet, and says how to fix each one:

HTML
<button className="ml-button ml-button-primary p-4" data-variant="huge">Save</button>
Terminal
error    "ml-button-primary" is not a Mlola class.
         Mlola has no variant classes: use "ml-button" with a data-* attribute (data-variant, data-tone, data-size).
warning  Utility classes (p-4) do nothing here: Mlola ships no utility framework.
error    data-variant="huge" is not a value ml-button ml-button-primary takes.
         Allowed: danger, link, outline, primary, secondary, subtle.

A class that exists can still be on the wrong element, and a color that reads a token can still read one that was made up. The check also knows which elements each class is drawn on, every token by name, each component's props, and what gives a control its name:

HTML
<div className="ml-button" onClick={archive}>Archive</div>
<button type="button" className="ml-button" data-size="icon"><IconTrash /></button>
<input className="ml-input" placeholder="Search projects" />
<p style={{ color: "var(--ml-text-secondary)", fontSize: 13 }}>Updated today</p>
Terminal
error    ml-button is drawn on <button>; on a <div> it takes no focus and no key press.
         Write <button type="button" class="ml-button">, or <a href> when it leads to another page.
error    This button has no name: it holds no text, and no aria-label says what it does.
         Give an icon-only control aria-label="…" (and a tooltip or title), or put the words in a <span class="ml-visually-hidden">.
error    This field has no label: a placeholder disappears as soon as someone types.
         Name it with <label for="its id">, by wrapping it in a <label>, or with aria-label when the design shows no label.
warning  A type size is written by hand in style (fontSize: 13).
error    --ml-text-secondary is not a Mlola token: the declaration that reads it does nothing.
         Closest: --ml-text, --ml-text-muted, --ml-text-faint. List the tokens with get_tokens.

Checked without being asked

An agent told to run a check sometimes forgets. In Claude Code, init adds a hook to .claude/settings.json: after each edit, the check runs on the file that changed. When it finds nothing it stays silent; when it finds something, the report goes back to the agent, which fixes it before going on. Files that hold no markup or CSS, and files outside the project, are left alone.

.claude/settings.json
{
  "hooks": {
    "PostToolUse": [
      { "matcher": "Edit|Write|MultiEdit", "hooks": [{ "type": "command", "command": "npx -y mlola-ui check --hook" }] }
    ]
  }
}

Look at the page

Source that passes every check can still draw a page with a title cut off on a phone. An agent cannot see what it built, so npx mlola-ui audit looks for it: it opens the page in a browser at 1280 and 390 pixels, in light and dark, and reports text cut off or running out of its card, a control sitting on another element's text, fields in one row that do not line up, sideways scroll, images that did not load, a menu or dialog past the window's edge, text below 4.5:1 (3:1 when large), and any error the page threw. These are the audits Mlola runs on its own components in every theme.

Terminal
npx mlola-ui audit localhost:3000/settings   # a desktop and a phone, light and dark
npx mlola-ui audit page.html --themes all     # a file, in every theme
npx mlola-ui audit localhost:3000 --shots .audit   # and a screenshot of each view

--interact also presses what opens (menus, dialogs, tabs) and checks each state; it is off unless you ask, since it presses the page's real buttons. The local MCP server offers the same as audit_page. The browser is your project's own Playwright (npm install -D playwright): the CLI ships none and installs none. It exits with 1 when it finds a problem.

Check a whole project

An agent checks what it just wrote. npx mlola-ui check runs the same check over every HTML, JSX, TSX, Vue, Svelte, Astro and CSS file, so a screen written last month is held to the same system as the one written today. It ends with the drift: how many different colors, spacing values, type sizes and radii were typed by hand instead of read from the tokens. --fix rewrites the spacing that is exactly a step of the scale (16px, 0.5rem) as that step, and leaves a length between the steps for a person to decide.

Terminal
npx mlola-ui check            # the whole project
npx mlola-ui check src --json # one folder, every issue as data
npx mlola-ui check --fix      # put lengths that are steps of the scale back on it
Terminal
src/app.css
     2  warning  Spacing is written by hand (margin-top: 18px).
                 Measure with the scale: var(--ml-space-2), var(--ml-space-4)… (get_tokens spacing), or a calc() of its steps; space that grows with the window is var(--ml-space-fluid-sm)… to -xl. An em tuned to the font is fine; a length invented between the steps is not.
     3  error    A color is written by hand in the stylesheet.
                 Read a token: var(--ml-text), var(--ml-primary-text), var(--ml-surface)… (get_tokens). The theme then keeps its contrast in every mode.

src/invite.tsx
     3  error    A color is written by hand in style.
                 Read a token: var(--ml-text), var(--ml-primary-text), var(--ml-surface)… (get_tokens).
     3  warning  Spacing is written by hand in style (padding: 18).
                 Measure with the scale: var(--ml-space-2), var(--ml-space-4)… (get_tokens spacing), or a calc() of its steps; space that grows with the window is var(--ml-space-fluid-sm)… to -xl. An em tuned to the font is fine; a length invented between the steps is not.
     5  error    "ml-button-primary" is not a Mlola class.
                 Mlola has no variant classes: use "ml-button" with a data-* attribute (data-variant, data-tone, data-size).

Checked 2 files: 3 errors and 2 warnings in 2 files.
Drift, typed by hand instead of read from the tokens:
  2 colors: #6b7280, #fafafa
  1 spacing value: 18px ×2
  --fix puts the lengths that are exactly a step of the scale back on it.

It works in any project, so it can measure one before it uses Mlola. In a Mlola project it leaves out what the CLI installed (--all takes the copied markup in; Mlola's own stylesheets, the built theme among them, are held by the library's gates and never checked). Where Tailwind, UnoCSS or Windi is installed it leaves utility classes alone and counts only the values typed into them, like bg-[#fafafa] or p-[13px].

It exits with 1 when it finds an error (with --strict, a warning too), and on GitHub Actions each issue is also an annotation on the pull request, so new UI meets the system before it merges:

GitHub Actions
# .github/workflows/ui.yml
name: UI
on: pull_request
jobs:
  mlola:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - run: npx -y mlola-ui@latest check src

The guide, without an agent

Everything the server knows is also plain Markdown, for any assistant or any person: mlola.agents.md in the project, @mlola-ui/engine/generated/agents.md in the package, and agents.json beside it with the same facts as data. Mlola Pro adds mlola-pro.agents.md with its own classes on the first Pro install.

The site answers in Markdown too: /llms.txt maps it, every component page is Markdown at its address plus .md (button.md), and /llms-full.txt holds the free contract and every free component in one file. Mlola Pro items appear there by what they do, never as source.