javascript - 如何在 React 中正确实现嵌套的动态表单
问题描述
我正在尝试使用具有以下 JSON 输出的 React 类组件来实现嵌套的动态表单:
"basketData": [
{
"finalTransfer": "",
"averageDistance": ""
"shares": [
"share01": "6",
"share02": "10",
]
},
{
"finalTransfer": "",
"averageDistance": ""
"shares": [
"share01": "21",
"share02": "18",
"share03": "7",
"share04": "32",
]
}
]
我希望能够通过表单动态添加多个购物篮数据,并在每个购物篮数据中动态添加共享字段。
以下几个示例到目前为止我有下面的实现,但是 JSON 输出不正确。
class Step3a extends React.Component {
constructor(props) {
super(props);
this.state = {
baskets: [{ finalTransfer: "", averageDistance: "" }],
shares: [{ share: "" }],
};
}
handleChange = (index, event) => {
const { name, value } = event.target;
const values = [...this.state.baskets];
values[index][name] = value;
this.setState({ values });
};
addBasket = () => {
this.setState((prevState) => ({
baskets: [
...prevState.baskets,
{ finalTransfer: "", averageDistance: "" },
],
}));
};
removeBasket = (index, event) => {
let baskets = [...this.state.baskets];
baskets.splice(index, 1);
this.setState({ baskets });
};
handleShareChange = (idx) => (event) => {
const newShares = this.state.shares.map((share, sidx) => {
if (idx !== sidx) return share;
return { ...share, name: event.target.value };
});
this.setState({ shares: newShares });
};
handleAddShare = () => {
this.setState({
shares: this.state.shares.concat([{ name: "" }]),
});
};
handleRemoveShare = (idx) => () => {
this.setState({
shares: this.state.shares.filter((s, sidx) => idx !== sidx),
});
};
isValidated() {
return true;
}
render() {
const { classes } = this.props;
let { baskets, shares } = this.state;
return (
<GridContainer justify="center">
<GridItem xs={12} sm={12}>
<h4 className={classes.infoText}>How about you add a baskets</h4>
</GridItem>
<GridItem xs={12} sm={12}>
{baskets.map((val, idx) => {
return (
<Card>
<CardContent>
<GridItem xs={12} sm={12}>
<h4>BasketData {idx + 1}</h4>
</GridItem>
<GridItem xs={12} sm={4}>
<TextField
fullWidth={true}
name="finalTransfer"
label="Final Transfer"
value={val.finalTransfer}
onChange={(event) => this.handleChange(idx, event)}
/>
</GridItem>
<GridItem xs={12} sm={4}>
<TextField
fullWidth={true}
name="averageDistance"
label="Average Distance"
value={val.averageDistance}
onChange={(event) => this.handleChange(idx, event)}
/>
</GridItem>
<Card>
<CardContent>
{shares.map((share, index) => {
return (
<GridItem xs={12} sm={4}>
<input
type="text"
placeholder={`Share #${index + 1} name`}
value={share.name}
onChange={this.handleShareChange(index)}
/>
<button
type="button"
onClick={this.handleRemoveShare(index)}
className="small"
>
Remove Share
</button>
</GridItem>
);
})}
<GridItem>
<button
type="button"
onClick={this.handleAddShare}
className="small"
>
Add Share
</button>
</GridItem>
</CardContent>
</Card>
<GridItem xs={12} sm={4}>
<Button
color="rose"
className={"Submit"}
onClick={(event) => this.removeBasket(idx, event)}
>
Remove BasketData
</Button>
</GridItem>
</CardContent>
</Card>
);
})}
</GridItem>
<GridItem xs={12} sm={4}>
<Button color="rose" className={"Submit"} onClick={this.addBasket}>
Add BasketData
</Button>
</GridItem>
</GridContainer>
);
}
}
Step3a.propTypes = {
classes: PropTypes.object,
};
export default withStyles(style)(Step3a);
通过上面的实现,我得到了一个1 个 basketData的输出,不幸的是它不能满足我的需要。
"basketData": [
{
"basketData": [
{
"finalTransfer": "",
"averageDistance": ""
}
],
"shares": [
{
"share": 0
},
{
"share": 0
}
],
"finalTransfer": "100",
"averageDistance": "180"
}
]
我怎样才能正确实施它?
解决方案
好像你忘记了列表的键。这就是您在列表中获得重复数据的原因。
如果您像这样映射数组,则需要为每个项目添加一个唯一键:但尽量不要使用索引,而是使用唯一 id,可能会自动生成以处理删除。
这是您的代码的工作沙箱。
推荐阅读
- python - 在 Python 中,我想打印同心正方形,因为我已经编写了代码,但我没有得到想要的输出
- javascript - Mutation Response from Schema When Object is Returned
- python - How to display the best fit equation (in text form) on plot when using numpy.polyfit?
- java - Java替换字符串中的一个字符
- php - 添加到数组中的数组(构建数据组)
- ruby-on-rails - PSQL 连接问题
- plot - Matlab/Octave - 解析和绘制日期字符串与整数
- javascript - Adding a skip button to my gif preloader for a website
- python - 将所有文件从目录树移动到另一个目录。重命名,如果重复名称
- angularjs - AngularJs waith before dom content loaded