Formatting form inputs with Cleave.js and React
Tags: javascript, react, cleave
Published: 2020-05-11 16:14:38

---
title: Formatting form inputs with Cleave.js and React
published: true
date: 2020-04-14 18:14:16 UTC
tags: javascript,react,cleave
canonical_url: https://blog.logrocket.com/formatting-form-inputs-with-cleave-js-and-react/
cover_image: https://dev-to-uploads.s3.amazonaws.com/i/evwysx7pse2l55r4kujg.png
---
**Written by [Adebiyi Adedotun](https://blog.logrocket.com/author/adebiyial/)**✏️

Undergoing a meaningful dialogue on the web requires a number of forms.

While the most of the attention has been reasonably placed on certain aspects such as validation, it’d be relatively easy to improve the form where it is closest to the user — its design.

Doing this will not only make our lives (as developers) easier, but also our users’. It’s a win-win. One way to do this is to format form inputs in real time to model its real-life equivalent. One tool that enables us do this is Cleave.js.

## What is Cleave.js?

To paraphrase, [Cleave.js](https://nosir.github.io/cleave.js/) helps you format your `<input/>` value as you type. That’s it.

> This tutorial is about how to use the Cleave.js library with React. You can also check the [GitHub page](https://github.com/nosir/cleave.js) to see how to use it in other ways.

### What can you format?

Cleave.js allows you to do 6 types of formatting:

- Credit card numbers
- Phone numbers
- Date formatting
- Time formatting
-  Numeral formatting
- Custom formatting (Prefix, Blocks, Delimiters etc)

[![LogRocket Free Trial Banner](https://i0.wp.com/blog.logrocket.com/wp-content/uploads/2017/03/f760c-1gpjapknnuyhu8esa3z0jga.png?resize=1200%2C280&ssl=1)](https://logrocket.com/signup/)

## Using CleaveJS with React

Instead of showing you how all the format types work in isolation, I’ve built a simple makeshift donation form:

![Annotation of Cleave.js formatted inputs](https://i1.wp.com/blog.logrocket.com/wp-content/uploads/2020/04/cleave-js-formatting-example.png?resize=730%2C717&ssl=1)

As annotated, we’ll be touching on:  
1 → Credit card number/type formatting  
2 → Date formatting  
3 → Digit formatting  
4 → Numeral formatting  
5 → Phone number formatting  
6 → Custom formatting (with prefix, blocks, and delimiters).

To get started, I’ve created a CodeSandbox and installed the Cleave.js package.

The first step is to import Cleave.js:

```jsx
import Cleave from "cleave.js/react";
```

Then, we use it instead of an `<input/>`:

```jsx
<Cleave placeholder="Enter credit card number" className="form-field" />
```

The `<Cleave/>` component returns an `<input/>` form element with the appropriate type (we don’t need to specify or bother about what type it returns). For its configuration, it takes an `options` props, which is a config for the different kind of formatting that can be done.

### Credit Card Formatting

```jsx
const [creditCardNo, setCreditCardNo] = useState("");

function onCreditCardChange(e) {
  setCreditCardNo(e.target.rawValue);
}

<Cleave
  placeholder="Enter credit card number"
  options={{
    creditCard: true,
  }}
  onChange={e => onCreditCardChange(e)}
  className="form-field"
/>
```

With the `creditCard` property to `true` and an `onChange` event handler. The `creditCardNo` state gets updated by accessing the formatted input value with `e.target.rawValue`.

This alone formats the input as the user types.

However, what would be fun is to be proactive and show them the kind of credit card provider the digits correspond to.

To do this, we pass in the `onCreditCardTypeChanged` event handler to the `options` property.

```jsx
const [creditCardNo, setCreditCardNo] = useState("");
const [creditCardType, setCreditCardType] = useState("");

function onCreditCardTypeChanged(type) {
   setCreditCardType(type);
}

function onCreditCardChange(e) {
  setCreditCardNo(e.target.rawValue);
}

<Cleave
  placeholder="Enter credit card number"
  options={{
    creditCard: true,
    onCreditCardTypeChanged
  }}
  onChange={e => onCreditCardChange(e)}
  className="form-field"
/>
```

> Unlike the `onChange` property on the `<Cleave/>` component, `onCreditCardTypeChanged` event handler is added as a property of `options` and accessed through the `type` (`type` is only a name, you can name it whatever you like).

### Date Formatting

```jsx
const [creditCardExpiryDate, setCreditCardExpiryDate] = useState("");

function onCreditCardExpiryChange(e) {
  setCreditCardExpiryDate(e.target.rawValue);
}

<Cleave
  placeholder="MM/YY"
  options={{ date: true, datePattern: ["m", "d"] }}
  onChange={onCreditCardExpiryChange}
  className="form-field"
/>
```

We’ve switched the `options` prop to have the type of `date` set to true and we’re formatting with a `datePattern` similar to that of credit cards, showing only the month and day.

### Block formatting

While there are other ways to enforce the three digits maximum for CVVs, cleave also offers an indirect way to do this. With blocks, you can pre-define the maximum length an input can be, and how many blocks. This is represented in an array.

For example, a block of `[2]` will make sure the user can only type two characters. Using this knowledge, we can cleave our CVV input as:

```jsx
const [cvv, setCVV] = useState("");

function onCVVChange(e) {
  setCVV(e.target.rawValue);
}

<Cleave
  placeholder="CVV"
  options={{
    blocks: [3],
    numericOnly: true
  }}
  onChange={onCVVChange}
  className="form-field"
/>
```

This allows for a single block of characters with a maximum of three digits, which we enforced with `numericOnly` set to `true`.

Our credit card details formatting should give this result:

![card details formatted with Cleave.js.](https://i2.wp.com/blog.logrocket.com/wp-content/uploads/2020/04/card-details-42.png?resize=730%2C221&ssl=1)

### Numeral Formatting

```jsx
const [donationAmount, setDonationAmount] = useState("");

function onDonationAmountChange(e) {
  setDonationAmount(e.target.rawValue);
}

<Cleave
  placeholder="0.00"
  options={{
    numeral: true,
    numeralThousandsGroupStyle: "thousand"
  }}
  onChange={onDonationAmountChange}
  className="form-field"
/>
```

To format our donation amount, we set the `numeral` property to `true` and also set numeral formatting to thousand with `numeralThousandsGroupStyle:` `"thousand"`.

> Keep in mind, this is an indirect way to format “currencies” as formatting [currencies is locale dependent](https://en.wikipedia.org/wiki/Template:Currency). Cleave formats numerals not currencies.

![Donation amount formatted with Cleave.js.](https://i1.wp.com/blog.logrocket.com/wp-content/uploads/2020/04/how-much-are-you-donating.png?resize=1074%2C196&ssl=1)  
Phone number Formatting

This is a little different than the others. To begin with, you need to import the locale/country, in this case, Nigeria, before using it.

```jsx
import "cleave.js/dist/addons/cleave-phone.ng";

const [phoneNumber, setPhoneNumber] = useState("");

function onPhoneChange(e) {
  setPhoneRawValue(e.target.rawValue);
}

<Cleave
  placeholder="0908 765 4321"
  options={{ phone: true, phoneRegionCode: "NG" }}
  onChange={onPhoneChange}
  className="form-field"
/>
```

Here, the `phone` property is set to true, and the `phoneRegionCode` is set to “NG”.

> If you find the phone number formatting a little different from what you intend, Cleave also provides a custom formatting – check the next format.

![Nigerian phone number format with Cleave.js.](https://i2.wp.com/blog.logrocket.com/wp-content/uploads/2020/04/phone-number.png?resize=1052%2C182&ssl=1)

### Custom Formatting

Imagine you require your users to enter cryptic 2FA passphrases. Cleave can help with its custom formatting:

```jsx
const [customValue, setCustomValue] = useState("");

function onCustomValueChange(e) {
  setCustomRawValue(e.target.rawValue);
}

<Cleave
  placeholder="KEY-2DJDH2-3I37X-2MXHGX"
  options={{
    prefix: "KEY",
    blocks: [3, 6, 5, 6],
    delimiter: "—",
    numericOnly: false
  }}
  onChange={onCustomValueChange}
  className="form-field"
/>
```

Some of the options you can pass here is the `prefix`, `blocks`, `delimiter` (for the blocks), `numericOnly` etc.

This will ensure a formatting of 3, 6, 5, and 6 digits, separated with the delimiter value, the first blocks item will be for the prefix:

![paraphrase](https://i1.wp.com/blog.logrocket.com/wp-content/uploads/2020/04/paraphrase.png?resize=730%2C121&ssl=1)

### Form submission

It is important to always remember that Cleave.js is meant for formatting not validation, so it customizes — not enforce — the input values. Before submission, make sure to validate your forms.

When you try to submit the form you do not need to worry about how what goes in the `state` or how the values gets transformed because Cleave.js strips all formatting away and gives you the raw value. If I try to submit this form:

![credit card formatting.](https://i2.wp.com/blog.logrocket.com/wp-content/uploads/2020/04/card-details.png?resize=730%2C687&ssl=1)

I get the values in my `state`:

```jsx
creditCardNo: "4242424242424242"
phoneRawValue: "09087363636"
dateRawValue: "1222"
donationAmount: "450000"
customRawValue: "KEY27272bbc6262gbxy2"
cvv: "222"
```

## Conclusion

Having users fill out forms in this way is no doubt an interesting and credible way to go and will put us a step ahead.

Check out the links below for more.  
1. [Codesandbox link to full example](https://codesandbox.io/s/cleavejs-demo-c3j27)  
2. [CleaveJS official website](https://nosir.github.io/cleave.js/)  
3. [CleaveJS GitHub project](https://github.com/nosir/cleave.js)

* * * 
## Full visibility into production React apps 

Debugging React applications can be difficult, especially when users experience issues that are difficult to reproduce. If you’re interested in monitoring and tracking Redux state, automatically surfacing JavaScript errors, and tracking slow network requests and component load time, [try LogRocket.](https://www2.logrocket.com/react-performance-monitoring)

![Alt Text](https://thepracticaldev.s3.amazonaws.com/i/eq752g8qhbffxt3hp9t4.png)

[LogRocket](https://www2.logrocket.com/react-performance-monitoring) is like a DVR for web apps, recording literally everything that happens on your React app. Instead of guessing why problems happen, you can aggregate and report on what state your application was in when an issue occurred. LogRocket also monitors your app's performance, reporting with metrics like client CPU load, client memory usage, and more.

The LogRocket Redux middleware package adds an extra layer of visibility into your user sessions. LogRocket logs all actions and state from your Redux stores.

Modernize how you debug your React apps — [start monitoring for free.](https://www2.logrocket.com/react-performance-monitoring)
* * *

The post [Formatting form inputs with Cleave.js and React](https://blog.logrocket.com/formatting-form-inputs-with-cleave-js-and-react/) appeared first on [LogRocket Blog](https://blog.logrocket.com).