前言
当前项目基于vue2.0+elementui来实现的,所以简单封装一个表格支持render函数来自定义渲染;
内容
custom-column
封装自定义列的组件
var customColumn = {
functional: true,
render: (h, data) => {
const params = {
row: data.props.row,
column: data.props.prop,
render: data.props.render,
};
return params.render
? params.render(h, params.row)
: h("span", params.row[params.column]);
},
};
render
引用时的写法
{
label: "主体资质状态",
prop: "status",
align: "center",
render: (h, row) => {
return h(
"el-tag",
{
props: {
type: TIKTOK_QUA_COLOR[row.status],
},
},
TIKTOK_QUA_STATUS[row.status]
);
},
},
ExpandTable
完整的表单组件,同理基于封装的render,这里的组件可以进一步的进行优化;
<template>
<div class="app-container">
<!-- 查询表单 -->
<el-form
:inline="true"
:model="formData"
ref="ruleForm"
v-if="formItems.length"
>
<el-form-item
v-for="item in formItems"
:label="item.label"
:key="item.name"
>
<component
:is="item.type"
:type="item.range"
:value-format="item.valueFormat"
:start-placeholder="item.startPlaceholder"
:end-placeholder="item.endPlaceholder"
v-model="formData[item.name]"
:placeholder="item.placeholder"
@keyup.enter.native="submitForm"
>
<component
v-for="(els, i) in item.els"
:key="i"
:is="els.type"
:slot="els.slot"
v-model="formData[els.name]"
class="input-width"
>
<el-option
v-for="op in els.options"
:key="op.value"
:label="op.label"
:value="op.value"
>
</el-option>
</component>
<el-option
v-for="op in item.options"
:key="op.value"
:label="op.label"
:value="op.value"
>
</el-option>
</component>
</el-form-item>
<el-form-item>
<el-button type="primary" @click="submitForm">查询</el-button>
<el-button @click="resetForm">重置</el-button>
<el-button v-if="tableConfig.export" @click="handleExport">
导出
</el-button>
<a id="downlink" />
</el-form-item>
</el-form>
<!-- 动态表格 -->
<el-button
v-if="tableConfig.add.status"
type="primary"
class="margin-b15"
@click="handleOperateEvent(tableConfig.add.value)"
>
{{ tableConfig.add.label }}
</el-button>
<el-table
:data="data"
border
fit
highlight-current-row
style="width: 100%"
:max-height="tableHeight"
>
<el-table-column
v-for="column in columns"
:type="column.type"
:key="column.prop"
:prop="column.prop"
:label="column.label"
:fixed="column.fixed"
:width="column.width"
:align="column.align"
>
<template scope="scope">
<!-- 自定义render -->
<custom-column
:render="column.render"
:row="scope.row"
:prop="column.prop"
/>
</template>
</el-table-column>
<el-table-column
v-if="tableConfig.op.status"
label="操作"
align="center"
fixed="right"
>
<template slot-scope="scope">
<el-link
v-for="els in tableConfig.op.items"
:key="els.value"
:type="els.type"
class="margin-r15"
@click="handleOperateEvent(els.value, scope.row)"
>
{{ els.label }}
</el-link>
</template>
</el-table-column>
</el-table>
<!-- 分页 -->
<v-page
style="margin-top: 15px"
:page="page"
@onChangePage="handlePageChange"
/>
</div>
</template>
<script>
var customColumn = {
functional: true,
props: {
row: Object,
render: Function,
prop: String,
},
render: (h, data) => {
const params = {
row: data.props.row,
column: data.props.prop,
render: data.props.render,
};
return params.render
? params.render(h, params.row)
: h("span", params.row[params.column]);
},
};
export default {
props: {
formItems: {
type: Array,
default: () => [],
},
data: Array,
columns: Array,
page: Object,
tableConfig: Object,
},
components: { customColumn },
data() {
return {
formData: {},
tableHeight: 600,
};
},
created() {
if (window) {
this.tableHeight = window.innerHeight - 320;
if (this.tableHeight < 300) this.tableHeight = 300;
}
},
methods: {
handleExport() {
this.$emit("export");
},
submitForm() {
this.$emit("search", this.formData);
},
resetForm() {
this.formData = {};
this.$emit("search", this.formData);
},
handlePageChange(data) {
this.$emit("page", data);
},
handleOperateEvent(type, data) {
this.$emit("operate", type, data);
},
},
};
</script>
<style lang="scss" scoped>
.margin-r15 {
margin-right: 15px;
}
.margin-b15 {
margin-bottom: 15px;
}
.input-width {
width: 88px !important;
}
</style>
使用
引用组件使用,因为组件直接在main.js中注册了,所以直接使用了
<template>
<div class="app-container">
<!-- 表格 -->
<v-ExpandTable
:data="tableData"
:columns="columns"
:form-items="formItems"
:page="page"
:table-config="tableConfig"
@search="handleSearch"
@page="handlePageChange"
@export="handleExport"
@operate="handleOperateEvent"
/>
</div>
</template>
<script>
import {
TIKTOK_QUA_OPTIONS,
TIKTOK_QUA_COLOR,
TIKTOK_QUA_STATUS,
} from "@/utils/data";
import { getQualificationList } from "@/api/dy-compete/qualification";
export default {
data() {
return {
searchForm: {},
formItems: [
{
type: "el-input",
label: "用户名称",
name: "username",
placeholder: "请输入用户名称",
},
{
type: "el-input",
label: "代理商名称",
name: "agent_name",
placeholder: "请输入代理商名称",
},
{
type: "el-input",
label: "一级代理商名称",
name: "first_agent_name",
placeholder: "请输入一级代理商名称",
},
{
type: "el-select",
label: "主体资质状态",
name: "status",
placeholder: "请选择主体资质状态",
options: TIKTOK_QUA_OPTIONS,
},
{
type: "el-select",
label: "行业资质状态",
name: "industry_qua_status",
placeholder: "请选择行业资质状态",
options: TIKTOK_QUA_OPTIONS,
},
],
tableConfig: {
type: "subject",
op: {
status: true,
items: [
{
label: "编辑",
value: "edit",
type: "primary",
},
{
label: "详情",
value: "detail",
type: "success",
},
],
},
add: {
status: true,
label: "新增主体资质",
value: "add",
},
export: true,
},
columns: [
{
label: "用户名称",
prop: "username",
align: "center",
},
{
label: "代理商",
prop: "agent_name",
align: "center",
},
{
label: "一级代理商",
prop: "first_agent_name",
align: "center",
},
{
label: "主体资质状态",
prop: "status",
align: "center",
render: (h, row) => {
return h(
"el-tag",
{
props: {
type: TIKTOK_QUA_COLOR[row.status],
},
},
TIKTOK_QUA_STATUS[row.status]
);
},
},
{
label: "行业资质状态",
prop: "industry_qua_status",
align: "center",
render: (h, row) => {
return h(
"el-tag",
{
props: {
type: TIKTOK_QUA_COLOR[row.status],
},
},
TIKTOK_QUA_STATUS[row.status]
);
},
},
{
label: "拒绝理由",
prop: "reject_reason",
align: "center",
},
],
tableData: [],
page: {},
};
},
created() {
this.getQualificationListInfo();
},
methods: {
handleExport() {
const head = {
username: "用户名",
agent_name: "代理商名称",
first_agent_name: "一级代理商",
status: "主体资质状态",
industry_qua_status: "行业资质状态",
reject_reason: "拒绝理由",
subject: "主体资质",
industries: "行业资质",
};
this.$downloadFile(
this.outFile,
"抖音竞价_主体资质信息",
head,
"/douyin/qualification/subject",
this.searchForm,
{},
"SUBJECT_QUALIFICATION"
);
},
handleSearch(data) {
this.searchForm = data;
this.getQualificationListInfo(data);
},
getQualificationListInfo(params) {
getQualificationList(params).then((r) => {
this.tableData = r.data.items;
this.page = r.data.page;
});
},
handlePageChange(data) {
this.getQualificationListInfo({ ...data, ...this.searchForm });
},
handleOperateEvent(type, data) {
console.log(type, data);
},
},
};
</script>
<style lang="scss" scoped></style>