如何使用通用句柄更新以下状态适用于以下方案的更改:



>我有一个组件和以下状态:

this.state = {
    form : {
        name : '',
        username: '',
        email: '',
        phone: '',
        address: {
            street: '',
            suite: '',
            city: '',
            zipcode: ''
        }
    }
}

在表单字段中,我在 onChange 中使用以下方法:

handleChange(e) {
    const {name, value} = e.target;
    let copyState = Object.assign({}, this.state);
    copyState.form[name] = value;
    this.setState(copyState);
}

下面是功能表单域的示例:

<input value={this.state.form.username} 
    onChange={this.handleChange} 
    name="username"
    type="text" 
    className="form-control" 
/>

这不起作用:

<input value={this.state.form.address.street} 
   onChange={this.handleChange} 
   name="address.street"
   type="text"
   className="form-control" 
/>

handleChange 方法可以完美地处理项目:姓名、用户名、电子邮件和电话,但在属于地址的属性中则不然。

如何解决这个问题?

非常感谢。:)

因为addressform状态内的嵌套对象。我们可以做这样的事情:您可以像这样更改句柄更改函数:

handleChange = (name, value, isAddress) => {
  let { form } = this.state;
  let {address}=form
  if(isAddress){
    address[name]=value
  }else{
  form[name] = value;      
  }    
  this.setState({ form: {...form, address} });
}

您的组件代码将如下所示:

class Forms extends React.Component {
  constructor() {
    super();
    this.state = {
      form: {
        name: "",
        username: "",
        email: "",
        phone: "",
        address: {
          street: "",
          suite: "",
          city: "",
          zipcode: ""
        }
      }
    };
    this.handleChange = this.handleChange.bind(this);
  }
  handleChange = (name, value, isAddress) => {
    let { form } = this.state;
    let {address}=form
    if(isAddress){
      address[name]=value
    }else{
    form[name] = value;      
    }    
    this.setState({ form: {...form, address} });
  }
  render() {
    let { form } = this.state;
    return (
      <div>
        Name: {form.name}
        <br />
        Username: {form.username}
        <br />
        email: {form.email}
        <br />
        phone: {form.phone}
        <br /> Street: {form.address.street}
        <br /> Suite: {form.address.suite}
        <br /> City: {form.address.city}
        <br /> Zipcode: {form.address.zipcode}
        <br />
        <input
          value={this.state.form.name}
          onChange={(e) => this.handleChange('name', e.target.value)}
          name="name"
          type="text"
          className="form-control"
        />
        <br />
        <input
          value={this.state.form.username}
          onChange={(e) => this.handleChange('username', e.target.value)}
          name="username"
          type="text"
          className="form-control"
        />
        <br />
        <input
          value={this.state.form.email}
          onChange={(e) => this.handleChange('email', e.target.value)}
          name="email"
          type="text"
          className="form-control"
        />
        <br />
        <input
          value={this.state.form.phone}
          onChange={(e) => this.handleChange('phone', e.target.value)}
          name="phone"
          type="text"
          className="form-control"
        />
        <br />
        <input
          value={this.state.form.address.street}
          onChange={(e) => this.handleChange('street', e.target.value, true)}
          name="street"
          type="text"
          className="form-control"
        />
        <br />
        <input
          value={this.state.form.address.suite}
          onChange={(e) => this.handleChange('suite', e.target.value, true)}
          name="suite"
          type="text"
          className="form-control"
        />
        <br />
        <input
          value={this.state.form.address.city}
          onChange={(e) => this.handleChange('city', e.target.value, true)}
          name="city"
          type="text"
          className="form-control"
        />
        <br />
        <input
          value={this.state.form.address.zipcode}
          onChange={(e) => this.handleChange('zipcode', e.target.value, true)}
          name="zipcode"
          type="text"
          className="form-control"
        />
        <br />
      </div>
    );
  }
}

这是现场演示

希望对:)有所帮助

如果你想使用嵌套的命名空间,你必须用点来分割,因为你不能做obj["foo.bar"]

handleChange(event) {
  const path = event.target.name.split('.');
  const depth = path.length;
  const state = { ...this.state };
  let stateRef = state;
  for (let i = 0; i < depth; i += 1) {
    if (i === depth - 1) {
      stateRef[path[i]] = event.target.value;
    } else {
      ref = stateRef[path[i]];
    }
  }
  this.setState(state);
}

最新更新