Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Adding Line Breaks to Chakra UI <Text> element?

I'm trying to add validator warning messages to the front-end of my signup form. My application is a React.js app that's styled using Chakra UI. My validator hook function looks as follows:

const passwordValidation = () => {
    const regex =
      /^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#?!@$%^&*-]).{8,}$/;
    if (!regex.test(formState.password) || formState.password === "") {
      setPasswordMessage(
        "*This is a required field. Please meet the following password requirements: A minimum of 8 characters. At least one uppercase letter. At least one lower case letter. At least one numerical character. At least one special character."
      );
    } else {
      setPasswordMessage("");
    }
  };

And here is where the password message is being displayed on the front-end:

<FormControl data-test="password-input" id="password">
              <FormLabel>Password: </FormLabel>
              <Input
                placeholder="******"
                name="password"
                type="password"
                value={formState.password}
                onChange={handleChange}
                required
              />
              <Text color="#FF0000" fontSize="md">
                {passwordMessage}
              </Text>
            </FormControl>

I would like to have line breaks after each listed password requirement but I can't seem to get the text to format that way.

I started by trying to add line break tags as follows:

const passwordValidation = () => {
    const regex =
      /^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#?!@$%^&*-]).{8,}$/;
    if (!regex.test(formState.password) || formState.password === "") {
      setPasswordMessage(
        "*This is a required field. Please meet the following password requirements: \n\n A minimum of 8 characters. \n At least one uppercase letter. \n At least one lower case letter. \n At least one numerical character. \n At least one special character."
      );
    } else {
      setPasswordMessage("");
    }
  };

This didn't work so I tried it another way:

const passwordValidation = () => {
    const regex =
      /^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#?!@$%^&*-]).{8,}$/;
    if (!regex.test(formState.password) || formState.password === "") {
      setPasswordMessage(
        "*This is a required field. Please meet the following password requirements: <br> A minimum of 8 characters. <br> At least one uppercase letter. <br> At least one lower case letter. <br> At least one numerical character. <br> At least one special character."
      );
    } else {
      setPasswordMessage("");
    }
  };

None of these worked. Is there a way to format this text with line breaks inside my validator hook function?

like image 651
Dan Gray Avatar asked Nov 07 '25 23:11

Dan Gray


2 Answers

In Chakra UI, to render line breaks from content that contains '\n', you can use the whiteSpace CSS property with the value of 'pre-line' on the Text component. This will preserve line breaks and display them correctly on the screen.

Inshort set whitespace to "pre-line" on <Text>.

Below is sample example

import { Text } from "@chakra-ui/react";

const description: "This is some text\n with line breaks \n in it."

function MyComponent() {
  return (
    <Text whiteSpace="pre-line">
      {description}
    </Text>
  );
}
like image 71
Tarun Jain Avatar answered Nov 09 '25 19:11

Tarun Jain


The Text element accepts a string or JSX. If you pass a string it would be rendered as is, and not parsed as HTML. Instead pass a JSX element.

The function should return JSX or an empty string. It doesn't need to set a state, because the value is derived from formState.password. In addition, setting another state would cause a needless re-render. The message should be a JSX element, so wrap it a standard element (span for example), or in a fragment (<></>). You should also move the RegExp outside of the function, so it won't be re-created when the function is called.

const regex = /^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#?!@$%^&*-]).{8,}$/;

const getPasswordValidation = ({ password }) =>
  !regex.test(password) || password === ''
  ? (
    <>* This is a required field. Please meet the following password requirements: <br /> A minimum of 8 characters. <br /> At least one uppercase letter. <br /> At least one lower case letter. <br /> At least one numerical character. <br /> At least one special character.</>
  )
  : '';

Call the function with the formState to get the message:

<Text color="#FF0000" fontSize="md">
  {getPasswordValidation(formState)}
</Text>

Another option is to convert the function to component:

const regex = /^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#?!@$%^&*-]).{8,}$/;

const PasswordValidation = ({ password }) =>
  !regex.test(password) || password === ''
  ? (
    <>* This is a required field. Please meet the following password requirements: <br /> A minimum of 8 characters. <br /> At least one uppercase letter. <br /> At least one lower case letter. <br /> At least one numerical character. <br /> At least one special character.</>
  )
  : '';

Usage:

<Text color="#FF0000" fontSize="md">
  <PasswordValidation password={formState.password} />
</Text>
like image 21
Ori Drori Avatar answered Nov 09 '25 18:11

Ori Drori



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!