Pricing

Input handbook

v1.2.0 · @snowui-design-system/components

License: Before reading component documentation, source, or npm usage instructions for the first time, read the full LICENSE. Reuse that review for the same task and version. Public API configuration and internal implementation changes have different license implications. All components use the unified runtime package; source rights remain governed by the license.

Overview

Provide single-line entry for text, search, password, number, date, time, and color, with composable labels, icons, and validation feedback.

When to use it

Use Input for single-line entry, SearchInput for dedicated search, and Textarea for multiple lines. Compose with Field when labels, help, or errors share one surface.

  • bind:value synchronizes edits. Explicit value wins over defaultValue; number input still produces a string that applications convert for calculations.

  • name participates in form submission. Controlled forms restore their bound initial value on reset. bind:element exposes the outer Frame element, not the native input.

  • file and range are not upload or slider modes. Use as="leading"/as="trailing" for accessories; a built-in clear control can occupy trailing.

Quick start

This example shows the recommended basic composition. See the sections below for more cases and composition limits.

<script lang="ts">	import { Input, Button } from '@snowui-design-system/components';	let submitted = $state(false);	function login(event: SubmitEvent) {		event.preventDefault();		submitted = true;	}</script> <form onsubmit={login} oninput={() => submitted = false} style="display: flex; flex-direction: column; gap: var(--gap-4); width: min(100%, 22.5rem); min-width: 0;">	<Input type="email" name="email" aria-label="Email" placeholder="Email" autocomplete="username" required />	<Input type="password" name="password" aria-label="Password" placeholder="Password" autocomplete="current-password" required />	<Button type="submit" variant="filled" size="md">Log in</Button></form>

API

Keyword Type Default Description
element HTMLElement — Reference to the outer Frame root via bind:element; it is not the native input element.
type HTMLInputAttributes["type"] "text" Single-line type: text, search, email, password, url, tel, number, date, time, datetime-local, month, week, or color. Date, time, and color have a visible component layer with a native value host. file and range fall back to text; no upload or slider is provided.
gap number — Inherited Frame gap token index. Omit it to retain the original preferred gap. Explicit values override the preference; effective graphics/text spacing remains at least 4 CSS px, including zero, root font scaling and gap scaling.
value InputValue — Current value, supporting bind:value. Explicit value wins over defaultValue. Editing and built-in clearing synchronize the native input.value string. Numeric calculations require application conversion.
defaultValue InputValue — Initial value when value is absent. Input synchronizes it internally; restore an application binding explicitly in onreset if required.
placeholder string — Hint for an empty input, not an accessible label. Date/time entry retains its segmented display.
name string — Native form field name used by FormData.
disabled boolean false Prevent entry and interaction; disabled native fields are excluded from form submission.
readonly boolean false Prevent editing while preserving focus, selection, and submission. Hide built-in clear, including after custom trailing focus, and use read-only styling.
clearable boolean true Show the built-in clear X. false removes only that control, leaving editing, validation, and custom trailing content intact. Applies standalone or inside Field.
required boolean false Participate in native required validation; no application error message is generated.
autocomplete HTMLInputAttributes["autocomplete"] — Browser autofill hint such as username, email, or new-password; suggestions come from browser data.
minlength number — Native minimum length for applicable text entry and form validation.
maxlength number — Native maximum text length. Floating as="search" defaults to 100 when unspecified.
pattern string — Native full-value validation pattern for text input, without surrounding slashes. required decides whether an empty value is valid.
min number | string — Minimum number or date/time value, using that native input type’s value format.
max number | string — Maximum number or date/time value, using that native input type’s value format.
step number | string — Native step constraint: numeric units for number; browser-defined units for date/time types.
inputmode HTMLInputAttributes["inputmode"] — Soft keyboard hint such as numeric, decimal, or tel; it does not filter or validate input.
enterkeyhint HTMLInputAttributes["enterkeyhint"] — Soft keyboard return-key hint such as next, search, or done; it does not navigate or submit automatically.
spellcheck boolean — Spellcheck setting; browser and inherited context apply when absent.
list string — ID of an external native datalist; caller and browser provide the options and presentation.
accept string — Native passthrough attribute reserved for supported inputs. File mode falls back to text, so it cannot add file restrictions or upload.
multiple boolean — Native multi-value hint for supported types such as comma-separated email addresses; it does not enable multiple file upload.
capture boolean | "user" | "environment" — Reserved native capture attribute. File mode falls back to text, so no camera/file acquisition is provided.
form string — Associate an external form by ID; native submission and reset include the field even outside the form element.
autofocus boolean — Native autofocus hint for ordinary input; browser focus may already be elsewhere. Date/time display activates its first segment on initial mount. Avoid stealing focus on page load.
tabindex number — Native focus order: 0 follows natural order, -1 leaves sequential navigation, positive values force an order. Prefer natural order in normal forms.
title string — Native placeholder, also reflected in date/time/color display layers; not a label replacement.
id string — Native input ID for <label for> and associated attributes.
invalid boolean false Set invalid state alongside aria-invalid and error styling. Standalone Input shakes on error; inside Field, Field aggregates feedback.
error string | Snippet — When invalid, generate built-in error Text from a string or parameterless Snippet. No error is generated by default.
parts ComponentPartsOf<{ Text: typeof Text; Button: typeof Button }> — Configure generated error Text or action Button through parts.Text/parts.Button; configure explicit child items directly.
onclick (event: MouseEvent) => void — Called on click with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
ondblclick (event: MouseEvent) => void — Called on double-click with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
oninput (event: Event) => void — Called on input with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
onchange (event: Event) => void — Called on change with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
onfocus (event: FocusEvent) => void — Called on focus with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
onblur (event: FocusEvent) => void — Called on blur with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
onkeydown (event: KeyboardEvent) => void — Called on keydown with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
onkeyup (event: KeyboardEvent) => void — Called on keyup with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
onkeypress (event: KeyboardEvent) => void — Called on deprecated keypress with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
onpaste (event: ClipboardEvent) => void — Called on paste with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
oncopy (event: ClipboardEvent) => void — Called on copy with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
oncut (event: ClipboardEvent) => void — Called on cut with the corresponding native event; returns nothing. Use event.preventDefault() for cancelable browser defaults. It does not roll back Input value synchronization already completed.
children Snippet — Parameterless explicit children. Use as="leading" or as="trailing" for icons or accessories; trailing content replaces the built-in clear control.
allowCustomValue boolean false Only within Listbox as="search": if no option matches, Enter adds and selects the typed custom value; custom items can later be removed.

See the base component documentation for inherited capabilities not redeclared here. This table lists only named public Props declared by this component.

Usage boundaries and details

Form composition and spacing

  • Field rhythm: default 12px vertical / 16px horizontal padding and 8px gap.

  • Standalone Input has its own 12px / 16px padding and 8px internal gap.

  • Input owns icon placement: leading/trailing icons sit 16px from the nearest visible inner edge by default.

  • The built-in error icon follows the same trailing icon rule without an overlay offset.

  • Inside Field, first distinguish whether Input uses as="segment".

  • Without as="segment", Field owns padding and gap; Input drops its padding but keeps its internal gap.

  • With as="segment", Input keeps padding and gap and maintains 16px icon clearance from its border or divider.

  • Adjacent row segments have vertical dividers; adjacent column segments have horizontal dividers.

  • Only one divider appears between neighboring segments.

  • label, description, and error are content, not owners of padding, gaps, or dividers.

  • The label + host + error pattern supplies text; it does not determine padding or gap.

  • In a connected Field row or Field column, mark child inputs explicitly as="segment".

Component role

Input is the interactive host of a field, not necessarily the entire field surface:

  • Standalone Input retains its complete default input-box appearance.

  • Inside Field, Field takes over surface padding and gap unless Input is marked as="segment".

  • Combine Input with Icon, Text, Checkbox, Switch, Badge, or Frame as="row" for richer fields.

  • Text mode uses a visible native <input>. Date and color modes use a visible display layer with a hidden native host synchronized to the value.

Inherited Frame capabilities

The outer Frame retains shared capabilities:

  • responsive / stateStyle / customStates / variants / styles

  • Hover / Click / Focus / whileAppear / timeline / orchestrate

  • loading / skeleton / renderHints

  • as / use / layoutId / itemId / scope / access

Input uses Frame as its surface. Text mode directly renders a visible native input and its event chain. Date/color modes assign value synchronization, form ownership, and picker opening to a hidden native host, while a custom layer displays text or color.

Error feedback and shake

invalid shows a stable error border, aria-invalid, and warning icon. A one-shot shake is built in; no extra Prop or private CSS class is needed.

Use the ordinary invalid-state declaration:

<Input    invalid    placeholder="name@example.com"/>

Standalone Input shakes on invalid/aria-invalid. Inside Field, Input does not shake separately; Field aggregates error state and moves as one surface.

Error feedback does not focus an input or simulate focus-within. Focus comes from user action, autofocus, or application focus().

Input-specific Props

The following table corresponds to named Props item by item; see Frame for undeclared general capabilities.

Layout model

Main layout model: slot host layout. See LayoutProtocol §12.3 (specs/maintainers/LayoutProtocol.md).

The root owns a fixed single-line Leading / Control / Trailing layout with at least 4 CSS px between slots. Explicit gap=0 and root-font or gap-scale reductions retain the floor; larger original preferred gaps are preserved. Field owns external regions and continuous surfaces without rewriting Input internals. Internal date segments, color text and drawing structures retain their spacing.

Input root has three regions: Leading, Control, and Trailing.

  • The root is Frame row; enableAutoLayout is fixed internally. External enableAutoLayout={false} does not disable Input’s slot layout.

  • Direct as="leading"/as="trailing" children can be complex; each side hugs its content.

  • The native input or visible date/color layer fills Content and retains min-width: 0.

  • Custom trailing replaces default date/clear controls; the error icon still follows Input’s trailing rule.

  • Field takes over only outer surface, padding, and dividers; Input still positions its own icons and control.

Floating search mode

Place <Input as="search"> in a floating host with a header portal, such as Listbox or Popover. Input then:

  1. Reads headerEl through LISTBOX_HEADER_PORTAL_KEY and moves into the fixed header after mount, outside the option scroller.

  2. Applies compact floating-panel padding, gap, and radius.

  3. Suppresses the expanded focus ring during :focus-within with --snowui-field-focus-ring-width: 0rem.

  4. Defaults maxlength to 100 when absent.

Within Listbox, it also connects filtering through ListboxOwnerContext.setFilterText when isListboxSearch is derived from listboxOwner. Inside Popover, it only takes the fixed-header presentation; no filtering side effect is added.

Shared selectors cover .snowui-quick-action-panel-header > .snowui-input, .snowui-listbox-header > .snowui-input, and .snowui-listbox > .snowui-input without duplicating each overlay’s rules.

Attribute Type Default Description
as "search" - Marks a floating search input, moves it into a fixed header when one exists, and connects setFilterText only in Listbox.

Behavior

  • oninput writes search text to ListboxOwnerContext.filterText; Select derives filteredOptions for case-insensitive matching.

  • Custom items added through allowCustomValue remain visible regardless of filter text.

  • When Listbox closes, synchronize Input and filter text back to an empty string.

  • On a custom option hover, a circular × delete button replaces the check icon, reusing Input’s clear SVG. Clicking it removes that option and clears selection if the option was selected.

Usage examples

 <Select placeholder="Choose a city">    <Listbox>        <Input as="search" placeholder="Search..." />        <MenuItem value="shanghai">Shanghai</MenuItem>        <MenuItem value="hangzhou">Hangzhou</MenuItem>    </Listbox></Select>  <Select placeholder="Choose or enter">    <Listbox>        <Input as="search" allowCustomValue placeholder="Search or enter a new option..." />        <MenuItem value="tag-a">Tag A</MenuItem>        <MenuItem value="tag-b">Tag B</MenuItem>    </Listbox></Select>  <Select placeholder="Choose a city">    <Listbox style="max-height: 120px;">        <Input as="search" placeholder="Search..." />        ...    </Listbox></Select>

Native capability boundary

Input is responsible for:

  • Passthrough of supported native <input> attributes.

  • value/defaultValue precedence.

  • bind:value synchronization

  • Combined aria-invalid and component invalid state.

Input is not responsible for:

  • Complete label/description layout; compose with Field. Input can generate its own error Text through the public error Prop.

  • Generating an autocomplete data source.

  • A centralized form-rule engine.

  • Application-specific error messages.

Usage examples

 <Field>  <Input placeholder="Enter content" /></Field>  <Field>  <Icon as="leading"><Search /></Icon>  <Input placeholder="Search content" />  <Button as="trailing" size="sm">Search</Button></Field>  <Field>  <Input type="date" />  <Button bare as="trailing" aria-label="Open date picker">    <ArrowLineDown size={16} />  </Button></Field>  <Field>  <Frame as="row" row>    <Input type="date" />    <Button bare as="trailing" aria-label="Open date picker">      <ArrowLineDown size={16} />    </Button>  </Frame></Field>  <Input type="email" name="email" autocomplete="email" />  <Input required minlength={3} maxlength={20} pattern="[a-zA-Z0-9_]+" />  <form>  <Input name="username" defaultValue="snowui" /></form>  <form id="css-behavior-form"></form><Input form="css-behavior-form" name="displayName" />  <Input  Click={{ Idle: "Active", Active: "Idle" }}  stateStyle={{    Idle: "--snowui-input-background: var(--surface-1, #ffffffcc);",    Active:      "--snowui-input-background: color-mix(in srgb, var(--primary, #000000) 8%, var(--surface-1, #ffffffcc));",  }}  value="Click the input to change Frame state"/>

Displaying openable, copyable links

A “link input” that only opens and copies is not an editable field. Use CopyLink: it has a borderless input-like hover, underlines linked text on hover, opens in a new tab on click, and copies from the rest of its surface. See specs/reference/NaturalLanguageToSnowUI.md for mapping. Use Input when addresses must be edited or read-only selected values shown.

Accessibility and forms

  • For browser autofill, set name and autocomplete.

  • For native suggestions, point list at a datalist.

  • When an error message is present, use aria-describedby to reference the Field description or error node.

  • Perform schema or business validation at Field/form level, then pass its result as invalid or aria-invalid.


Input style overlay

Read the full LICENSE first; reuse that review for the same task, version, and scope.

First use public component Props to match the desired appearance, preserving the existing look where possible. If changes are necessary, follow the style selection and override order: use your own class (including Tailwind already in the project) or an instance style. The names below are public overrides actually consumed by source; check their scope and do not modify private DOM. Choose the correct SnowUI token family. External apps need not install SnowUI website utilities.

Variable Purpose and default reference
--snowui-input-background-override Background (see component source for the default).
--snowui-input-font-size-override font-size (see component source for the default).
--snowui-input-gap-override Gap (default var(--gap-2) = 8px)
--snowui-input-height-override Height (see the component source code for the default value)
--snowui-input-line-height-override line-height (see component source for the default).
--snowui-input-padding-override Overall padding (see the component source code for the default value)
--snowui-input-placeholder-color-override Placeholder color (see the component source code for the default value)
--snowui-input-radius-override border-radius
--snowui-input-warning-icon-color-override Warning icon color (see the component source code for the default value)
--snowui-input-warning-icon-font-size-override Warning icon font-size (see the component source code for the default value)
--snowui-input-warning-icon-line-height-override Warning icon line-height (see the component source code for the default value)
--snowui-input-warning-icon-size-override Warning icon size (size px, see the component source code for the default value)
--snowui-input-width-override Width (see the component source code for the default value)

Design Guide · Token · Combination boundary

Input type and status

Required Props: no named required Props.

Two-way binding: bind:value, bind:element.

Inheritance statement: Omit<FrameProps, "tag">. The inheritance ability is subject to the public document of the base class; the fields in Omit have been excluded and cannot be used as they are according to the base class.

Share Frame API · Return API

The following type declarations are actually referenced by public Props and come from source. A Svelte Snippet denotes a content fragment; ComponentProps denotes the Props of the corresponding component.

InputValue

Source: components/src/components/Input.svelte

type InputValue = string | number | undefined;

ComponentPartsOf

Source: components/src/logic/component-parts.svelte.ts

export type ComponentPartsOf<    T extends Record<string, Component<any>>,> = {    [K in keyof T]?: ConfigurableComponentPartProps<T[K]>;};

ConfigurableComponentPartProps

Source: components/src/logic/component-parts.svelte.ts

export type ConfigurableComponentPartProps<C extends Component<any>> = Partial<    Omit<ComponentProps<C>, ComponentPartControlledKey>>;

ComponentPartControlledKey

Source: components/src/logic/component-parts.svelte.ts

export type ComponentPartControlledKey =    | "children"    | "as"    | "value"    | "defaultValue"    | "open"    | "selected"    | "checked"    | "disabled"    | "readonly"    | "id"    | `on${string}`    | `aria-${string}`;

External type source:

  • HTMLInputAttributes — svelte/elements