我有应用程序,我从API得到一些数据。然后我把这个数据放入名为"数据"的数组中。然后这个"数据"数组被转换为名为"元素"的组件数组。(数组的子组件由"data"中的数据生成;数组)。当你按下"按钮,将新的空白数据添加到"data"然后使用effect cast updateelements函数,该函数使用这些数据创建子组件,并将这些组件放入"元素"中。数组中。我通过按save按钮创建了testfunc cast,它将console.log的内容设置为"elements"。数组中。同样的事情也发生在function &; handledelete&;从子组件,但它抛出一个没有元素的数组。
在这里你可以尝试一下,看看我在说什么:https://react-tw6smz.stackblitz.io
子组件:
const CategoryField = (props) => {
const [label, setLabel] = useState(props.data.label);
const [categoryId, setCategoryId] = useState(props.data.categoryId);
const [description, setDescription] = useState(props.data.description);
const [uniqueName, setUniqueName] = useState(props.data.uniqueName);
return (
<Row className="categoryBox">
<Col xs={12}>
<Row>
<Col xs={12} className="categoryLabel">
{label}
</Col>
</Row>
<Row>
<Col xs={4} className="categoryFieldTitle">
categoryId:
<input
id="categoryId"
onChange={(e) =>
props.handleChange(e.target.value, props.id, e.target.id)
}
defaultValue={categoryId}
className="categoryInput"
/>
</Col>
<Col xs={8} className="categoryFieldTitle">
description:
<input
id="description"
onChange={(e) =>
props.handleChange(e.target.value, props.id, e.target.id)
}
defaultValue={description}
className="categoryInput"
/>
</Col>
</Row>
<Row>
<Col xs={4} className="categoryFieldTitle">
uniqueName:
<input
id="uniqueName"
onChange={(e) =>
props.handleChange(e.target.value, props.id, e.target.id)
}
defaultValue={uniqueName}
className="categoryInput"
/>
</Col>
<Col xs={8} className="categoryFieldTitle">
label:
<input
id="label"
onChange={(e) => {
setLabel(e.target.value);
props.handleChange(e.target.value, props.id, e.target.id);
}}
defaultValue={label}
className="categoryInput"
/>
</Col>
</Row>
<Row>
<Col xs={12}>
<button
className="categoryDeleteButton"
onClick={(e) => props.handleDelete(props.id)}
>
Delete
</button>
</Col>
</Row>
</Col>
</Row>
);
};
父组件:
export default function App() {
const [data, setData] = useState([]);
const [elements, setElements] = useState();
const addBlank = () => {
let tmp = [...data];
tmp.push({
uniqueName: 'unique_name',
categoryId: 'category_id',
description: 'some description',
label: 'Nazwa',
});
setData(tmp);
};
const handleChange = (change, id, type) => {
let tmp = [...data];
switch (type) {
case 'categoryId':
tmp[parseInt(id)].categoryId = change;
break;
case 'description':
tmp[parseInt(id)].description = change;
break;
case 'uniqueName':
tmp[parseInt(id)].uniqueName = change;
break;
case 'label':
tmp[parseInt(id)].label = change;
break;
}
setData(tmp);
};
const handleDelete = (id) => {
console.log(elements);
};
const updateElements = () => {
let tab = [];
for (let i = 0; i < data.length; i++) {
tab.push(
<CategoryField
key={data[i].uniqueName.toString() + '' + i}
data={data[i]}
id={i}
handleChange={handleChange}
handleDelete={handleDelete}
/>
);
}
setElements(tab);
};
useEffect(() => {
console.log('changed elements');
console.log(elements);
}, [elements]);
useEffect(() => {
// const reqOptions = {
// method: 'GET',
// headers: {
// 'Content-Type': 'application/json',
// },
// };
// fetch('http://127.0.0.1:5050/test', reqOptions)
// .then((res) => res.json())
// .then((dt) => {
// setData(dt);
// });
setData([
{
uniqueName: 'test_name',
categoryId: '434324324',
description: 'Some desc',
label: 'Test Name',
},
]);
}, []);
useEffect(() => {
updateElements();
}, [data]);
const testfunc = () => {
console.log(elements);
};
return (
<div className="main">
<Container>
<Row className="sectionTitleBox">
<Col xs={12} className="sectionTitle">
Categories
</Col>
</Row>
{elements}
<Row>
<Col xs={12}>
<button onClick={testfunc}>Save</button>
<button onClick={addBlank}>Add</button>
</Col>
</Row>
</Container>
</div>
);
}
当你点击"您可以看到添加新元素。"Save"按钮打印"元素"内容;数组与我的数据。如果你按下"删除"键按钮,它也打印元素;数组,但不包含一个元素。
我看到的唯一错误的代码是handleDelete
函数实际上并没有改变数据状态。你只记录当前的数据,不改变它。
你的handleDelete
函数应该是这样的:
const handleDelete = (id) => {
setData(prev => prev.filter(d => d.categoryId !== id))
};
嗯,我看到这是一个可以用useContext解决的问题,在组件之间共享状态和改变函数