【Vue 开发实战】实战篇 # 40:自己封装一个支持自动校验的表单项

简介: 【Vue 开发实战】实战篇 # 40:自己封装一个支持自动校验的表单项

说明

【Vue 开发实战】学习笔记。



自定义表单控件


自定义或第三方的表单控件,也可以与 Form 组件一起使用。只要该组件遵循以下的约定:


  • 提供受控属性 value 或其它与 valuePropName-参数) 的值同名的属性。
  • 提供 onChange 事件或 trigger-参数) 的值同名的事件。
  • 不能是函数式组件。



实现的组件效果


支持下拉选择,然后自定义校验该组件,提交能把选择的数据传递到接口02e82297064146ea9bff0542b39dabc1.png不通过:fbd02690a4e74822979e5ea7333fec66.png



编写组件

新建 ant-design-vue-pro\src\components\ReceiverAccount.vue

<template>
    <a-input-group compact>
        <a-select v-model="type" style="width: 120px;" @change="handleTypeChange">
            <a-select-option value="alipay">支付宝</a-select-option>
            <a-select-option value="bank">银行账户</a-select-option>
        </a-select>
        <a-input style="width: calc(100% - 120px);" v-model="number" @change="handleNumberChange"/>
    </a-input-group>
</template>
<script>
export default {
    props: {
        value: {
            type: Object,
        },
    },
    data() {
        const { type, number } = this.value;
        return {
            type: type || "alipay",
            number: number || ""
        };
    },
    watch: {
        value(val) {
            // 同步给 type、number
            Object.assign(this, val);
        }
    },
    methods: {
        handleTypeChange(val) {
            this.$emit("change", { ...this.value, type: val });
        },
        handleNumberChange(e) {
            this.$emit("change", { ...this.value, number: e.target.value });
        }
    },
};
</script>
<style></style>


表单的 vuex 添加状态

const state = {
    step: {
        payAccount: "kaimo313",
        receiverAccount: {
            type: "alipay",
            number: ""
        }
    }
}


在 Step1 组件里使用

<template>
    <div>
        <a-form layout="horizontal" :form="form">
            <a-form-item
                label="付款账号"
                :label-col="formItemLayout.labelCol"
                :wrapper-col="formItemLayout.wrapperCol"
            >
                <a-input v-decorator="[
                    'payAccount',
                    {
                        initialValue: step.payAccount,
                        rules: [
                            {
                                required: true,
                                message: '请输入付款账号'
                            }
                        ]
                    },
                ]" placeholder="请输入付款账号" />
            </a-form-item>
            <a-form-item
                label="收款账号"
                :label-col="formItemLayout.labelCol"
                :wrapper-col="formItemLayout.wrapperCol"
            >
                <ReceiverAccount v-decorator="[
                    'receiverAccount',
                    {
                        initialValue: step.receiverAccount,
                        rules: [
                            {
                                required: true,
                                message: '请输入收款账号',
                                validator: (rule, value, callback) => {
                                    if(value && value.number) {
                                        callback();
                                    }else{
                                        callback('收款账号没有填写');
                                    }
                                }
                            },
                        ]
                    },
                ]"/>
            </a-form-item>
            <a-form-item>
                <a-button type="primary" @click="handleSubmit">下一步</a-button>
            </a-form-item>
        </a-form>
    </div>
</template>
<script>
import ReceiverAccount from "@/components/ReceiverAccount.vue";
export default {
    data() {
        this.form = this.$form.createForm(this);
        return {
            formItemLayout:{
                labelCol: { span: 4 },
                wrapperCol: { span: 14 },
            }
        };
    },
    components: { ReceiverAccount },
    computed: {
        step() {
            return this.$store.state.form.step
        }
    },
    created() {
        console.log("this.$store---->", this.$store)
    },
    methods: {
        handleSubmit() {
            const { form, $router, $store} = this;
            form.validateFields((err, values) => {
                console.log(err, values)
                if(!err) {
                    console.log(values);
                    $store.commit({
                        type: "form/saveStepFormData",
                        payload: values
                    });
                    $router.push("/form/step-form/confirm");
                }
            })
        }
    },
};
</script>
<style></style>


目录
相关文章
|
3天前
|
监控 JavaScript 前端开发
使用Vue.js开发员工上网行为监控的实时数据展示页面
使用Vue.js开发的实时员工上网行为监控页面,展示员工访问的网站、应用和时间等数据。页面响应式设计,适应不同设备。通过Vue组件显示实时数据,如`&lt;li v-for=&quot;activity in activities&quot;&gt;`循环渲染。数据定时更新,利用Vue的生命周期钩子和axios从服务器获取并自动刷新,确保数据的时效性。该页面有助于管理者即时了解员工网络活动,保障企业网络安全和资源管理。
23 5
|
3天前
|
JavaScript API
【vue实战项目】通用管理系统:信息列表,信息的编辑和删除
【vue实战项目】通用管理系统:信息列表,信息的编辑和删除
20 2
|
3天前
|
JavaScript 前端开发 API
【vue实战项目】通用管理系统:学生列表
【vue实战项目】通用管理系统:学生列表
16 2
|
3天前
|
缓存 JavaScript
【vue实战项目】通用管理系统:首页
【vue实战项目】通用管理系统:首页
10 2
|
9天前
|
缓存 JavaScript 前端开发
Nuxt.js实战:Vue.js的服务器端渲染框架
Nuxt.js提供了开发、构建和部署的完整工作流。使用nuxt命令启动开发服务器,nuxt build进行生产构建,nuxt start启动生产服务器
16 0
|
10天前
|
JavaScript
|
10天前
|
JavaScript Java 测试技术
基于ssm+vue.js+uniapp小程序的二手交易平台设计与开发附带文章和源代码部署视频讲解等
基于ssm+vue.js+uniapp小程序的二手交易平台设计与开发附带文章和源代码部署视频讲解等
17 0
|
19小时前
|
JavaScript 前端开发 测试技术
使用 Vue CLI 脚手架生成 Vue 项目
通过 Vue CLI 创建 Vue 项目可以极大地提高开发效率。它不仅提供了一整套标准化的项目结构,还集成了常用的开发工具和配置,使得开发者可以专注于业务逻辑的实现,而不需要花费大量时间在项目配置上。
53 7
使用 Vue CLI 脚手架生成 Vue 项目
|
2天前
|
JavaScript 算法
“Error: error:0308010C:digital envelope routines::unsupported”启动vue项目遇到一个错误【已解决
“Error: error:0308010C:digital envelope routines::unsupported”启动vue项目遇到一个错误【已解决
8 1
|
2天前
|
JavaScript
error Component name “Login“ should always be multi-word vue/multi-word-component-names【已解决】
error Component name “Login“ should always be multi-word vue/multi-word-component-names【已解决】
6 1