大家好,欢迎来到IT知识分享网。
前文回顾
我开源的商城零代码可视化搭建平台Mall-Cook受到大家喜爱,使我深受鼓励。本着授人以鱼不如授人以渔思想,在项目新建shelf分支,带大家从零开发一个自己的可视化搭建平台。
前面我们已经:
-
介绍了可视化搭建的架构,开发了可嵌套搭建面板
-
介绍了物料JSON构建属性面板流水线,开发了基础类型与复合类型属性的构建
本章目的
前面我们已经开发了物料JSON构建属性面板流水线,通过物料JSON这张身卡来解析构建物料属性面板。
因为JSON是无规则的,所以我们定义了JSON Schema规范来约束JSON。
可按照规范编写JSON费时费力,且容易出错,为了避免手动繁琐编写的JSON,我们选择开发Json Schema生成器,通过可视化组装属性面板,生成符合平台JSON Schema规范的JSON,补上整条流水线的最后一环。
Json Schema生成器
类似可视化搭建,我们通过拖拽各类型的物料操作组件,可视化的组装属性面板,然后解析成JSON。
基础演示
前文我们介绍了复合类型,所以需提供组件嵌套,实现object、array类型的容器嵌套
对象类型
对象数组类型
构建标题物料属性面板
我们举个栗子可视化组装标题物料的属性面板
标题物料的属性面板
Schema生成器构建
导出JSON
开发
接下来我们来开发Json Schema生成器,功能主要分为:
- 注册属性类型操作组件JSON
- 开发生成器可嵌套搭建面板
- 生成JSON
生成器可嵌套搭建面板
开发逻辑每个类型操作组件包里,也有一个initializing.js作为它的身份卡。然后我就根据这个规则,利用require.context遍历custom-schema-template包下文件,找到所有initializing.js进行注册
注册类型操作组件,创建$cmpConfig(操作组件描述数组)
// 获取所有属性配置组件 initializing
function registerSchemaInitializing() {
const files = require.context("@/custom-schema-template", true, /initializing.js$/);
const list = [];
files.keys().forEach((key) => {
let name = key.replace(/(\.\/|\/initializing.js)/g, "");
let [, , componentName] = key.split('/') // 获取组件名
list.push({ component: componentName, ...files(key).default })
});
Vue.prototype.$cmpConfig = list
}
IT知识分享网
开发生成器可嵌套搭建面板
我们使用的拖拽插件是vuedraggable,主要逻辑为拖拽模板物料到页面面板,深拷贝物料配置数据到页面配置中。
IT知识分享网<!-- 生成器搭建面板 -->
<template>
<div class="canvas">
<!-- 页面面板 -->
<div class="canvas-center">
<div class="canvas-center-drag">
<schema-content-item :componentList.sync="content.model.componentList" ></schema-content-item>
</div>
</div>
<!-- 物料模板列表 -->
<div class="canvas-left">
<draggable v-model="$cmpConfig" :options="{ group: { name: 'itxst', pull: 'clone' }, sort: false }" :clone="handleClone" animation="300" >
<div v-for="(item, index) in $cmpConfig" :key="index" class="canvas-left-item" >
<span class="f13">{{ item.label }}</span>
<span class="canvas-left-item-type">{{ item.type }}</span>
</div>
</draggable>
</div>
<!-- 属性面板 -->
<div class="canvas-right">
<component v-if="content.curComponent" :is="curComponentConfig" v-bind="content.curComponent" ></component>
<schema-component v-else></schema-component>
</div>
</div>
</template>
<script> export default { inject: ["content"], computed: { curComponentConfig() { return `${this.content?.curComponent?.component}Config`; }, }, methods: { // 拷贝模板,生成组件 handleClone(model) { return { ...this._.cloneDeep(model), id: this.$getRandomCode(8), property: `${model.type}_${this.$getRandomCode(2, false)}`, }; }, }, }; </script>
想要实现可嵌套物料主要有三点:
- 物料中包含slot,已供子物料存放
- 物料配置中增加children属性,用于存放子物料配置
- 递归渲染物料实现无限层级嵌套
<!-- 递归可嵌套组件 -->
<template>
<draggable v-model="list" group="itxst" ghostClass="ghost" chosenClass="chosen" selector="selector" :animation="500" :sort="true" :class="[isChild ? 'drag-child' : 'drag-area']" >
<schema-content-shape v-for="item in list" :key="item.id" :data="item">
<component :is="item.component" :component-key="item.id" :edit="true" v-bind="item" :class="[['object', 'array'].includes(item.type) ? '' : 'event-none']" >
<!-- 包含slot的组件才能进行嵌套渲染 -->
<schema-content-item :componentList.sync="item.child" // 子物料列表 :isChild="true" // 是否为子物料 ></schema-content-item>
</component>
</schema-content-shape>
</draggable>
</template>
编译生成JSON
组合把组件列表解析成JSON,由于存在复合类型,所以属性(fields)有可能为树状结构
IT知识分享网// 编译物料JSON
parsing () {
this.config = {
label: this.content.model.label,
icon: this.content.model.icon,
fields: {}
}
this.content.model.componentList.map(cmp => {
this.parsingFields(cmp, this.config.fields)
})
this.isComplete = true
},
// 递归解析物料属性
parsingFields (config, fields) {
let { property, label, type, child, value, data, options } = config
let target = (fields[property] = ['object', 'array'].includes(type)
? { label, type }
: { label, type, value })
data && (target.data = data)
options && (target.options = options)
if (child) {
target.child = {}
child.map(c => this.parsingFields(c, target.child))
}
}
下一节预告
- 开发多页面构建
- 开发模板项目,实现实时预览与封面自动生成
系列文章
- 【平台开源】基于Vue实现商城可视化无代码搭建平台 Mall-Cook
- 手把手带你开发一个低代码可视化平台(一)拖拽搭建面板开发
- 手把手带你开发一个低代码可视化平台(二)拖拽搭建面板开发
- 手把手带你开发一个低代码可视化平台(三)拖拽搭建面板开发
交流群
交流群二维码可在项目github首页查看Mall-Cook主页
免责声明:本站所有文章内容,图片,视频等均是来源于用户投稿和互联网及文摘转载整编而成,不代表本站观点,不承担相关法律责任。其著作权各归其原作者或其出版社所有。如发现本站有涉嫌抄袭侵权/违法违规的内容,侵犯到您的权益,请在线联系站长,一经查实,本站将立刻删除。 本文来自网络,若有侵权,请联系删除,如若转载,请注明出处:https://yundeesoft.com/9440.html