动态将子功能嵌入主表单

在处理根据所选数据不同,呈现不同表单的时候,通常我们会创建多个功能来动态调用,但是这个需要将所有情况都考虑,将每一种情况都设计一个功能,这种实现方式比较麻烦,会重复大量工作,且无法满足动态调取多个功能表单一起呈现的需求。例如,在产品组合bom的场景中,需要根据所选的bom类型集合,列出所有对应需要填写的bom规格表单。下面讲解如何实现该种需求。

设计思路:

在白码低代码开发平台上分别将不同类型bom对应的表单功能创建出来,作为子功能,再创建一个主体功能,根据用户选择的bom清单,动态将其对应的子表单调取呈现到主体功能表单中,当主体表单功能提交后,将所有子表单功能提交。

准备工作:

1、bom类型表,并添加几个类型数据。

2、创建产品表,记录产品的主题信息

3、针对不同类型bom创建对应的规格表,表中必须包含“产品-关联-产品表”字段。

4、创建各bom规格表的新建功能,以钢板类型为例:

1) 创建“数据-选择-产品表”步骤

2) 获取选择产品步骤id

3) 将子功能表单加载到主功能表单时,不希望“选择产品”步骤也显示出来,因此添加预处理步骤,将该步隐藏

编写以下代码:

function prepare($programStore, $form, vue) {
    let procedure = "60d54fb612849c106b6739b9";//选择产品步骤id
    $programStore.dispatch("helper/hide", { procedure });
}

4) 添加“数据-新增-高板规格表”步骤,将“产品”字段设为“选择产品”并隐藏,其余字段根据需求设为填写。

5) 将功能发布,并获取功能id,备用

其他bom规格功能以此类推。

5、创建新增产品功能:

1) 添加“数据-新增-产品表”步骤

2) 添加“集合-选择-bom规格”步骤

3) 获取“选择bom规格”步骤id、“类型”id

4) 添加“交互-预处理”步骤

编写以下代码:

function prepare($programStore, $form, vue) {
 
    //bom规格对应功能id
    let flowMap = {
        "钢化玻璃": "60d552910d777b106434024c",
        "钢板": "60d54fb1bfea51105dfbd4e2",
}
 
    let flowList = []; //需要调用的功能
    let programMap = {};//子功能
let programElements = [];//子功能元素
 
    let proProcedure = "60d5530c87c96b1063ffc75f"; //产品信息步骤id
    let bomTypesProcedure = "60d55352bfea51105dfbd4ff";//选择bom规格步骤id
let typeField = "60d54c7a0d777b10643401ff";//类型id
 
    //子表单插入到该步骤后
    let insertProcedure = "60d55352bfea51105dfbd4ff";//选择bom规格步骤id
    //监控选择bom规格
    vue.$watch(() => { return programStore.getters["getFormValue"](bomTypesProcedure) },
        function (value, oldValue) {
            if (!_.isEqual(value, oldValue)) {//数据变动
                // 清空旧的子表单
                for (let i = 0; i < programElements.length; i++) {
                    let el = programElements[i];
                    if (el) {
                        el.remove();
                        if (el.__vue__) {
                            el.__vue__.$destroy();
                        }
                    }
                }
                flowList = [];
                programMap = {};
                programElements = [];
 
                //选择bom规格步骤数据
                let bomTypes = value.data || [];
                for (let i = 0; i < bomTypes.length; i++) {
                    let type = bomTypes[i][typeField] || ""; //类型
                    if (flowMap[type]) {
                        flowList.push(flowMap[type]);//添加需要调用的功能id
                    }
                }
 
                //插入子功能表单
                run(programElements, programMap, flowList, insertProcedure).then(() => {
                    let pro = programStore.getters["getFormValue"](proProcedure);//选择产品数据
                    let children = Object.values(programMap);
                    for (let i = 0; i < children.length; i++) {
                        let child = children[i];
                        //更新子功能的表单-选择产品
                        child.dispatch("set", {
                            index: 0,//第一个步骤
                            value: pro
                        });
                    }
                });
 
                //本功能提交钩子
                $programStore.dispatch("handler/set", {
                    //提交后
                    after: async function (store, result) {
                        let children = Object.values(programMap);
                        for (let i = 0; i < children.length; i++) {
                            let child = children[i];
                            //提交子表单
                            await child.dispatch("submit");
                        }
                    }
                })
            }
        }
);
 
    //生成表单组件的方法
    const createProgram = async (flow) => {
        //获取功能
        let program = await vue.$store.dispatch("program/display", { flow });
        // 生成组件
        let view = await vue.$store.dispatch("component/build", function (h) {
            //参考vue createElement
            return h("BmProgram", {
                props: {
                    program
                }
            })
        });
        //组件element
        let $el = view.$el;
        //子功能的view
        let childView = view.view;
        //子功能的store
        let childStore = childView.programStore;
        return {
            view: childView,
            store: childStore,
            $el: $el
        }
}
 
    //插入表单组件的方法
    let run = async (children, childrenMap, list, procedure) => {
        for (let i = 0; i < list.length; i++) {
            let flow = list[i];
            //生成功能
            let program = await createProgram(flow);
            //element插入到列表
            children.push(program.$el);
            //设定映射关系
            childrenMap[flow] = program.store;
        }
        //插入到对应位置
        let processElement = document.querySelector(`.bm-process.process-procedure-${procedure}`);
        //插入到步骤后面
        for (let i = 0; i < children.length; i++) {
            processElement.append(children[i]);
        }
    }
}

5) 将功能保存发布。

效果:

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值