javascript - React 16 Modal 表单更新操作

标签 javascript reactjs ecmascript-6

我是 React-16 的新手,已经完成了 React-16 的保存和删除操作。当涉及到编辑/更新操作时,我发现方法有困难。1)当我点击更新按钮时,打开模式但每个字段中都没有显示值。2)保存后如何更新 setState 函数中的表单值。谢谢。

import React, { Component } from "react";
import {Form,FormGroup,FormControl,Col,Button,Modal,ButtonToolbar,Table} from "react-bootstrap";
class Dashboard extends Component {
  constructor(props) {
    super(props);

    this.state = {
      name: "",
      description: "",
      amount: "",
      date: "",
      show: false,
      formdata: []
    };

    this.handleSubmit = this.handleSubmit.bind(this);
    this.handleInputChange = this.handleInputChange.bind(this);
    this.showModal = this.showModal.bind(this);
    this.hideModal = this.hideModal.bind(this);
    this.showEditModal = this.showEditModal.bind(this);
  }

  showModal() {
    this.setState({ show: true });
  }

  showEditModal(event) {
    this.setState({
      show: true,

      name: this.state.name.value,
      description: this.state.description.value,
      amount: this.state.amount.value,
      date: this.state.date.value
    });
  }

  hideModal() {
    this.setState({
      show: false,
      name: "",
      description: "",
      amount: "",
      date: ""
    });
  }

  handleInputChange(event) {
    this.setState({
      [event.target.name]: event.target.value,
      [event.target.description]: event.target.value,
      [event.target.amount]: event.target.value,
      [event.target.date]: event.target.value
    });
  }
  handleSubmit(event) {
    const formItem = {
      name: this.state.name,
      description: this.state.description,
      amount: this.state.amount,
      date: this.state.date
    };

    if (
      this.state.name === "" ||
      this.state.amount === "" ||
      this.state.date === ""
    ) {
      alert("Please fill mandatory filed");
    } else {
      this.setState(prevState => ({
        formdata: prevState.formdata.concat(formItem)
      }));

      alert("form submited: ");

      this.setState({
        name: "",
        description: "",
        amount: "",
        date: ""
      });
    }
    event.preventDefault();
  }

  deleteExpense(i) {
    alert("are you sure you want to Delete this item ?");
    this.setState({
      formdata: this.state.formdata.filter((item, index) => {
        return index !== i;
      })
    });
  }

  render() {
    return (
      <div>
        <p>Welcome</p>

        <ButtonToolbar>
          <Button bsStyle="primary" onClick={this.showModal}>
            Add Expenses
          </Button>
          <Table striped bordered condensed hover>
            <thead>
              <tr>
                <th>name</th>
                <th>description</th>
                <th>amount</th>
                <th>date</th>
                <th>Action</th>
              </tr>
            </thead>
            <tbody>
              {this.state.formdata.map((item, i) => (
                <tr key={i}>
                  <td>{item.name}</td>
                  <td>{item.description}</td>
                  <td>{item.amount}</td>
                  <td>{item.date}</td>
                  <td>
                    <Button bsStyle="warning" onClick={this.showEditModal}>
                      Update
                    </Button>
                    <Button
                      bsStyle="danger"
                      onClick={() => this.deleteExpense(i)}
                    >
                      Delete
                    </Button>
                  </td>
                  <td />
                </tr>
              ))}
            </tbody>
          </Table>
          <Modal
            {...this.props}
            show={this.state.show}
            onHide={this.hideModal}
            dialogClassName="custom-modal"
          >
            <Modal.Header closeButton>
              <Modal.Title
                id="contained-modal-title-lg "
                className="text-center"
              >
                Add Expenses
              </Modal.Title>
            </Modal.Header>
            <Modal.Body>
              <Form horizontal onSubmit={this.handleSubmit}>
                <FormGroup controlId="formHorizontalEmail">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="Text"
                      placeholder="name"
                      name="name"
                      value={this.state.name}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>
                <FormGroup controlId="formHorizontalPassword">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="description"
                      placeholder="description"
                      name="description"
                      value={this.state.description}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>
                <FormGroup controlId="formHorizontalPassword">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="amount"
                      placeholder="amount"
                      name="amount"
                      value={this.state.amount}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>
                <FormGroup controlId="formHorizontalPassword">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="date"
                      placeholder="date"
                      name="date"
                      value={this.state.date}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>

                <FormGroup>
                  <Col smOffset={5} sm={4}>
                    <Button type="submit" bsStyle="primary">
                      Add
                    </Button>
                  </Col>
                </FormGroup>
              </Form>
            </Modal.Body>
          </Modal>
        </ButtonToolbar>
      </div>
    );
  }
}
export default Dashboard;

最佳答案

在您的 openEditModal() 方法中,您需要将状态值设置为您要编辑的记录(您在表中单击的记录)的值。在这种情况下,您需要查找所选项目、更新状态,然后打开模式。像这样:

import React, { Component } from "react";
import {Form,FormGroup,FormControl,Col,Button,Modal,ButtonToolbar,Table} from "react-bootstrap";

class Dashboard extends Component {
  constructor(props) {
    super(props);

    this.state = {
      name: "",
      description: "",
      amount: "",
      date: "",
      show: false,
      formdata: []
    };

    this.handleSubmit = this.handleSubmit.bind(this);
    this.handleInputChange = this.handleInputChange.bind(this);
    this.showModal = this.showModal.bind(this);
    this.hideModal = this.hideModal.bind(this);
    this.showEditModal = this.showEditModal.bind(this);
  }

  showModal() {
    this.setState({ show: true });
  }

  showEditModal(event, i) {
    const recordToEdit = this.state.formdata.filter((item, index) => {
      return index === i;
    })[0];

    this.setState({
      show: true,

      name: recordToEdit.name,
      description: recordToEdit.description,
      amount: recordToEdit.amount,
      date: recordToEdit.date
    });
  }

  hideModal() {
    this.setState({
      show: false,
      name: "",
      description: "",
      amount: "",
      date: ""
    });
  }

  handleInputChange(event) {
    // update the input that changed
    this.setState({
      [event.target.name]: event.target.value
    });
  }
  
  handleSubmit(event) {
    const formItem = {
      name: this.state.name,
      description: this.state.description,
      amount: this.state.amount,
      date: this.state.date
    };

    if (
      this.state.name === "" ||
      this.state.amount === "" ||
      this.state.date === ""
    ) {
      alert("Please fill mandatory filed");
    } else {
      if (this.state.formdata.filter(item => item.name === formItem.name).length > 0) {
        // update item
        this.setState(prevState => ({
          formdata: prevState.formdata.map(item => {
            if (item.name === formItem.name)
              return formItem;
            else
              return item;
          })
        }));

      } else {
        // add new item
        this.setState(prevState => ({
          formdata: prevState.formdata.concat(formItem)
        }));

      }

      alert("form submited: ");

      this.setState({
        name: "",
        description: "",
        amount: "",
        date: ""
      });
    }
    event.preventDefault();
  }

  deleteExpense(i) {
    alert("are you sure you want to Delete this item ?");
    this.setState({
      formdata: this.state.formdata.filter((item, index) => {
        return index !== i;
      })
    });
  }

  render() {
    return (
      <div>
        <p>Welcome</p>

        <ButtonToolbar>
          <Button bsStyle="primary" onClick={this.showModal}>
            Add Expenses
          </Button>
          <Table striped bordered condensed hover>
            <thead>
              <tr>
                <th>name</th>
                <th>description</th>
                <th>amount</th>
                <th>date</th>
                <th>Action</th>
              </tr>
            </thead>
            <tbody>
              {this.state.formdata.map((item, i) => (
                <tr key={i}>
                  <td>{item.name}</td>
                  <td>{item.description}</td>
                  <td>{item.amount}</td>
                  <td>{item.date}</td>
                  <td>
                    <Button bsStyle="warning" onClick={(e) => this.showEditModal(e, i)}>
                      Update
                    </Button>
                    <Button
                      bsStyle="danger"
                      onClick={() => this.deleteExpense(i)}
                    >
                      Delete
                    </Button>
                  </td>
                  <td />
                </tr>
              ))}
            </tbody>
          </Table>
          <Modal
            {...this.props}
            show={this.state.show}
            onHide={this.hideModal}
            dialogClassName="custom-modal"
          >
            <Modal.Header closeButton>
              <Modal.Title
                id="contained-modal-title-lg "
                className="text-center"
              >
                Add Expenses
              </Modal.Title>
            </Modal.Header>
            <Modal.Body>
              <Form horizontal onSubmit={this.handleSubmit}>
                <FormGroup controlId="formHorizontalEmail">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="Text"
                      placeholder="name"
                      name="name"
                      value={this.state.name}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>
                <FormGroup controlId="formHorizontalPassword">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="description"
                      placeholder="description"
                      name="description"
                      value={this.state.description}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>
                <FormGroup controlId="formHorizontalPassword">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="amount"
                      placeholder="amount"
                      name="amount"
                      value={this.state.amount}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>
                <FormGroup controlId="formHorizontalPassword">
                  <Col smOffset={4} sm={4}>
                    <FormControl
                      type="date"
                      placeholder="date"
                      name="date"
                      value={this.state.date}
                      onChange={this.handleInputChange}
                    />
                  </Col>
                </FormGroup>

                <FormGroup>
                  <Col smOffset={5} sm={4}>
                    <Button type="submit" bsStyle="primary">
                      Add
                    </Button>
                  </Col>
                </FormGroup>
              </Form>
            </Modal.Body>
          </Modal>
        </ButtonToolbar>
      </div>
    );
  }
}
export default Dashboard;

请注意,我将索引传递给 showEditModal() 函数,这样我就可以使用所选记录更新状态。此外,我正在使用每个表单输入的 name="field_name" 属性更新 handleInputChange() 方法中的字段。

旁注:根据 React docs :

We don’t recommend using indexes for keys if the order of items may change. This can negatively impact performance and may cause issues with component state.

考虑为每条记录使用唯一 ID 而不是 map 函数提供的索引。

关于javascript - React 16 Modal 表单更新操作,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47772750/

相关文章:

reactjs - 如何显示 base64 图像 - React Native

javascript - 当不存在构造函数时, `new` 调用的结果。 ES6 类

javascript - Angular- 如何重复具有不同数据的组件?

javascript - 根据对象中的数据对对象数组进行排序,并嵌套它们

javascript - Bootstrap Select2 在键入任何单词之前不会在粘贴时触发选择事件

javascript - 如何使用 Jquery 动态创建 li 内的复选框

reactjs - React 测试库 - userEvent 上传到输入 : "cannot find toLowerCase"

javascript - 从使用react-router的web应用程序解析物理URL

javascript - execCommand ('copy' ) 在 OS X 上的 Chrome 上失败

javascript - 了解 JavaScript 中的生成器