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

如何在remix-validated-form中重置动态数组输入的旧值?

解决remix-validated-form数组输入框重置旧值的问题

问题根源

你当前的代码存在两个核心问题:

  1. 输入框的name属性未使用数组索引格式(如internalNumber[0]),表单无法区分不同数组项,导致旧值被错误保留。
  2. 未将输入框与表单状态绑定,也没有在下拉框数值变化时主动重置对应字段的状态。

解决方案

借助remix-validated-form的表单状态控制API,监听下拉框的数值变化,主动重置数组字段状态,同时修正输入框的命名与绑定逻辑:

步骤1:修正输入框命名与状态绑定

使用Controller组件或useField钩子,将每个输入框与表单的internalNumber[index]字段绑定,确保状态同步。

步骤2:监听下拉框变化,重置数组字段

当下拉框选中的数量(假设为selectedCount)改变时,调用表单的setValues方法,将internalNumber重置为对应长度的空数组,清空所有旧值。

完整代码示例

import { useForm, Controller } from "remix-validated-form";
import { useState, useEffect } from "react";
import { Form } from "@remix-run/react";

export default function ArrayInputForm() {
  // 下拉框选中的输入框数量
  const [selectedCount, setSelectedCount] = useState(0);
  const { control, setValues, getValues } = useForm();

  // 监听数量变化,重置数组字段
  useEffect(() => {
    setValues({
      ...getValues(), // 保留其他表单字段的值
      internalNumber: Array(selectedCount).fill("")
    });
  }, [selectedCount, setValues, getValues]);

  // 生成对应数量的输入框模板
  const inputList = Array(selectedCount).fill(null);

  return (
    <Form method="post">
      {/* 下拉框组件 */}
      <select
        value={selectedCount}
        onChange={(e) => setSelectedCount(Number(e.target.value))}
      >
        <option value="0">0个输入框</option>
        <option value="1">1个输入框</option>
        <option value="2">2个输入框</option>
        <option value="3">3个输入框</option>
      </select>

      {/* 渲染数组输入框 */}
      {inputList.map((_, index) => (
        <Controller
          key={index}
          name={`internalNumber[${index}]`}
          control={control}
          render={({ field }) => (
            <input
              type="text"
              placeholder="Enter a number"
              {...field}
              className="mt-2 block w-full"
            />
          )}
        />
      ))}

      <button type="submit" className="mt-4 px-4 py-2 bg-blue-500 text-white">
        提交表单
      </button>
    </Form>
  );
}

替代方案:使用useField钩子

如果不想使用Controller,可以直接用useField钩子绑定输入框:

import { useForm, useField } from "remix-validated-form";
import { useState, useEffect } from "react";
import { Form } from "@remix-run/react";

export default function ArrayInputForm() {
  const [selectedCount, setSelectedCount] = useState(0);
  const { setValues, getValues } = useForm();

  useEffect(() => {
    setValues({
      ...getValues(),
      internalNumber: Array(selectedCount).fill("")
    });
  }, [selectedCount, setValues, getValues]);

  const inputList = Array(selectedCount).fill(null);

  return (
    <Form method="post">
      <select
        value={selectedCount}
        onChange={(e) => setSelectedCount(Number(e.target.value))}
      >
        <option value="0">0个输入框</option>
        <option value="1">1个输入框</option>
        <option value="2">2个输入框</option>
      </select>

      {inputList.map((_, index) => {
        const { field } = useField(`internalNumber[${index}]`);
        return (
          <input
            key={index}
            type="text"
            placeholder="Enter a number"
            {...field}
            className="mt-2 block w-full"
          />
        );
      })}

      <button type="submit" className="mt-4 px-4 py-2 bg-blue-500 text-white">
        提交表单
      </button>
    </Form>
  );
}

关键说明

  • 必须使用internalNumber[${index}]格式的name属性,remix-validated-form才能正确识别数组类型字段。
  • 通过setValues在下拉框变化时重置数组,确保新渲染的输入框初始值为空。
  • 绑定field对象到输入框,保证输入框值与表单状态实时同步,重置操作能立即生效。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.17 01:47:50