React Bootstrap验证:在子组件中使用已验证的输入

10

我正在使用react-bootstrap-validation,它修饰了React-Bootstrap的Input标签。

ValidatedInput要求必须在Form组件内部。当我将ValidatedInput添加到自定义子组件中时,会出现错误,说它需要在Form内部,但是我猜它现在在树的更深处,所以无法看到Form。

有没有办法引用父表单(parent Form),这样ValidatedInput就能看到父表单了。

从Validation库的源代码来看,ValidationInput需要向Form注册,但不确定如何从子组件中执行此操作。

// Parent render 
render(){
   <Form
   className="fl-form fl-form-inline fl-form-large"
   name="customer-details"
   onValidSubmit={this._handleValidSubmit}
   onInvalidSubmit={this._handleInvalidSubmit}
   validationEvent='onChange'>
    
     <TitleSelect handleChange={this.updateDropDown} value={this.state.form.title} />
     
   </form>
}


// Sub class containing the ValidatedInput
export class TitleSelect extends React.Component {

    static propTypes = {
      handleChange: React.PropTypes.func.isRequired,
      value: React.PropTypes.string.isRequired
    }

    render(){

        return (
          <ValidatedInput
            name="title"
            label='title'
            type='select'
            value={this.props.value}
            onChange={this.props.handleChange}
            groupClassName='form-group input-title'
            wrapperClassName='fl-input-wrapper'
            validate='required'
            errorHelp={{
              required: 'Please select a title.'
            }}>

            <option value="" ></option>
            <option value="Mr">Mr</option>
            <option value="Mrs">Mrs</option>
            <option value="Master">Mstr.</option>
            <option value="Ms">Ms</option>
            <option value="Miss">Miss</option>
            <option value="Reverend">Rev.</option>
            <option value="Doctor">Dr.</option>
            <option value="Professor">Prof.</option>
            <option value="Lord">Lord</option>
            <option value="Lady">Lady</option>
            <option value="Sir">Sir</option>
            <option value="Master">Mstr.</option>
            <option value="Miss">Miss</option>
          </ValidatedInput>
        )
    }
};


查看检查器以了解React如何解析您的组件。这应该会给你一个起点。 - J. Mark Stevens
2个回答

3

目前这是不可能做到的。在React中,如果我们能够获得适当的基于父级的上下文,那么在未来的版本中将会有可能实现。我会将组件迁移到上下文中。但是目前,我建议您将render()方法拆分为几个较小的方法,并重复使用它们。


关于“将组件迁移到上下文”方面有什么进展吗?同时,你能否用代码示例来说明你的建议?我真的无法理解如何通过“拆分render()函数”来解决这个问题。 - GreenAsJade
目前还没有关于该功能的预计时间,抱歉。至于拆分render()方法,请参考以下示例:https://github.com/react-bootstrap/react-bootstrap/blob/master/src/InputBase.js#L184-L207 - Ivan Reshetnikov

2

如上所述,由于当前设计的限制,现在无法实现。我采用的解决方案是这样的。

  1. Convert subcomponent to plain JS object

    TitleSelect = {
      // move prop types to parent
      renderTitleSelect(){
        ...
      }
    }
    
  2. Add new object as a mixin to parent and render a function

    mixins: [TitleSelect],
    ...
    render() {
      <Form ...>
        // parentheses are important!
        {this.renderTitleSelect()}
      </Form>
    }
    

谢谢,我听说混入将在某个时候被移除,所以不想走这条路。我想我只需将我的输入移出子组件,直到我们能够引入上下文为止。 - Will
我没有看到任何有关移除mixin的提及(说实话这很奇怪,因为这种机制是必要的),而切换到上下文可能需要很长时间。 - Mike Szyndel
阅读此文章 https://medium.com/@dan_abramov/mixins-are-dead-long-live-higher-order-components-94a0d2f9e750 ,作者在 React Europe 的演讲中也提到了这个问题。我认为在我们解决上下文问题之前可能不会使用子组件。 - Will
有进展吗?我读了相关文章,发现很难理解如何使用那里描述的内容来解决这个问题。 - GreenAsJade
我最终使用了类似答案中所示的混合方法。 - Will

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接