首页 > 解决方案 > 在 ReactJs 中使用 useState 钩子时如何确保获取最新的输入值

问题描述

下面是一个使用useState钩子的 React 组件,但我没有得到最新的值。

import { FC, useRef,useState } from "react";
import { Album } from "../../../types/album";
import "./album.module.css";

interface Props {
 addAlbum(newAlbum: Album): void;  
}

const NewAlbum: FC<Props> = (props) => {
const [name, setName] = useState('');
const [releaseDate, setReleaseDate] = useState('');

console.info("New Album Component Render");

const releaseDateRef = useRef<HTMLInputElement>(null);
const albumNameRef = useRef<HTMLInputElement>(null);

const addAlbumHandler = () => {
  setName(albumNameRef.current?.value!)
  setReleaseDate(releaseDateRef.current?.value!)


 // *LOC
  props.addAlbum({
   name: name,
   releaseDate: releaseDate
   id: Math.random().toString(),
 });
};

return (
<>
  <div>
    <input type="text" placeholder="Album Name" ref={albumNameRef} />
  </div>
  <div>
    <input type="text" placeholder="Release year" ref={releaseDateRef} />
  </div>
  <div>
    <button type="button" onClick={addAlbumHandler}>
      Add New Album
    </button>
  </div>
</>
)};

export default NewAlbum;

但是,当我单击 AddNewAlbum 按钮时,addAlbumHandler()会被调用,但我没有得到name&的最新值releaseDate

但是,当我在 *LOC 更新代码时,如下所示

 props.addAlbum({
  name: albumNameRef.current?.value!,
  releaseDate: releaseDateRef.current?.value!,
  id: Math.random().toString(),
});

我确实得到了想要的值,

我知道useState幕后的钩子不会立即执行

在 React 中使用 useState 钩子时如何确保获取最新的输入值?

标签: reactjsuse-state

解决方案


一些技巧:

  1. 您永远不必使用useRef从元素中检索值。这是完全没有反应和完全没有必要的。通常的反应方式是定义状态,它用作输入的值,并为改变状态的输入提供适当的值更改处理程序。
  2. 如您所知,状态更改不会立即发生。这是您的第一个示例不起作用的唯一原因,也解释了第二个示例为何起作用。

对应该工作的代码的建议:

import { FC, useRef,useState } from "react";
import { Album } from "../../../types/album";
import "./album.module.css";

interface Props {
  addAlbum(newAlbum: Album): void;  
}

const NewAlbum: FC<Props> = (props) => {
  const [name, setName] = useState('');
  const [releaseDate, setReleaseDate] = useState('');

  const nameChangeHandler = (e) => setName(e.target.value);
  const releaseDateChangeHandler = (e) => setReleaseDate(e.target.value);

  console.info("New Album Component Render");

  const addAlbumHandler = (e) => {    
    // *LOC
    props.addAlbum({
      name: name,
      releaseDate: releaseDate
      id: Math.random().toString(),
    });
  };

  return (
    <>
      <div>
        <input
          type="text"
          placeholder="Album Name"
          value={name}
          onChange={nameChangeHandler}
        />
      </div>
      <div>
        <input
          type="text"
          placeholder="Release year"
          value={releaseDate}
          onChange={releaseDateChangeHandler}
        />
      </div>
      <div>
        <button type="button" onClick={addAlbumHandler}>
          Add New Album
        </button>
      </div>
    </>
  );
}

export default NewAlbum;

推荐阅读