You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React中使用useState时输入框失焦问题排查求助

React输入框输入时立即失焦的解决办法

问题根源

你的代码里VariantUI组件定义在Footer组件内部,每次Footer因状态更新(比如输入框修改sizeInput、增删颜色/尺寸)重新渲染时,VariantUI都会被重新定义成全新组件。React会卸载旧的VariantUI再挂载新的,这直接导致输入框失去焦点。

另外你更新数组状态时直接修改原数组(比如let temp = sizeArray; temp.push(input);),违反了React状态不可变的原则,也可能引发额外渲染问题。

解决步骤

  • 将内部组件移到外部:把VariantUI和Test组件移到Footer组件外,避免每次渲染都重建组件。需要用到的状态和方法通过props传递。
  • 用不可变方式更新数组状态:更新colorsArray和sizeArray时,不直接修改原数组,而是创建新数组后再调用setter方法。

修改后的完整代码

import React, { useState } from "react";

// 移到外部,所需状态和方法通过props传入
const VariantUI = ({ sizeInput, setsizeInput, sizeArray, sizeElementRemoveHandler }) => {
  return (
    <>
      <div>
        <label>Size</label>
        <input
          id="optionName"
          type="text"
          placeholder="e.g S, M, L, XL"
          onChange={(e) => {
            setsizeInput(e.target.value);
          }}
          value={sizeInput}
        />
      </div>
      <ul>
        {sizeArray.map((data, index) => {
          return (
            <li key={index}>
              {data}
              <i onClick={() => sizeElementRemoveHandler(index)}></i>
            </li>
          );
        })}
      </ul>
    </>
  );
};

const Test = ({ sizeInput, setsizeInput }) => {
  return (
    <input
      type="text"
      onChange={(e) => {
        setsizeInput(e.target.value);
      }}
      value={sizeInput}
    />
  );
};

const Footer = ({ formData }) => {
  const [colorsArray, setColors] = useState(["Red", "Green", "Blue", "Yellow"]);
  const [sizeArray, setSizes] = useState(["S", "M", "L", "XL"]);

  const [sizeInput, setsizeInput] = useState("");

  const colorElementRemoveHandler = (indexToRemove) => {
    const filteredValue = colorsArray.filter((data, index) => {
      return indexToRemove !== index;
    });
    setColors(filteredValue);
  };

  const sizeElementRemoveHandler = (indexToRemove) => {
    const filteredValue = sizeArray.filter((data, index) => {
      return indexToRemove !== index;
    });

    setSizes(filteredValue);
  };

  const addColorHandler = (e) => {
    let input = e.target.value.toLowerCase();
    if (input.length > 2) {
      // 创建新数组,不修改原状态
      setColors([...colorsArray, input]);
    }
  };
  const addSizeHandler = (e) => {
    let input = e.target.value.toUpperCase();
    if (input.length > 0) {
      // 创建新数组,不修改原状态
      setSizes([...sizeArray, input]);
    }
  };

  return (
    <VariantUI 
      formData={formData}
      sizeInput={sizeInput}
      setsizeInput={setsizeInput}
      sizeArray={sizeArray}
      sizeElementRemoveHandler={sizeElementRemoveHandler}
    />
  );
};

export default Footer;

额外说明

  • 你之前用数组index作为key,虽然暂时可用,但如果数组有增删操作,index作为key可能导致React渲染异常,建议如果每个尺寸/颜色有唯一标识(比如id),改用唯一标识当key。
  • 状态更新必须遵循不可变原则,直接修改原数组会让React无法正确检测状态变化,引发各种意外问题。

内容的提问来源于stack exchange,提问作者Techguy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.09 04:40:23