coss.com Svelte

OTP Field

A segmented input for one-time passwords and verification codes.

Loading p-otp-field-1 preview…

This component provides a Svelte implementation of the COSS OTP Field behavior. Each slot is a real native input.

Installation

pnpm dlx shadcn-svelte@latest add https://coss-sv.vercel.app/r/otp-field.json

Usage

<script lang="ts">
  import * as OTPField from "$lib/components/ui/otp-field/index.js";
</script>

<OTPField.Root aria-label="Verification code" length={6}>
  <OTPField.Input />
  <OTPField.Input aria-label="Character 2 of 6" />
  <OTPField.Input aria-label="Character 3 of 6" />
  <OTPField.Separator />
  <OTPField.Input aria-label="Character 4 of 6" />
  <OTPField.Input aria-label="Character 5 of 6" />
  <OTPField.Input aria-label="Character 6 of 6" />
</OTPField.Root>

API Reference

Each slot is a real <input>. Its order in the tree must match length on the root.

OTPField.Root

Root component. class merges with the default layout styles.

Use required length for the number of characters. The previous maxLength prop from the legacy input-otp package is not used.

PropTypeDefaultDescription
size"default" \| "lg""default"Size applied to all slots
validationType"numeric" \| "alpha" \| "alphanumeric" \| "none""numeric"Accepted character set
maskbooleanfalseMasks entered characters in each slot

OTPField.Input

Renders one OTP character input. Slots use DOM order and do not take an index prop.

PropTypeDescription
classstringMerges with the default slot styles
placeholderstringNative placeholder text

Label the OTP control on the root with aria-label or a visible Label or Field.Label. The first input inherits the field label. Give later slots an explicit label such as Character 2 of 6.

OTPField.Separator

Visual separator between slot groups. It uses the design-system Separator for layout and semantics.

Examples

Large

Loading p-otp-field-2 preview…

With Separator

Loading p-otp-field-3 preview…

With Label

Loading p-otp-field-4 preview…

Custom normalization

Set validationType="none" with normalizeValue to normalize pasted input before it reaches state, or to enforce custom character rules. Use inputMode for the virtual keyboard hint and onValueInvalid for characters rejected after normalization.

Loading p-otp-field-6 preview…

Auto Validation

Loading p-otp-field-7 preview…

Alphanumeric

Use validationType="alphanumeric" for recovery, backup, or invite codes that mix letters and numbers.

Loading p-otp-field-8 preview…

Placeholder hints

Each slot is a real input, so placeholder and CSS work as usual. Hide the placeholder on focus when the active slot should not show a hint.

Loading p-otp-field-9 preview…

Masked entry

Pass mask on the root when the code should be obscured while it is typed, for example on shared screens.

Loading p-otp-field-10 preview…

Changelog

  • Apr 14, 2026 - input-otp.tsx was replaced by otp-field.tsx and @coss/otp-field upstream.