首页 > 解决方案 > 使用嵌套 json 和受控组件反应表单

问题描述

我正在构建一个带有可重用组件的反应表单。

我想更新我的 json 以便我可以嵌套一些数据,但是我遇到了一个“受控与不受控”的错误(再次!),我无法解决。我一直在研究它,但我可能缺乏正确的词汇来提高效率。我应该在哪里或如何定义“宠物”..?

后来,我的目标是能够为一个主人添加几只宠物。

宠物表格

import React, { useState, useEffect } from 'react';
import Controls from './reusables/Controls';
import { useForm, Form } from './reusables/useForm';

const initialFieldValues = {
    id: 0,
    owner: '',
    pet : [{
        petName: '',
        petBreed: ''
    }]
}
export default function PetsForm(props) {
    const {
        values,
        setValues,
        errors,
        setErrors,
        handleInputChange,
        resetForm
    } = useForm(initialFieldValues, true, validate);
 return (
    <Paper>
       <Box>
             <Controls.Input
                   label="Owner"
                   name='owner'
                   placeholder="Owner"
                   value={values.owner = values.owner.toUpperCase()}
                   onChange={handleInputChange}
              />
              <Controls.Input
                   label="PetName"
                   name='petName'
                   placeholder="Pet Name"
                   value={values.petName = values.petName.toUpperCase()}
                   onChange={handleInputChange}
              />
              <Controls.Input
                   label="PetBreed"
                   name='petBreed'
                   placeholder="Pet Breed"
                   value={values.petBreed}
                   onChange={handleInputChange}
              />
        </Box>
   </Paper>
etc...
}

我的 useForm

export function useForm(initialFieldValues, validateOnChange=false, validate) {

    const [values, setValues] = useState(initialFieldValues);
    const [errors, setErrors] = useState({});

    const handleInputChange = event => {
        const { name, value } = event.target 
        setValues({
            ...values,
            [name]: value,
        })
        if(validateOnChange)
        validate({ 
            [name]: value,
        })
    }

    return {
        values,
        setValues,
        errors,
        setErrors,
        handleInputChange,
    };
}

标签: jsonreactjsforms

解决方案


您收到错误是因为您的价值观values.petNamevalues.petBreedundefined。因为你的价值观是

const initialFieldValues = {
    id: 0,
    owner: '',
    pet : [{
        petName: '',
        petBreed: ''
    }]
}

所以petnameandpetBreed必须被称为values.pet.[0].petNameand values.pet.[0].petBreed

设置嵌套对象的值

您可以使用 lodash set设置深度嵌套对象的值。您需要做的就是提供name虚线路径值。对于 petname,您需要将name属性提供为pet.[0].petName

现在我们可以使用 lodash set 设置你的值对象的值,

 const handleInputChange = event => {
        const { name, value } = event.target 
        // clone the values . you can use lodash cloneDeep for this
        set(clonedValues, name, value);
        setValues(clonedValues); 
        ....
    }

现在您可以检索深度嵌套的值

<Controls.Input
    label="PetBreed"
    name='pet.[0].petBreed'
    placeholder="Pet Breed"
    value={values.pet.[0].petBreed}
    onChange={handleInputChange}
 />

推荐阅读