首页 > 解决方案 > React - 如何使用钩子来隐藏或显示基于 onChange 事件的组件

问题描述

我试图弄清楚如何使用反应挂钩来隐藏或显示基于 onChange 事件的组件(在表单中选择了一个选定的选项)。

我有一个名为 Animal 的组件,在有人从表单的选择菜单中选择“动物”之前,该组件将被隐藏。

这就是我试图做的:

import React, { useState, useEffect } from "react";
import useForm from "react-hook-form";
import { withRouter } from "react-router-dom";
import Select from "react-select";
import Animal from "./tips/Animal";


const specialFeatures = [
  { value: "animals", label: "Animals" },
  { value: "none", label: "None of these apply" }
];

const Method = props => {
  const { register, handleSubmit, setValue, errors, reset } = useForm();

  const [valuesSpecialFeatures, setSpecialFeatures] = useState([]);
  const [showAnimal, setShowAnimal] = useState(false);


  const handleMultiChangeSpecialFeatures = selectedOption => {
    setValue("specialFeatures", selectedOption, true);
    setSpecialFeatures(selectedOption);
    if selectedOption === 'animals' setAnimal(!<Animal />)
  };


  return (
    <div>

        <form onSubmit={handleSubmit(onSubmit)}>

          <label>Does this proposal incldue any of these features?</label>
          <Select
            className="reactSelect"
            name="specialFeatures"
            placeholder="Select at least one"
            value={valuesSpecialFeatures}
            options={specialFeatures}
            onChange={handleMultiChangeSpecialFeatures}
            isMulti
          />

          { showAnimal && "animals" <Animal /> }

          <input type="submit" value="next" />
        </form>

    </div>
  );
};

export default withRouter(Method);

我正在尝试测试名为 specialFeatures 的表单字段是否具有包含值“animals”的 selectedOption,如果有,我想在该字段下方显示 Animal 组件。

这种尝试显然是不正确的,但我看不到如何设置 useEffect 来切换可见性。

标签: javascriptreactjsreact-hooks

解决方案


首先,您需要将showAnimal状态设置为布尔值,然后使用它来显示或隐藏组件:

const Method = props => {
  const { register, handleSubmit, setValue, errors, reset } = useForm();
  const [valuesSpecialFeatures, setSpecialFeatures] = useState([]);
  const [showAnimal, setShowAnimal] = useState(false);

  const handleMultiChangeSpecialFeatures = selectedOption => {
    setValue("specialFeatures", selectedOption, true);
    setSpecialFeatures(selectedOption);
    setShowAnimal(selectedOption.some(option => option.value === "animals")); // Toggle 'showAnimal'
  };

  return (
    <div>
      <form onSubmit={handleSubmit(onSubmit)}>
        <label>Does this proposal incldue any of these features?</label>
        <Select
          className="reactSelect"
          name="specialFeatures"
          placeholder="Select at least one"
          value={valuesSpecialFeatures}
          options={specialFeatures}
          onChange={handleMultiChangeSpecialFeatures}
          isMulti
        />
        {showAnimal && <Animal />} // Render component based on the toggle
        <input type="submit" value="next" />
      </form>
    </div>
  );
};

不过有一个更简单的替代方案,它不涉及将值设置为状态,您可以在渲染期间派生它:

const Method = props => {
  const { register, handleSubmit, setValue, errors, reset } = useForm();

  const [valuesSpecialFeatures, setSpecialFeatures] = useState([]);

  const handleMultiChangeSpecialFeatures = selectedOption => {
    setValue("specialFeatures", selectedOption, true);
    setSpecialFeatures(selectedOption);
  };

  // Derive the value based on the value of `valuesSpecialFeatures`
  const isAnimalSelected = valuesSpecialFeatures.some(
    option => option.value === "animals"
  );

  return (
    <div>
      <form onSubmit={handleSubmit(onSubmit)}>
        <label>Does this proposal incldue any of these features?</label>
        <Select
          className="reactSelect"
          name="specialFeatures"
          placeholder="Select at least one"
          value={valuesSpecialFeatures}
          options={specialFeatures}
          onChange={handleMultiChangeSpecialFeatures}
          isMulti
        />
        {isAnimalSelected && <Animal />} // Use derived value to render component
        <input type="submit" value="next" />
      </form>
    </div>
  );
};

推荐阅读