/// Inputs
PasswordInput
Masked text field with a trailing reveal/hide toggle and an optional strength-meter slot.
import { PasswordInput } from "@protocore/pds";Basics
The field starts masked. The trailing eye toggle swaps between password and text; its aria-label flips between show and hide, and focus stays in the field.
Used to unseal the local key store.
Strength meter
Pass any node to meter to render a strength readout directly below the field — a ProgressBar, a row of segments, or a hint line. The meter is yours to compute.
Strong
Confirm field
Set hideToggle on a confirm-password field so the two rows stay visually aligned and there's no second reveal control. Wrap either in a Field for a label and error.
When to use it
Use PasswordInput for any secret a user types — a login password, an API secret being set, a passphrase. The reveal toggle cuts typos on long secrets without weakening masking by default. For one-time codes use OTPInput; for a plain non-secret string use Input. Compute strength yourself and pass the result to meter — the component intentionally ships no scoring so you can plug in zxcvbn, a server rule, or nothing at all.
Usage
Do
- Give the field an accessible name via `aria-label` or a wrapping `Field`.
- Keep the default masked state — reveal is opt-in, per field.
- Use `meter` for feedback the user can act on, not a decorative bar.
- Set `hideToggle` on confirm fields so the reveal control isn't duplicated.
Don't
- Don't default to revealed — it removes shoulder-surfing protection.
- Don't reuse it for one-time codes; OTPInput handles those.
- Don't hard-code a strength algorithm into the field; feed `meter` instead.
- Don't remove the toggle on a primary password field.
Accessibility
| Keys | Action |
|---|---|
| Tab | Move focus to the field, then to the reveal toggle. |
| Enter / Space | On the toggle, reveal or re-mask the value. |
- The toggle is a real `button` with an `aria-label` that flips between 'Show password' and 'Hide password' and an `aria-pressed` state.
- Pressing the toggle returns focus to the field so the caret position is preserved.
- The masked field composes the base `Input`, inheriting its focus ring, sizes, and invalid state.
PasswordInput props
| Prop | Type | Default | Description |
|---|---|---|---|
className | string | — | |
defaultValue | string | — | Initial value when uncontrolled. |
defaultVisible | boolean | false | Start with the value revealed (uncontrolled visibility). |
hideToggle | boolean | false | Hide the reveal/hide toggle entirely (e.g. a confirm-password field). |
invalid | boolean | — | Mark the field invalid — danger border plus `aria-invalid`. |
meter | ReactNode | — | Optional strength-meter node rendered directly below the field. |
onValueChange | ((value: string) => void) | — | Fires with the new value on every edit. |
onVisibleChange | ((visible: boolean) => void) | — | Fires with the next visibility when the toggle is pressed. |
size | enum | — | Control height: `sm` (32) · `md` (36, default) · `lg` (40). |
startAdornment | ReactNode | — | Leading slot (muted; mono for glyph/unit labels), rendered inside the field. |
style | CSSProperties | — | |
toggleLabel | { show: string; hide: string; } | { show: "Show password", hide: "Hide password" } | Accessible label for the reveal/hide toggle. |
value | string | — | Controlled value. Pair with `onValueChange`. |
visible | boolean | — | Controlled visibility — when set, the toggle calls `onVisibleChange` instead of owning state. |