我对React
并不陌生,我正在尝试向已经存在的新组件中添加新组件,但是我不确定该怎么做。
因此,这里有Seances
的列表以及添加更多内容的按钮:
SeanceManager.js
return (
<MDBRow>
<MDBCol md="6">
<MDBCard>
<MDBCardBody>
<form>
<p className="h4 text-center py-4">Sign up</p>
<div className="grey-text">
<MDBInput
label="Type your email"
icon="envelope"
group
type="email"
validate
error="wrong"
success="right"
/>
<MDBInput
label="Type your password"
icon="lock"
group
type="password"
validate
/>
</div>
<div className="text-center py-4 mt-3">
<MDBBtn color="cyan" type="submit" onClick={props.submitLogin}>
Log in
</MDBBtn>
</div>
</form>
</MDBCardBody>
</MDBCard>
</MDBCol>
</MDBRow>
);
通过按按钮添加更多内容,将弹出一个模式视图,最后它具有一个submit
按钮,应添加Seance
。
AddSeanceModal.js
return (
<Modal
{...this.props}
size="lg"
aria-labelledby="contained-modal-title-vcenter"
centered
>
<Modal.Header closeButton>
<Modal.Title id="contained-modal-title-vcenter">Add Seance</Modal.Title>
</Modal.Header>
<Modal.Body>
<div>
<form>
{/*First row*/}
<MDBRow>
<MDBCol md="4">
<div className="custom-file">
<input
type="file"
className="custom-file-input"
id="inputGroupFile01"
aria-describedby="inputGroupFileAddon01"
/>
<label className="custom-file-label" htmlFor="inputGroupFile01">
Choose file
</label>
</div>
</MDBCol>
</MDBRow>
{/*Second row*/}
<MDBRow>
<MDBCol md="4">
<MDBInput
onChange={this.changeHandler}
type="text"
id="materialFormRegisterPasswordEx4"
name="algus_aeg"
label="Algus Aeg"
required
/>
</MDBCol>
<MDBCol md="4">
<MDBInput
onChange={this.changeHandler}
type="text"
id="materialFormRegisterPasswordEx4"
name="lopp_aeg"
label="Lõpp Aeg"
required
/>
</MDBCol>
</MDBRow>
{/*Third row*/}
<MDBRow>
<MDBCol md="4">
<MDBInput
onChange={this.changeHandler}
type="text"
id="materialFormRegisterPasswordEx4"
name="aja_samm"
label="Aja Samm"
required
/>
</MDBCol>
</MDBRow>
<Button variant="secondary" onClick={this.props.onHide}>
Close
</Button>
<MDBBtn color="success" type="submit" className="float-right">
Add Seance
</MDBBtn>
</form>
</div>
</Modal.Body>
</Modal>
);
最后是Seance
本身:
Seance.js
return (
<div
className="card"
style={{ marginBottom: "7px" }}
onClick={() => this.setState({ modalShow: true })}
>
<div className="card-body">
<h5 className="card-title">Seance nr: {this.props.id}</h5>
<p className="card-text">Start aeg: {this.props.startDate}</p>
<p className="card-text">End aeg: {this.props.endDate}</p>
<button type="button" className="close float-right" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
<ResultModal id={1} show={this.state.modalShow} onHide={modalClose} />
</div>
</div>
);
我还在沙盒上摆弄了一个小提琴: https://codesandbox.io/s/qloo1vqr7j?fontsize=14
目前,我有4个静态Seances
,但它应以0开头,并在添加后添加更多。
会议上的X
也应将其删除。
我尝试在SeanceManager.js
中的状态上创建列表,但是我还没有理解如何从另一个组件AddSeanceModal
向列表中添加组件。
答案 0 :(得分:1)
有很多代码选择使应用程序无法动态运行。
首先,您需要利用container component
处理与Seance
状态有关的所有事物。其中包括adding
,removing
和viewing
。所有这些都需要由父级处理,该父级必须根据其state
中的当前更新其子级。请按照本指南了解containers vs components。
第二,您需要重构如何利用Seances
。它们需要作为array
存储在父母的state
中。现在,它已经硬编码为4 <Seances />
,无法删除/更新。
相反,您应该在array
中创建object
个state
中的seances: [
{ id: "1", startDate: "2019-04-10 10:28:05.926-07", endDate: "2019-05-10 10:28:05.924-07" },
{ id: "2", startDate: "2019-04-11 11:28:05.926-07", endDate: "2019-05-11 11:28:05.924-07" },
{ id: "3", startDate: "2019-04-12 12:28:05.926-07", endDate: "2019-05-12 12:28:05.924-07" },
...etc
];
:
array
您将利用Array.map来动态映射这些会议return
和implicitly <Seance id={id} />
这些会议(为了易于阅读,我正在编写您的{{ 1}}内联组件):
<div>
{seances.map(({ id, startDate, endDate }) => (
<div key={id}>
<h1>Seance nr: {id} </h1>
<p>Start date: {startDate}</p>
<p>End date: {endDate}</p>
<button type="button" onClick={() => handleDeleteSeance(id)}>X</button>
</div>
))}
</div>
现在,您将通过seance的seances
属性利用Array.filter从id
数组中删除这些项目。用户单击“ X”按钮时,它将以特定的this.handleDeleteSeance
调用id
:
handleDeleteSeance = id => {
this.setState(prevState => ({
...prevState, // spread out any previous state not related to "seances"
seances: prevState.seances.filter(seance => seance.id !== id) // this translates to: compare each "seance" within "seances" and implicitly return any that do NOT match the "id" that was clicked
})
};
要将项目添加到seances
数组中,您将利用spread operator,并添加具有从object
收集的属性的form
:>
handleSubmit = e => {
e.preventDefault();
const { id, startDate, endDate } = this.state;
if (!id || !startDate || !endDate } return null; // if any properties are missing, don't add an item yet
this.setState(prevState => ({
...prevState, // spread out any previous state not related to "seances"
seances: [...prevState.seances, { id, startDate, endDate } ] // this translates to: spread out any previous seances and add a new object with "id", "startDate" and "endDate"
});
}
使用数组示例(由于这是一个仅用于客户端的实现,因此我决定按数组位置进行过滤,因此不必处理生成唯一的id
;但是,您可以根据需要使用uuid生成这些动态id
):
其他说明:
let modalClose = () =>
this.setState({ modalShow: false });
方法中包含一个render
。
这是无效的,应将其定义为类方法。FileInput
)。随着应用程序的增长,您可能需要在其他地方使用FileInput
来获得另一种形式。props
组件deconstruct Login
像这样:const Login = ({ submitLogin }) => ( <MDBRow>...etc</MDBRow>);
。