简体   繁体   中英

Button click gives error message if input field is empty in react hooks

Now I would need your help with a simple validation: if input field is empty when I click a button I want a message to pop up. I want the message to disappear when the field is filled in.

with this code

if (number.trim().length === 0) {
      return;
    }

I prevent any action to take place, but the user don´t get any error message. I come up with:

const [errors, setErrors] = useState([]);

const isRequired = (number) => {
  return number.trim().length > 0 ? '' : 'Please enter scorers number';
};
const validate = (validations) => {
    setErrors(validations.map((err) => err(number)));
  };

{errors.length > 0 ? <h4 style={{color: 'red'}}>{errors}</h4> : null}

but how can I make the message show and hide? I guess I have to attach to the onClick?

My whole code:

import React from 'react';
import './App.css';
import {useState} from 'react';
import {New} from './New';
const isRequired = (number) => {
  return number.trim().length > 0 ? '' : 'Please enter scorers number';
};

const App = () => {
  const [number, setNumber] = useState('');
  const [totPoints, setTotPoints] = useState(0);
  const [scorers, setScorers] = useState([]);
  const [focused, setFocused] = useState(false);
  const [errors, setErrors] = useState([]);

  const validate = (validations) => {
    setErrors(validations.map((err) => err(number)));
  };

  const sortedScorers = [...scorers].sort((a, b) => a.number - b.number);

  const onePointScoredHandler = () => {
    const players = [...scorers];
    if (number.trim().length === 0) {
      return;
    }
    const pos = players.map((player) => player.number).indexOf(+number);

    if (pos !== -1) {
      console.log('exist');
      setScorers((scorers) =>
        scorers.map((scorer, index) =>
          index === pos
            ? {
                ...scorer,
                totPoints: scorer.totPoints + 1,
              }
            : scorer
        )
      );
    } else {
      console.log('new');
      const newScorer = {
        id: Math.floor(Math.random() * 1000),
        number: +number,
        totPoints: totPoints + 1,
      };

      setScorers([...scorers, newScorer]);
      setTotPoints(totPoints);
    }
    setNumber('');
    console.log(scorers);
  };

  const twoPointScoredHandler = () => {
    if (number.trim().length === 0) {
      return;
    }
    const players = [...scorers];

    const pos = players.map((player) => player.number).indexOf(+number);

    if (pos !== -1) {
      console.log('exist');
      setScorers((scorers) =>
        scorers.map((scorer, index) =>
          index === pos
            ? {
                ...scorer,
                totPoints: scorer.totPoints + 2,
              }
            : scorer
        )
      );
    } else {
      console.log('new');
      const newScorer = {
        id: Math.floor(Math.random() * 1000),
        number: +number,
        totPoints: totPoints + 2,
      };
      setScorers([...scorers, newScorer]);
      setTotPoints(totPoints);
    }
    setNumber('');
    console.log(scorers);
  };
  const threePointScoredHandler = () => {
    if (number.trim().length === 0) {
      return;
    }
    const players = [...scorers];

    const pos = players.map((player) => player.number).indexOf(+number);

    if (pos !== -1) {
      console.log('exist');
      setScorers((scorers) =>
        scorers.map((scorer, index) =>
          index === pos
            ? {
                ...scorer,
                totPoints: scorer.totPoints + 3,
              }
            : scorer
        )
      );
    } else {
      console.log('new');
      const newScorer = {
        id: Math.floor(Math.random() * 1000),
        number: +number,
        totPoints: totPoints + 3,
      };
      setScorers([...scorers, newScorer]);
      setTotPoints(totPoints);
    }
    setNumber('');
    console.log(scorers);
  };

  return (
    <div className="App">
      <h4>Individual points</h4>
      <br />
      <br />
      <br />
      <input
        type="number"
        value={number}
        placeholder="scorer number"
        onChange={(e) => setNumber(e.target.value)}
        onFocus={() => setFocused(true)}
        onBlur={() => {
          setFocused(false);
        }}
      />
      {errors.length > 0 ? <h4 style={{color: 'red'}}>{errors}</h4> : null}
      <br />
      <br />
      <button onClick={(onePointScoredHandler, validate([isRequired]))}>
        1p scored
      </button>
      <button onClick={twoPointScoredHandler}>2p scored</button>
      <button onClick={threePointScoredHandler}>3p scored</button>
      <br />
      <br />

      {scorers.length ? (
        <table className="table">
          <thead>
            <tr>
              <th>player NUMBER</th>
              <th>Total Points</th>
            </tr>
          </thead>
          <tbody>
            {sortedScorers
              .sort((a, b) => a.number - b.number)
              .map((player) => (
                <tr key={player.id}>
                  <td>{player.number}</td>
                  <td>{player.totPoints}</td>
                </tr>
              ))}
          </tbody>
        </table>
      ) : (
        <New />
      )}
    </div>
  );
};

export default App;

```
Thanks in advance
/Peter

a couple things I noted and thought I'll share my thoughts with you.

  1. It is easier for you and for other developers if you structure functionality etc. in own components so that like here, your <App/> isn't that bloated.
  2. {errors.length > 0? <h4 style={{color: 'red'}}>{errors}</h4>: null} {errors.length > 0? <h4 style={{color: 'red'}}>{errors}</h4>: null} this is an unnecessary ternary, you can just use {errors.length && <h4 style={{color: 'red'}}>{errors}</h4>
  3. You should post your error message that you are getting and explain what you do not understand about it. I think I know the problem, but I don't like guessing.

you should use

setTimeout(() =>{
  setErors('')
},5000)

you message will automatically disappear after 5 se enter code here c. strong text

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM