Skip to main content
U.S. Flag

An official website of the United States government

Label-Masked Field

A label-masked field is a text-field pattern that provides instant, visual feedback about how inputed data is being interpreted without creating a noisy aural experience.

Examples

This component mirrors user input as formatted "hint text" after the label to provide visual feedback about the data as the user is typing. The text in the input field itself will not be formatted until the field loses focus, which is when we know the user has finished typing.

Because the hinting isn't being applied to the input itself, it's less distracting and obtrusive to screen reader users, providing a quieter and more usable experience for everyone. It is an updated alternative to our Masked Field.

The label-mask currently has five built-in implementations: currency, phone number, Social Security Number, ZIP code, and date. The date mask is implemented by the Calendar Picker and Single-Input Date Field components, while the rest are available for direct use with the Text Field component.

Currency

Loading

Phone number

Loading

Social Security number

Loading

ZIP code

Loading

Code

React

Passing a labelMask prop into a TextField component with a valid masking function will turn it into a label mask. You can either import one of the named, built-in mask functions (SSN_MASK, ZIP_MASK, PHONE_MASK, or CURRENCY_MASK), or you can provide a custom mask function. The following table shows the TextField prop that is specific to label masks:

React Properties Documentation
NameTypeDefaultDescription
labelMask(rawInput: string, valueOnly?: boolean) => stringApplies date format masking to the input value entered and renders to a text field above the input. Passing true to valueOnly will return just the formatted value entered.

Handling input changes

When tracking state in a parent component, treat the value as a raw input string, which is updated by the onChange handler. Do not try to unmask or clean the value before passing it back to the TextField component instance. The intention with this is to keep the API and behavior of the component as simple as possible. You don't need to handle onBlur separately from onChange. You only need to update your value when onChange is called, and it will be called whenever the value of the input changes, including on blur. A more appropriate place to clean the input would be in your validation code.

// A simplified example of change handling. This is not a recommendation
// for how to structure error messages or validation code but serves only
// to illustrate how to set and get values from the label-masked field.

import { useState } from "react";
import { Button, TextField, SSN_MASK } from '@cmsgov/design-system';

export const MyForm = () => {
  const [value, setValue] = useState('');
  const [error, setError] = useState();

  function validate() {
    if (!isValidSsn(value)) {
      e.preventDefault();
      setError('You have entered an invalid SSN.');
    }
  }

  return (
    <form onSubmit={validate}>
      {error && <Alert variation="error">{error}<Alert>}
      <TextField
        label="Social security number (SSN)"
        labelMask={SSN_MASK}
        name="ssn_example"
        value={value}
        onChange={setValue}
      />
      <Button type="submit">Submit</Button>
    </form>
  )
};

Guidance

When to use

  • In fields with a specific expected format like Social Security Number or ZIP code, a label mask allows you to constrain and shape the information being entered without impairing the user's ability to copy/paste or correct mistyping

When to consider alternatives

  • When the input requires a free-form field that doesn't use a common input pattern, masking is not appropriate.
  • When the pattern is too complicated to allow for a valid label mask. A pattern like email, with many possible scenarios for input, is not a good candidate for masking. Allow the user to enter their email address (or other complicated data) and have your validation library confirm before form submission.

Usage

  • Only show error validation messages or stylings after a user has interacted with a particular field

Accessibility

Learn more

Component maturity

For more information about how we tested and validated our work for each checklist item, read our component maturity documentation.

Accessibility

  • Color

    Meets AA color contrast standards for accessibility and color blindness.
    Complete
  • Forced Colors Mode (FCM)

    While using FCM the components text is legible and improves readability.
    Complete
  • WCAG 2.1 Level AA Conformance

    All Axe checks for WCAG AA compliance have passed.
    Complete
  • Screen readers

    VoiceOver, NVDA, and JAWS screen readers provide concise communication and interaction.
    Complete
  • Keyboard navigation

    Component is fully navigable with a keyboard.
    Complete

Code

  • Storybook

    Component has stories to cover all defined props.
    Complete
  • Responsive

    Component designed to work in all responsive breakpoints.
    Complete
  • Spanish translations

    Includes Spanish translations for default text content.
    Not applicable

Tokens

  • Code

    Tokens implemented in code.
    Complete
  • Design

    Tokens implemented in the Sketch.
    Complete