Skip to main content
Search
Search the documentation

Password input

A password field with a visibility toggle that does not break password managers.

pnpm dlx shadcn-svelte@latest add https://coral.imlargo.dev/r/kit-password-input.json

Switching type between password and text is one line, and it is the line that goes wrong: the caret jumps to the start, the toggle announces itself as a different button after every press, and a form submitted while the password is showing hands a password manager a plain text field, so the offer to save it never comes.

Try it with Caps Lock on.

What Coral adds

  • Hidden again on submit. The field goes back to type="password" inside the form's submit event, before the browser reads it, so saving and autofill keep working.
  • The caret stays put. Selection is read before the switch and restored after it.
  • One toggle, one name: aria-pressed carries the state, so "Show password, pressed" means what it says, instead of a name that flips between "Show" and "Hide" and never says which is current.
  • Caps Lock warning: read with getModifierState, which catches a lock that was already on and does not get it backwards on macOS. Announced politely, cleared on blur.
  • Nothing sent to a spellchecker. Spellcheck, autocorrect and autocapitalize are off. A shown password is a text field to the browser, and enhanced spellcheck services upload text fields.

In a form

Visible: no

Show the password and submit: the form reports type="password". Turn this off with hideOnSubmit={false} only if the field is not a credential.

autocomplete defaults to current-password. Set new-password on sign-up and change-password forms, which is what tells a password manager to offer a generated one.

Import

<script lang="ts">
	import PasswordInput from '#lib/components/coral/kit/password-input/password-input.svelte';
</script>

Props

Everything the shadcn input accepts stays available: name, id, placeholder, required, minlength, disabled, aria-*. On top of that:

PropTypeDefaultDescription
valuestring-Bindable.
visiblebooleanfalseBindable. Whether the password is shown.
capsLockbooleanfalseBindable. Caps Lock at the last key press in the field.
hideOnSubmitbooleantrueHides the password when its form submits.
onvisiblechange(visible: boolean) => void-The reader toggled visibility.
autocompletestringcurrent-passwordUse new-password on sign-up forms.
toggleLabelstringShow passwordAccessible name of the toggle. The same in both states.
capsLockLabelstringCaps Lock is onAnnounced, and the indicator's tooltip.
classstring-Merged onto the input.
groupClassstring-Merged onto the bordered group.
capsLockIndicatorSnippet-Replaces the indicator. Render nothing to drop the warning.

Accessibility

The toggle is a type="button" with aria-pressed and aria-controls pointing at the field, so it never submits the form and assistive tech knows what it changes. The Caps Lock warning is a polite status message and the icon is hidden, so it is heard once rather than read as part of the field.