赞
踩
由于视频教程中用的antd版本还是低版本,当时还能用Form.create()方法,但是在本人学习的时候,该方法已经弃用,又觉得要解决问题,不能用降低版本的方式,既然弃用,肯定有新的解决方法,一味的跟视频模仿,学不了更多,首先看新版本的官方文档,
Form中的api,暂时没有找到能解决的,能力有限
<Modal title="修改分类"
visible={showStatus === 2}
onOk={this.updateCategory}
destroyOnClose={true}
onCancel={this.handleCancel}>
<UpdateForm categoryName={category.name}
setForm={(form) => { this.form = form }} />
</Modal>
找到外层Modal的api中有一个
使用这个可以清除
然后就是要在弹出的input框中显示预设修改值,而且不能只是单纯的用placeholder表示,因为placeholder只能展示,如果只是加几个字,还得挨着输入之前一样的数据,所以要把input的state里的value,在一弹出来就添加上,
查了半天,现在的antd4x不支持之前的方法了,可以用setFieldsValue的方法,但是这个方法要配合ref进行使用,用createRef(),在组件没有挂载前,ref并不会传出我们想要的setFieldsValue方法,只有当组件挂载后,ref才有意义,所以我最开始把setFieldsValue方法用在willMount上就报错,为null,要用在didMount中,但是总感觉加在这里,不是一弹出就显示,如果哪个环节加载慢了,就只能显示预设的placeholder了,所以这是双重保险让人眼反应不过来?虽然两者颜色不太一样。但是目前能力有限,暂时只能做到这个样子
componentDidMount() { const { categoryName } = this.props this.formRef.current.setFieldsValue({ input: categoryName//此处的键input是后面Item的name,Item是Form.Item,省略了前面的const Item = Form.Item }) } //为form创建一个ref formRef = React.createRef() render() { const { categoryName } = this.props return ( <Form initialValues={categoryName} ref={this.formRef}//给Form添加ref onValuesChange={this.onFinish} > <Item name='input' > <Input ref={input => this.props.setForm(input)}> </Input> </Item> </Form> ) }
总结,新版本的antd中class形式的Form组件可以用ref传递出Form创造的实例form,并用form的一系列方法,如何动态的使用呢,因为如果提前传出或者半路传出都无法得到想要的值,就可以在Form标签写上 onValueChange事件,进行绑定,在这个事件函数里面写就可以了(2021.4.19补充括号内的提醒,这种做法效率不高,因为每次input输入都会传出,但是只有最后一次完成的时候,传出的才能用,其他的都是冗余的,没有进行防抖,主要也是因为笔者当时还没接触到防抖节流,知道效率不高也没啥办法,当时能想出这种办法就挺高兴了哈哈),但是要在外部,将一个能传出ref的函数写到Form的props里面,如下
外部写:
<UpdateForm
categoryName={category.name}
setForm={(form) => { this.form = form }}
deliverForm={(form) => { this.deliForm = form }}
/>
内部写:
export default class UpdateForm extends Component { //为form创建一个ref formRef = React.createRef() static propTypes = { setForm: PropTypes.func.isRequired, categoryName: PropTypes.string.isRequired, deliverForm: PropTypes.func.isRequired, } deliverResult=()=>{ // 把form对象传出去,实时的,所以最后用的是完整的 this.props.deliverForm(this.formRef.current) } componentDidMount() { const { categoryName } = this.props // 设置的是name为input的组件的value this.formRef.current.setFieldsValue({ input: categoryName }) } componentWillUnmount() { console.log('我是update,我结束了'); } render() { return ( <Form ref={this.formRef} onValuesChange={this.deliverResult}> <Item name='input' rules={[ { required: true, message:'分类名称必须输入' } ]}> <Input ref={input => this.props.setForm(input)} > </Input> </Item> </Form> ) } }
但是//会出现一种情况就是,如果不进行修改数据,就不会触发,那么就不会传出form对象,后续基于form的操作就无法实现
如何让其一上来就传递出form对象呢,可以在didmount里面在写一个,然后就可以保证运行了
componentDidMount() { // 给分类下拉菜单添加初始值value,classer是select组件被包装成Item后的name // select的option,value在这里是设置的c._id,所以会先渲染好每一个option // 此处的预设初始值,是根据value来找到对应的option,该option是渲染好的,会显示c.name,下拉框会对应该项,并显示灰色 // 但是如果我设置此处的value为c.name,但是又是通过parentId找,那就找不到对应的option // 那就会显示一个新的option,value和显示的都是parentId,并且在预先渲染好的下拉框中找不到, const { parentId } = this.props this.formRef.current.setFieldsValue({ classer: parentId }) console.log(this.formRef.current); // 一上来就得有一个form对象传出去,不然外面的操作无法进行 this.props.deliverForm(this.formRef.current) //能工作,但是不能在didmount里面使用,因为这个是为了收集表单数据 // 但是,didmount里面只是刚打开这个弹窗,没有进行操作,所以无法得到想要的数据, // 可以先预设值进去,然后在didmount里用,应该可以,注意先后顺序 // const aa = this.formRef.current.getFieldsValue() // console.log('aa', aa); // this.props.setForm(this.formRef) }
可参考
https://blog.csdn.net/wqylry/article/details/110872012
https://blog.csdn.net/sky_blue6/article/details/108155215
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。