Commit ab434ceb06ca8c2930969d23bfd0220ed1983899
1 parent
5bbd40ed
Exists in
master
and in
1 other branch
新增新式表格
Showing
4 changed files
with
150 additions
and
25 deletions
Show diff stats
examples/views/page/form-new/form-render.vue
| ... | ... | @@ -21,7 +21,7 @@ |
| 21 | 21 | </component> |
| 22 | 22 | <!-- 正常无分组表单项 --> |
| 23 | 23 | <component :is="colComponent" v-else :span="type === 'div' ? undefined : item.span || span" :key="index" |
| 24 | - :style="{ width: type === 'div' && item.style && item.style.width.indexOf('%') > -1 ? item.style.width : undefined, paddingRight: '10px' }" | |
| 24 | + :style="{ width: type === 'div' && item.style && item.style.width.includes('%') ? item.style.width : undefined, paddingRight: '10px' }" | |
| 25 | 25 | > |
| 26 | 26 | <el-form-item :label="item.label" :label-width="item.labelWidth" :prop="item.fullKey" :rules="item.rules" :class="itemClass || 'eagle-form__item'"> |
| 27 | 27 | <!-- 自定义组件 --> | ... | ... |
examples/views/page/form-new/index.vue
| ... | ... | @@ -23,12 +23,10 @@ |
| 23 | 23 | |
| 24 | 24 | <template> |
| 25 | 25 | <el-form ref="form" size="mini" :class="formClass" :model="formModel" :label-width="labelWidth" :label-position="labelPosition || labelWidth ? 'right' : 'top'"> |
| 26 | - {{ formModel }} | |
| 27 | 26 | <form-render :title-class="titleClass" :content-class="contentClass" :item-class="itemClass" :list="formList" :value="model" |
| 28 | 27 | :model="model" :span="span" :type="type" |
| 29 | 28 | @item-change="onItemChange" @form-item-change="onFormItemChange" @item-update="onItemUpdate" |
| 30 | 29 | ></form-render> |
| 31 | - {{ list }} | |
| 32 | 30 | </el-form> |
| 33 | 31 | </template> |
| 34 | 32 | |
| ... | ... | @@ -80,7 +78,7 @@ export default { |
| 80 | 78 | if (item.group.key) { |
| 81 | 79 | item.fullKey = `${parentKey ? `${parentKey}-${item.group.key}` : item.group.key}`; |
| 82 | 80 | } else { |
| 83 | - item.fullKey = item.key; | |
| 81 | + item.fullKey = parentKey || item.key; | |
| 84 | 82 | } |
| 85 | 83 | generateFullKey(item.list, item.fullKey); |
| 86 | 84 | } else { | ... | ... |
examples/views/page/other.vue
| ... | ... | @@ -12,10 +12,25 @@ |
| 12 | 12 | |
| 13 | 13 | <template> |
| 14 | 14 | <div> |
| 15 | - <p>这是一个非markdown页面</p> | |
| 15 | + <pre>{{ model }}</pre> | |
| 16 | + <eg-table :value="[this.model]" :list="option.list" :tableProps="{ border: true }"> | |
| 17 | + <el-table-column type="selection"></el-table-column> | |
| 18 | + <template #value-location-locationMin="{ value }"> | |
| 19 | + <el-tag size="mini">{{ value }}</el-tag> | |
| 20 | + </template> | |
| 21 | + <template #value-location-district-province="{ value }"> | |
| 22 | + <el-tag type="success" size="mini">{{ value }}</el-tag> | |
| 23 | + </template> | |
| 24 | + <template #location-district-city> | |
| 25 | + <el-table-column label="城市测试" prop="location-district-city"> | |
| 26 | + <el-tag type="danger" size="mini" slot-scope="{ row: { location: { district: { city } = {} } = {} } }">{{ city }}</el-tag> | |
| 27 | + </el-table-column> | |
| 28 | + </template> | |
| 29 | + </eg-table> | |
| 30 | + <!-- <p>这是一个非markdown页面</p> | |
| 16 | 31 | <pre>{{ model }}</pre> |
| 17 | 32 | <el-button size="mini" @click="handleGetValue">校验</el-button> |
| 18 | - <!-- <eg-form ref="form" v-model="model" :list="option.list" @validate="onValidate" label-width="80px" :span="6" type="div"></eg-form> --> | |
| 33 | + <eg-form ref="form" v-model="model" :list="option.list" @validate="onValidate" label-width="80px" :span="6" type="div"></eg-form> --> | |
| 19 | 34 | <eg-form |
| 20 | 35 | ref="form" v-model="model" :list="option.list" @validate="onValidate" :span="4" |
| 21 | 36 | form-class="custom-form" title-class="custom-title" content-class="custom-content" item-class="custom-item" |
| ... | ... | @@ -25,10 +40,11 @@ |
| 25 | 40 | |
| 26 | 41 | <script> |
| 27 | 42 | import EgForm from './form-new'; |
| 43 | +import EgTable from './table-new'; | |
| 28 | 44 | |
| 29 | 45 | export default { |
| 30 | 46 | name: 'other', |
| 31 | - components: { EgForm }, | |
| 47 | + components: { EgForm, EgTable }, | |
| 32 | 48 | data() { |
| 33 | 49 | return { |
| 34 | 50 | model: { |
| ... | ... | @@ -101,24 +117,6 @@ export default { |
| 101 | 117 | }, |
| 102 | 118 | { type: 'el-input', label: '身高', key: 'height', props: { type: 'textarea', min: 3 }, style: { width: '100%' }, span: 24 }, |
| 103 | 119 | { type: 'el-input', label: '体重', key: 'weight' }, |
| 104 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 105 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 106 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 107 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 108 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 109 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 110 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 111 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 112 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 113 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 114 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 115 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 116 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 117 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 118 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 119 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 120 | - { type: 'el-input', label: '身高', key: 'height' }, | |
| 121 | - { type: 'el-input', label: '体重', key: 'weight' }, | |
| 122 | 120 | ] |
| 123 | 121 | } |
| 124 | 122 | } | ... | ... |
| ... | ... | @@ -0,0 +1,129 @@ |
| 1 | +<style> | |
| 2 | +.eagle-table { | |
| 3 | + width: 100%; | |
| 4 | +} | |
| 5 | +</style> | |
| 6 | + | |
| 7 | +<template> | |
| 8 | + <div> | |
| 9 | + <pre>{{ tableList }}</pre> | |
| 10 | + <el-table class="eagle-table" ref="table" :data="tableData" v-bind="{ size: 'small', ...tableProps }" v-on="tableEvents"> | |
| 11 | + <slot name="default"></slot> | |
| 12 | + <template v-if="tableList && tableList.length > 0"> | |
| 13 | + <template v-for="(item, index) in tableList"> | |
| 14 | + <template v-if="bindItemVisible(item.visible)"> | |
| 15 | + <slot v-if="$scopedSlots[item.keyPath.join('-')] || $slots[item.keyPath.join('-')]" :name="item.keyPath.join('-')" v-bind="item"></slot> | |
| 16 | + <el-table-column v-else-if="$scopedSlots[`value-${item.keyPath.join('-')}`] || $slots[`value-${item.keyPath.join('-')}`]" | |
| 17 | + v-bind="item" :prop="item.agentKey || item.fullKey || item.key" :key="index" | |
| 18 | + :min-width="item.minWidth || item['min-width']" | |
| 19 | + > | |
| 20 | + <slot slot-scope="{ row, column, $index }" :name="`value-${item.keyPath.join('-')}`" v-bind="item" | |
| 21 | + :row="row" :value="$_get(row, item.fullKey)" :column="column" :index="$index" | |
| 22 | + ></slot> | |
| 23 | + </el-table-column> | |
| 24 | + <el-table-column v-else v-bind="item" :prop="item.agentKey || item.fullKey || item.key" | |
| 25 | + :key="index" :min-width="item.minWidth || item['min-width']" | |
| 26 | + ></el-table-column> | |
| 27 | + </template> | |
| 28 | + </template> | |
| 29 | + </template> | |
| 30 | + <slot name="column-append"></slot> | |
| 31 | + <slot name="column-end"></slot> | |
| 32 | + </el-table> | |
| 33 | + </div> | |
| 34 | +</template> | |
| 35 | + | |
| 36 | +<script> | |
| 37 | +import { cloneDeep, get } from '../form-new/util'; | |
| 38 | + | |
| 39 | +export default { | |
| 40 | + name: 'TableNew', | |
| 41 | + props: { | |
| 42 | + // 用于实例化本组件绑定v-model的值 | |
| 43 | + value: Array, | |
| 44 | + // 配置列表 | |
| 45 | + list: { | |
| 46 | + type: Array, | |
| 47 | + required: true | |
| 48 | + }, | |
| 49 | + // 表格参数 | |
| 50 | + tableProps: { | |
| 51 | + type: Object, | |
| 52 | + default() { return {} } | |
| 53 | + }, | |
| 54 | + // 表格事件 | |
| 55 | + tableEvents: Object, | |
| 56 | + }, | |
| 57 | + data() { | |
| 58 | + return { | |
| 59 | + tableList: [], | |
| 60 | + tableData: [], | |
| 61 | + }; | |
| 62 | + }, | |
| 63 | + computed: { | |
| 64 | + // 表格实体 | |
| 65 | + instance: { | |
| 66 | + get() { | |
| 67 | + return this.$refs.table; | |
| 68 | + } | |
| 69 | + } | |
| 70 | + }, | |
| 71 | + watch: { | |
| 72 | + value: { | |
| 73 | + handler(val = []) { | |
| 74 | + this.tableData = val; | |
| 75 | + }, | |
| 76 | + immediate: true | |
| 77 | + }, | |
| 78 | + list: { | |
| 79 | + handler(val) { | |
| 80 | + // 深度克隆传入的列表,避免原始值被修改 | |
| 81 | + const newList = cloneDeep(this.list); | |
| 82 | + // 生成列表值的全路径key,即列表项为对象时,对象内的key与上一级的key合并作为全路径key | |
| 83 | + const generateFullKey = (list, parentKey) => { | |
| 84 | + list.forEach(item => { | |
| 85 | + if (item.group && item.list) { | |
| 86 | + if (item.group.key) { | |
| 87 | + item.fullKey = `${parentKey ? `${parentKey}.${item.group.key}` : item.group.key}`; | |
| 88 | + } else { | |
| 89 | + item.fullKey = parentKey || item.key; | |
| 90 | + } | |
| 91 | + generateFullKey(item.list, item.fullKey); | |
| 92 | + } else { | |
| 93 | + item.fullKey = `${parentKey ? `${parentKey}.${item.key}` : item.key}`; | |
| 94 | + } | |
| 95 | + }); | |
| 96 | + }; | |
| 97 | + // 生成fullKey | |
| 98 | + generateFullKey(newList); | |
| 99 | + // 创建输出列表 | |
| 100 | + const result = []; | |
| 101 | + // 生成列表值的全路径key,即列表项为对象时,对象内的key与上一级的key合并作为全路径key | |
| 102 | + const generateFlatList = (list) => { | |
| 103 | + list.forEach(item => { | |
| 104 | + if (item.group && item.list) { | |
| 105 | + generateFlatList(item.list); | |
| 106 | + } else if (!item.group && !item.list) { | |
| 107 | + result.push({ ...item, keyPath: item.fullKey.split('.') }); | |
| 108 | + } | |
| 109 | + }); | |
| 110 | + }; | |
| 111 | + generateFlatList(newList); | |
| 112 | + this.tableList = result; | |
| 113 | + }, | |
| 114 | + immediate: true | |
| 115 | + } | |
| 116 | + }, | |
| 117 | + methods: { | |
| 118 | + $_get: get, | |
| 119 | + // 绑定表格列显示隐藏状态 | |
| 120 | + bindItemVisible(visible = true) { | |
| 121 | + let result = visible; | |
| 122 | + if (typeof visible === 'function') { | |
| 123 | + result = visible(this.tableData); | |
| 124 | + } | |
| 125 | + return result; | |
| 126 | + }, | |
| 127 | + } | |
| 128 | +}; | |
| 129 | +</script> | |
| 0 | 130 | \ No newline at end of file | ... | ... |