Copy-paste

Recipes

Production-ready PhoneField patterns composed from the same primitives and shadcn components used by the playground.

Basics

Inline country select

defaultshadcn

One visual field with separate accessible country and phone controls.

Loading preview…

Use when

Use this as the default for profiles, contact forms, and account settings.

Requires

field · input-group

Accessibility

Country and phone keep independent names while sharing one visual boundary.

Separated country select

checkoutresponsive

Country and phone retain their own visual boundaries for dense forms.

Loading preview…

Use when

Use it when labels and column alignment matter more than compactness.

Requires

field · input

Accessibility

Each control has its own visible label and focus target.

Fixed country

single marketsimple

Remove the picker when the product already knows the supported market.

Loading preview…

Use when

Use it for market-specific products or tenant-level country policies.

Requires

field · input-group

Accessibility

The dialing code remains visible even though it is not interactive.

Phone with extension

businessextension

Collect an office extension without mixing it into the canonical phone value.

Loading preview…

Use when

Use it for business contacts, support desks, and PBX-backed phone records.

Requires

field · input-group

Accessibility

Phone and extension have independent labels, values, and input modes.

Forms

Validated field

fieldvalidation

Required and invalid states read from the field itself, with accessible error messaging.

Loading preview…

Use when

Use it when the field owns validation and no form library is involved.

Requires

field · input-group

Accessibility

The message is linked with aria-describedby, and aria-invalid follows the field state automatically.

Server-safe FormData

server actionnative

Submit minimal source values and rebuild trusted derived data at the boundary.

Loading preview…

Use when

Use it for native forms, server actions, or progressively enhanced submissions.

Requires

field · input-group

Accessibility

The visible field remains native while hidden source inputs serialize the value.

React Hook Form + Zod

rhfzod

Controller-based integration with Standard Schema validation on every change.

Loading preview…

Use when

Use it when React Hook Form owns the complete form state and submission lifecycle.

Requires

react-hook-form · @hookform/resolvers · zod · field · input-group

Accessibility

Controller forwards blur, value changes, invalid state, and the Zod message.

TanStack Form + Zod

tanstackzod

Type-safe field composition using TanStack Form's Standard Schema support.

Loading preview…

Use when

Use it for deeply typed or highly reactive forms built around TanStack's ecosystem.

Requires

@tanstack/react-form · zod · field · input-group

Accessibility

Field meta drives real-time aria-invalid and a colocated error announcement.

Disabled, read-only, and loading

statesa11y

Production states that preserve visual structure and communicate availability.

Loading preview…

Use when

Use these patterns for permissions, persisted values, and async mutations.

Requires

field · input-group

Accessibility

Native disabled/readOnly semantics are paired with visible status affordances.

Product flows

Phone verification flow

otpmulti-step

A complete phone-to-OTP interaction with editable and verified states.

Loading preview…

Use when

Use it for sign-in, onboarding, account recovery, and phone verification.

Requires

button · card · field · input-group · input-otp

Accessibility

Each step exposes a single task, preserves the phone value, and labels the OTP slots.

International paste detection

pastee.164

Pasting an international number updates country and normalized output.

Loading preview…

Use when

Use it when users frequently paste numbers from contacts, CRMs, or messages.

Requires

field · input-group

Accessibility

Country changes are reflected in visible text, not communicated by flag alone.

Mobile & localization

Localized country subset

i18nsubset

Limit supported markets, pin the key ones, and localize country names, search, and sorting.

Loading preview…

Use when

Use it when product availability is restricted to a known set of countries.

Requires

field · input-group

Accessibility

Localized names remain searchable and visible beside their dialing codes.

Native country select

nativeusePhoneField

Drive the field from a plain <select> with usePhoneField, no popup required.

Loading preview…

Use when

Use it when the platform picker beats a custom popup, such as in mobile web or embedded webviews.

Requires

field · input-group

Accessibility

A real select keeps native keyboard, screen reader, and touch behavior for the country.

Country select in a Drawer

drawermobile

A thumb-friendly country picker designed for mobile product flows.

Loading preview…

Use when

Use it on mobile-first forms where a popover would feel cramped or hard to scan.

Requires

button · drawer · field · input · input-group

Accessibility

The trigger names its purpose and the current country, and the modal drawer keeps search and options reachable.