访问表单值 - 数据数组

时间:2017-06-15 04:05:23

标签: reactjs

我正在使用数据库中的数据数组呈现表单。当我提交表单handleFormSubmit(event)时,我需要获取所有输入字段。由于我不知道输入字段的调用内容或输入字段的数量,我该如何访问这些值?

function CareerPosition(props) {
  return (
    <li>
      <SingleInput
        inputType={'text'}
        title={'Company name'}
        name={'position.company'}
        controlFunc={this.handleInputChange}
        defaultValue={props.companyName}
        placeholder={'Company name'}
        bsSize={null}
      />
    </li>

  )
}

export default class CareerHistoryFormPage extends Component {
  constructor(props) {
    super(props);

    this.state = {
      'position.company': '',
      'position.title': '',
      profileCandidateCollectionId: null,
      errors: {}
    };

    this.handleFormSubmit = this.handleFormSubmit.bind(this);
    this.handleInputChange = this.handleInputChange.bind(this);
  }

  handleInputChange(event) {
    const target = event.target;
    const value = target.type === 'checkbox' ? target.checked : target.value;
    const name = target.name;

    this.setState({
      [name]: value
    });
  }

  renderCareerPositions(props) {
    const profileCandidateCollection = this.props.profileCandidate;
    const careerHistoryPositions = profileCandidateCollection && profileCandidateCollection.careerHistoryPositions;

    if(careerHistoryPositions) {
      const careerPositions = careerHistoryPositions.map((position) =>
        <CareerPosition
          key={position.uniqueId}
          companyName={position.company}
          positionTitle={position.title}
          uniqueId={position.uniqueId}
        />
      );
      return (
        <ul>
          {careerPositions}
        </ul>
      )
    }
  }

  handleFormSubmit(event) {
    event.preventDefault();

    console.log("AllFormData:", this.state.value);
  }

  render() {
    return (
      <Row className="show-grid">
        <Col sm={12} md={3}>
          <EditCandidateProfileLinks />
        </Col>
        <Col sm={12} md={9}>
          <div className="paper">
            <form className="careerHistoryForm" onSubmit={this.handleFormSubmit}>
              <section className="form-title">
                <h3 className="text-center">Career History</h3>
              </section>
              <hr />
              <section className="form-content">
                {this.state.errors.databaseError ? <AlertNotification bsStyle="danger" error={this.state.errors.databaseError} /> : '' }

                {this.renderCareerPositions()}

                <SingleInput
                  inputType={'text'}
                  title={'Company name'}
                  name={'position.company'}
                  controlFunc={this.handleInputChange}
                  content={this.state['position.company']}
                  placeholder={'Company name'}
                  bsSize={null}
                  error={this.state.errors['position.company']}
                />

                <SingleInput
                  inputType={'text'}
                  title={'Title'}
                  name={'position.title'}
                  controlFunc={this.handleInputChange}
                  content={this.state['position.title']}
                  placeholder={'Title'}
                  bsSize={null}
                  error={this.state.errors['position.title']}
                />

              </section>
              <hr />
              <section className="form-buttons">
                <input type="submit" className="btn btn-primary" value="Save" />
              </section>
            </form>
          </div>
        </Col>
      </Row>
    );
  }
}

CareerHistoryFormPage.propTypes = {
  profileCandidate: PropTypes.object
};

1 个答案:

答案 0 :(得分:1)

我认为我们可以使用一些细微的变化来使其工作。

如您所述,数据位于您所在的州,如下所示:

this.state = {
  'position.company': '',
  'position.title': '',
  /*... There are some "service" accommodating data...*/
  profileCandidateCollectionId: null,
  errors: {}
};

您无法控制从DB获取的属性数量。让我们重构一下,把所有动态数据放在自己的对象里面,如下所示:

 this.state = {
  data: {
      'position.company': '',
      'position.title': ''
  }
  /*... There are some "service" accommodating data...*/
  profileCandidateCollectionId: null,
  errors: {}
};

现在,在您的渲染方法中,我们可以安全地迭代“数据”的所有属性,并为每个渲染一个输入(无需对此进行硬编码):

render()
{
    var inputs = [];
    for(var pName of Object.keys(this.state.data))
    {
         inputs.push(
                <SingleInput
                  inputType={'text'}
                  title={'Title'}
                  name={pName}
                  controlFunc={this.handleInputChange}
                  content={this.state.data[pName]}
                  placeholder={'Title'}
                  bsSize={null}
                  error={this.state.errors[pName]}
                />
          );
    }
}

注意我省略了如何处理占位符 - 您可以以类似的方式执行此操作。

handleInputChange看起来有点类似于:

handleInputChange(event) {
    const target = event.target;
    const value = target.type === 'checkbox' ? target.checked : target.value;
    const name = target.name;

    var data = {...this.state.data, ...{[name]: value}};

    this.setState({
      data: data
    });
}

现在,在输入任何更改后 - 您的state.data将始终包含更新的数据 - 因此无需明确收集它。