在基于Vue的工作流项目模块中,我们在查看表单明细的时候,需要包含公用表单信息,特定表单信息两部分内容。前者表单数据可以统一呈现,而后者则是不同业务的表单数据不同。为了实现更好的维护性,把它们分开作为两部分处理,但是页面入口设计为统一的呈现页面,这里介绍使用动态组件的方式统一呈现不同表单数据的处理方式。

1、表单数据分类

刚才提到,表单数据按内容区分分为了两类:通用业务表单、特定业务表单

如果我们要把两者统一在一个通用页面中进行展示,就需要根据不同表单名称,动态加载属于特定表单的展示模块,也就是动态组件的实现方式,大概的业务规则如下所示。

表单查看的实际效果界面如下所示。

2、动态组件的实现

首先我们需要在前端的路由器集合中加入一个路由地址的配置,以便定位到统一查看表单页面明细的路径,如下所示。

  '_viewDetail': {
path: '/_viewDetail',
meta: {
title: '查看申请单信息'
},
component: Layout,
children: [{
path: '',
component: () => import('@/views/workflow/system/viewdetail')
}]
},

完成后,我们开始编写页面,包含两部分,一部分是通用的表单信息

一部分是动态组件构建的特定表单信息,如下组件代码所示

    <!--实现动态组件的展示-->
<component :is="viewType" :applyid="applyid" />

在我们平时使用vue中的模板的时候,许多时候都是直接定义成一个固定的模板,但是,vue中提供了一个动态模板,可以在任意模板中切换,就是用vue中<component>用:is来挂载不同的组件。

而其中viewType 是一个属性定义,我们可以通过后台API获取对应的模块名称

  methods: {
getViewType () {
if (this.applyid) {
// 通过申请单的DataTable去掉前缀,转换小写,获得模块名称,如TW_Payment => payment
var param = { applyId: this.applyid }
apply.GetModuleName(param).then(data => {
if (data.result) {
this.viewType = data.result.toLowerCase()
}
})
}
},

而其中viewType就是我们组件的名称,这里能够呈现出来的内容,必须是这些组件已经注册到全局中去了,就类似我们在Vue 项目中使用Element组件一样,之所以可以使用它也是它已经全局注册了(或者以组件方式加载到页面)。

而我们定义的表单内容可能很多,如下目录所示。

手工加载这些组件,难免遗漏或者错误,因此需要考虑按一定的规则动态加载进去系统中使用。

我们编写一个js文件,用于动态获取指定目录下的vue组件,并使用Vue.component 动态安装所需组件到系统中,如下代码所示。

export default {
install(Vue) {
// 从模块目录中自动载入模块内容
const viewFiles = require.context('./view', true, /\.vue$/)
const viewModules = viewFiles.keys().reduce((viewModules, modulePath) => {
// set './app.vue' => 'app'
const moduleName = modulePath.replace(/^\.\/(.*)\.\w+$/, '$1').toLowerCase()
const value = viewFiles(modulePath)
viewModules[moduleName] = value.default
return viewModules
}, {}) // console.log(viewModules)
Object.keys(viewModules).forEach(key => {
// console.log(key)
Vue.component(key, viewModules[key])
}) }
}

然后我们在main.js中调用它安装所需组件即可,如下代码所示。

// 导入工作流查看、创建等模块
import workflow from './views/workflow/modules'
Vue.use(workflow)

这样我们就完成了组件的动态加载安装,在通用的查看页面中,就可以通过component的 is 方式动态呈现不同页面表单的数据了。

以支付申请表单为例,我们的payment.vue组件代码如下所示。

<template>
<div class="app-container">
<el-card class="box-card">
<div slot="header" class="clearfix">
<span>付款申请单-表单数据</span>
</div>
<el-form ref="viewForm" :model="viewForm" label-width="120px">
<el-tabs value="basicPage" type="border-card">
<el-tab-pane name="basicPage" label="基本信息">
<el-row>
<el-col :span="24">
<el-form-item label="付款事由">
<el-input v-model="viewForm.reason" readonly />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="付款金额">
<el-input v-model="viewForm.payAmount" readonly>
<span slot="suffix">元</span>
</el-input>
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="付款方式">
<el-input v-model="viewForm.payType" readonly />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="付款日期">
<el-date-picker v-model="viewForm.payDate" align="right" type="datetime" placeholder="选择日期"
value-format="yyyy-MM-dd HH:mm:ss" readonly />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="收款人全称">
<el-input v-model="viewForm.payeeFullName" readonly />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="银行账号">
<el-input v-model="viewForm.bankAccount" readonly />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="开户行">
<el-input v-model="viewForm.bank" readonly />
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item label="备注信息">
<el-input v-model="viewForm.note" readonly type="textarea" :rows="5" />
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item label="附件">
<my-attachment v-model="viewForm.attachGUID" />
</el-form-item>
</el-col>
</el-row>
</el-tab-pane>
</el-tabs>
</el-form>
</el-card> <div class="dialog-footer">
<el-button type="success" @click="goback">返回列表页面</el-button>
</div>
</div>
</template>

并在js代码中定义了prop属性applyid,如下所示。

  props: {
applyid: {// 申请单ID, 接受外部v-model传入的值
type: [String, Number],
default: ''
}
},

这样我们在页面创建的时候,就可以根据applyid来获得对应的特定表单数据,然后页面内容就会正常展示了。

  created () {
this.getData() // 显示数据
},
methods: {
getData () {
if (this.applyid) {
var param = { applyId: this.applyid }
payment.FindByApplyId(param).then(data => {
// console.log(data)
Object.assign(this.viewForm, data.result)
})
}
}

表单查看的实际效果界面如下所示。

这样就完成了我们通过统一的展示页面,展示不同表单数据的统一操作。

查看页面的操作,都通过路由名称_viewdetail实现了统一的跳转。

      <!--表格行操作按钮 -->
<el-table-column align="center" label="操作" width="110">
<template scope="scope">
<el-row>
<el-button-group>
<el-tooltip effect="light" content="查看" placement="top-start">
<el-button icon="el-icon-search" type="success" circle size="mini"
@click="showView(scope.row.apply_ID)" />
</el-tooltip>
<el-tooltip effect="light" content="删除" placement="top-start">
<el-button icon="el-icon-delete" type="danger" circle size="mini" @click="showDelete(scope.row.id)" />
</el-tooltip>
</el-button-group>
</el-row>
</template>
</el-table-column>

JS代码如下

    showView (id) { // 显示查看对话框处理
this.$router.push(
{
path: `/_viewDetail`, // 查看申请单路径,以_view开始
query: { id: id }
})
},

以上就是在Vue的工作流项目模块中,使用动态组件的方式统一呈现不同表单数据的处理方式,希望对您有所启发,在一些特定的场景使用它,可以极大提高灵活性和开发效率。

基于Vue的工作流项目模块中,使用动态组件的方式统一呈现不同表单数据的处理方式的更多相关文章

  1. 基于Vue的Quasar Framework 介绍 这个框架UI组件很全面

    基于Vue的Quasar Framework 介绍 这个框架UI组件很全面 基于Vue的Quasar Framework 中文网http://www.quasarchs.com/ quasarfram ...

  2. strus2中获取表单数据 两种方式 属性驱动 和模型驱动

    strus2中获取表单数据 两种方式 属性驱动 和模型驱动 属性驱动 /** * 当前请求的action在栈顶,ss是栈顶的元素,所以可以利用setValue方法赋值 * 如果一个属性在对象栈,在页面 ...

  3. 基于Vue的WebApp项目开发(二)

    利用webpack解析和打包.vue组件页面 相关知识: vue项目中的每个页面其实都是一个.vue的文件,这种文件,Vue称之为组件页面,必须借助于webpack的vue-loader才能运行,所以 ...

  4. 基于vue脚手架的项目打包上线(发布)方法和误区

    最近要把vue脚手架开发的一个项目上线,只知道vue脚手架是基于node的服务端项目,那么只需要 npm run dev 就可以轻松启动整个项目,当我想当然的给服务器配置合适的node环境(这里也遇到 ...

  5. 基于vue+uniapp直播项目|uni-app仿抖音/陌陌直播室

    一.项目简介 uni-liveShow是一个基于vue+uni-app技术开发的集小视频/IM聊天/直播等功能于一体的微直播项目.界面仿制抖音|火山小视频/陌陌直播,支持编译到多端(H5.小程序.Ap ...

  6. 基于Vue的WebApp项目开发(六)

    实现商品购买列表页面 步骤一:新建goodslist.vue文件 <template> <div id="tml"> <!--利用mui中的图文表格组 ...

  7. 基于Vue的WebApp项目开发(五)

    实现图片分享列表 步骤一:新增图片列表文件photolist.vue <template> <div id="tml"> 图片分享页面 </div&g ...

  8. 基于Vue的WebApp项目开发(四)

    实现新闻咨询页面 目录结构 步骤一:创建newslist.vue文件 <template> <div id="tml"> <!--使用mui框架,实现 ...

  9. 基于Vue的WebApp项目开发(三)

    实现根组件通用的头部和底部样式 明白由webpack搭建起来的Vue项目的执行流程,那么就可以知道实现这个需要只要在根组件和入口文件上做“手脚”即可 <!--以后项目的根组件--> < ...

随机推荐

  1. TypeScript 中命名空间与模块的理解?区别?

    一.模块 TypeScript 与ECMAScript 2015 一样,任何包含顶级 import 或者 export 的文件都被当成一个模块 相反地,如果一个文件不带有顶级的import或者expo ...

  2. RocketMQ详解(四)核心设计原理

    专题目录 RocketMQ详解(一)原理概览 RocketMQ详解(二)安装使用详解 RocketMQ详解(三)启动运行原理 RocketMQ详解(四)核心设计原理 RocketMQ详解(五)总结提高 ...

  3. 动态规划精讲(一)A单串

    单串 单串 dp[i] 线性动态规划最简单的一类问题,输入是一个串,状态一般定义为 dp[i] := 考虑[0..i]上,原问题的解,其中 i 位置的处理,根据不同的问题,主要有两种方式: 第一种是 ...

  4. ❤️【Android精进之路-01】定计划,重行动来学Android吧❤️

    您好,我是码农飞哥,感谢您阅读本文,欢迎一键三连哦. Android精进之路第一篇,确定安卓学习计划. 干货满满,建议收藏,需要用到时常看看.小伙伴们如有问题及需要,欢迎踊跃留言哦~ ~ ~. 前言 ...

  5. java线程day-01

    综述:下面写的是我学习java线程时做的一些笔记和查阅的一些资料总结而成.大多以问答的形式出现. 一.什么是线程? 答:线程是一个轻量级的进程,现在操作系统中一个基本的调度单位,而且线程是彼此独立执行 ...

  6. ecshop调用商品的购买次数方法

    这时候我们修改一下 写成一个函数放到lib_goods.php 这样就可以随便调用了 --------------------------------------------------------- ...

  7. windows10 升级并安装配置 jmeter5.3

    一.安装配置JDK Jmeter5.3依赖JDK1.8+版本,JDK安装百度搜索JAVA下载JDK,地址:https://www.oracle.com/technetwork/java/javase/ ...

  8. javascript/html 禁止图片缓存

    更新图片, 如果图片的url没有改变, 刷新页面之后图片会使用缓存的图片 Solutions: * js改变图片链接 (添加get参数) // 假设当前这个图片的dom对象为img img.src + ...

  9. 一文让你彻底理解SQL的子查询

    什么是子查询 当一个查询是另一个查询的条件时,称之为子查询. 为什么要使用子查询 在SELECT.INSERT.UPDATE或DELETE命令中只要是表达式的地方都可以包含子查询,子查询甚至可以包含在 ...

  10. flask_sqlalchemy 查询结果转dict 终极解决方案

    之前为了学习Python,试着拿Flask作框架搞小网站,感觉还不错,基本就抛弃了PHP.前段时间做了一个微信小程序,想着yii框架拿来写几十个小接口是不是浪费了,就继续用flask写api了,哪想到 ...