sh-view 2.1.0 → 2.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +9 -13
- package/packages/components/global-components/sh-alert/index.vue +175 -173
- package/packages/components/global-components/sh-badge/index.vue +57 -43
- package/packages/components/global-components/sh-card/index.vue +24 -16
- package/packages/components/global-components/sh-code-editor/index.vue +250 -260
- package/packages/components/global-components/sh-col/index.vue +44 -36
- package/packages/components/global-components/sh-corner/index.vue +230 -228
- package/packages/components/global-components/sh-count-to/index.vue +60 -51
- package/packages/components/global-components/sh-drawer/index.vue +209 -182
- package/packages/components/global-components/sh-drawer/scrollbar.js +44 -42
- package/packages/components/global-components/sh-empty/index.vue +0 -1
- package/packages/components/global-components/sh-form/form.vue +110 -0
- package/packages/components/global-components/sh-form/js/props.js +76 -63
- package/packages/components/global-components/sh-form/js/useForm.js +236 -0
- package/packages/components/global-components/sh-form/query.vue +70 -0
- package/packages/components/global-components/sh-header/index.vue +35 -50
- package/packages/components/global-components/sh-icon/css/index.scss +44 -0
- package/packages/components/global-components/sh-icon/index.vue +24 -11
- package/packages/components/global-components/sh-image/index.vue +47 -38
- package/packages/components/global-components/sh-list/index.vue +42 -37
- package/packages/components/global-components/sh-loading/index.vue +12 -8
- package/packages/components/global-components/sh-modal/index.vue +49 -40
- package/packages/components/global-components/sh-noticebar/index.vue +68 -54
- package/packages/components/global-components/sh-poptip/index.vue +247 -130
- package/packages/components/global-components/sh-progress/index.vue +71 -69
- package/packages/components/global-components/sh-pull-refresh/index.vue +156 -157
- package/packages/components/global-components/sh-result/index.vue +37 -28
- package/packages/components/global-components/sh-row/index.vue +21 -18
- package/packages/components/global-components/sh-split/index.vue +115 -109
- package/packages/components/global-components/sh-table/components/importModal.vue +95 -86
- package/packages/components/global-components/sh-table/components/sh-column.vue +62 -0
- package/packages/components/global-components/sh-table/{index.vue → grid.vue} +34 -145
- package/packages/components/global-components/sh-table/js/tableMethods.js +175 -0
- package/packages/components/global-components/sh-table/js/useTable.js +592 -0
- package/packages/components/global-components/sh-table/table.vue +266 -0
- package/packages/components/global-components/sh-tabs/index.vue +118 -93
- package/packages/components/global-components/sh-tag/index.vue +52 -51
- package/packages/components/global-components/sh-toolbar/index.vue +53 -47
- package/packages/components/global-components/sh-tree/components/table-tree.vue +152 -139
- package/packages/components/global-components/sh-tree/index.vue +218 -195
- package/packages/components/global-components/sh-tree/mixin/treeProps.js +118 -120
- package/packages/components/global-components/sh-upload/index.vue +308 -51
- package/packages/components/global-components/sh-water-fall/index.vue +4 -11
- package/packages/components/index.js +5 -3
- package/packages/components/other-components/sh-cron-modal/components/cron-content.vue +140 -129
- package/packages/components/other-components/sh-cron-modal/css/index.scss +0 -5
- package/packages/components/other-components/sh-cron-modal/index.vue +81 -67
- package/packages/components/other-components/sh-cron-modal/mixin/cron-emits.js +1 -0
- package/packages/components/other-components/sh-cron-modal/mixin/cron-hooks.js +179 -0
- package/packages/components/other-components/sh-cron-modal/mixin/cron-props.js +9 -0
- package/packages/components/other-components/sh-cron-modal/tabs/cron-day-box.vue +101 -92
- package/packages/components/other-components/sh-cron-modal/tabs/cron-hour-box.vue +68 -56
- package/packages/components/other-components/sh-cron-modal/tabs/cron-minute-box.vue +68 -56
- package/packages/components/other-components/sh-cron-modal/tabs/cron-month-box.vue +68 -56
- package/packages/components/other-components/sh-cron-modal/tabs/cron-second-box.vue +68 -56
- package/packages/components/other-components/sh-cron-modal/tabs/cron-week-box.vue +126 -115
- package/packages/components/other-components/sh-cron-modal/tabs/cron-year-box.vue +59 -46
- package/packages/components/other-components/sh-menu/index.vue +73 -60
- package/packages/components/other-components/sh-menu/menu-group-content.vue +71 -59
- package/packages/components/other-components/sh-menu/menu-item-content.vue +40 -30
- package/packages/components/other-components/sh-menu-card/index.vue +70 -64
- package/packages/components/other-components/sh-menu-card/menu-box.vue +50 -44
- package/packages/components/other-components/sh-preview/components/sh-excel.vue +182 -0
- package/packages/components/other-components/sh-preview/components/sh-word.vue +73 -0
- package/packages/components/other-components/sh-preview/index.vue +86 -85
- package/packages/components/other-components/sh-preview/js/data-hook.js +37 -0
- package/packages/components/other-components/sh-preview/js/data-props.js +11 -0
- package/packages/components/other-components/sh-system-tip/index.vue +28 -24
- package/packages/css/index.js +4 -4
- package/packages/directive/module/prevent-click.js +1 -1
- package/packages/directive/module/resize.js +11 -154
- package/packages/index.js +39 -39
- package/packages/mixin/index.js +86 -87
- package/packages/vxeTable/render/cell/vxe-render-checkbox.vue +14 -5
- package/packages/vxeTable/render/cell/vxe-render-checkgroup.vue +43 -36
- package/packages/vxeTable/render/cell/vxe-render-code.vue +14 -5
- package/packages/vxeTable/render/cell/vxe-render-goption.vue +34 -24
- package/packages/vxeTable/render/cell/vxe-render-href.vue +21 -11
- package/packages/vxeTable/render/cell/vxe-render-img.vue +16 -10
- package/packages/vxeTable/render/cell/vxe-render-input.vue +83 -79
- package/packages/vxeTable/render/cell/vxe-render-money.vue +14 -6
- package/packages/vxeTable/render/cell/vxe-render-progress.vue +28 -19
- package/packages/vxeTable/render/cell/vxe-render-radio.vue +14 -5
- package/packages/vxeTable/render/cell/vxe-render-radiogroup.vue +43 -36
- package/packages/vxeTable/render/cell/vxe-render-select.vue +44 -36
- package/packages/vxeTable/render/cell/vxe-render-switch.vue +14 -5
- package/packages/vxeTable/render/cell/vxe-render-table.vue +51 -78
- package/packages/vxeTable/render/cell/vxe-render-textarea.vue +14 -5
- package/packages/vxeTable/render/cell/vxe-render-time.vue +23 -13
- package/packages/vxeTable/render/cell/vxe-render-tree.vue +23 -27
- package/packages/vxeTable/render/cell/vxe-render-upload.vue +11 -7
- package/packages/vxeTable/render/filters/vxe-filter-input.vue +25 -43
- package/packages/vxeTable/render/footer/vxe-footer-input.vue +23 -13
- package/packages/vxeTable/render/footer/vxe-footer-money.vue +30 -20
- package/packages/vxeTable/render/globalRenders.jsx +1 -1
- package/packages/vxeTable/render/header/vxe-header-money.vue +31 -21
- package/packages/vxeTable/render/mixin/cell-hooks.js +162 -0
- package/packages/vxeTable/render/mixin/cell-props.js +23 -0
- package/packages/vxeTable/render/mixin/filter-hooks.js +28 -0
- package/packages/components/global-components/sh-form/components/form-item.vue +0 -25
- package/packages/components/global-components/sh-form/css/index.scss +0 -55
- package/packages/components/global-components/sh-form/index.vue +0 -114
- package/packages/components/global-components/sh-form/js/methods.js +0 -146
- package/packages/components/global-components/sh-form/mixin/defaultData.js +0 -32
- package/packages/components/global-components/sh-icon/css/default/index.scss +0 -27
- package/packages/components/global-components/sh-icon/css/font/index.scss +0 -16
- package/packages/components/global-components/sh-icon/icon-default.vue +0 -32
- package/packages/components/global-components/sh-icon/icon-font.vue +0 -32
- package/packages/components/global-components/sh-poptip/popper.js +0 -115
- package/packages/components/global-components/sh-query/index.vue +0 -317
- package/packages/components/global-components/sh-table/js/methods.js +0 -549
- package/packages/components/global-components/sh-table/mixin/defaultData.js +0 -94
- package/packages/components/global-components/sh-upload/js/mixin.js +0 -257
- package/packages/components/other-components/sh-cron-modal/mixin/cron-box.js +0 -169
- package/packages/vxeTable/render/mixin/cell-mixin.js +0 -195
- /package/packages/components/global-components/sh-icon/css/default/{fonts/ionicons.svg → ionicons.svg} +0 -0
- /package/packages/components/global-components/sh-icon/css/default/{fonts/ionicons.ttf → ionicons.ttf} +0 -0
- /package/packages/components/global-components/sh-icon/css/default/{fonts/ionicons.woff → ionicons.woff} +0 -0
- /package/packages/components/global-components/sh-icon/css/default/{fonts/ionicons.woff2 → ionicons.woff2} +0 -0
- /package/packages/components/global-components/sh-icon/css/font/{fonts/iconfont.js → iconfont.js} +0 -0
- /package/packages/components/global-components/sh-icon/css/font/{fonts/iconfont.json → iconfont.json} +0 -0
- /package/packages/components/global-components/sh-icon/css/font/{fonts/iconfont.ttf → iconfont.ttf} +0 -0
- /package/packages/components/global-components/sh-icon/css/font/{fonts/iconfont.woff → iconfont.woff} +0 -0
- /package/packages/components/global-components/sh-icon/css/font/{fonts/iconfont.woff2 → iconfont.woff2} +0 -0
- /package/packages/{assets/css → css}/animated.scss +0 -0
- /package/packages/{assets/css → css}/loader.scss +0 -0
- /package/packages/{assets/css → css}/main.scss +0 -0
- /package/packages/{assets/css → css}/theme.scss +0 -0
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
<template>
|
|
2
|
-
<div ref="
|
|
2
|
+
<div ref="splitRef" v-resize="computeOffset" class="sh-split" :class="{ 'no-select': isMoving }">
|
|
3
3
|
<sh-loading v-if="loading" loading :content="loadingText" class="layout-loader"></sh-loading>
|
|
4
|
-
<div v-if="isHorizontal"
|
|
4
|
+
<div v-if="isHorizontal" class="sh-split-horizontal">
|
|
5
5
|
<div :style="{ right: `${anotherOffset}%` }" class="left-pane" :class="paneClasses">
|
|
6
6
|
<slot name="left" />
|
|
7
7
|
</div>
|
|
8
|
-
<div
|
|
8
|
+
<div class="sh-split-trigger-con" :style="{ left: `${offset}%` }" @mousedown="handleMousedown">
|
|
9
9
|
<slot name="trigger">
|
|
10
10
|
<trigger mode="vertical" />
|
|
11
11
|
</slot>
|
|
@@ -14,11 +14,11 @@
|
|
|
14
14
|
<slot name="right" />
|
|
15
15
|
</div>
|
|
16
16
|
</div>
|
|
17
|
-
<div v-else
|
|
17
|
+
<div v-else class="sh-split-vertical">
|
|
18
18
|
<div :style="{ bottom: `${anotherOffset}%` }" class="top-pane" :class="paneClasses">
|
|
19
19
|
<slot name="top" />
|
|
20
20
|
</div>
|
|
21
|
-
<div
|
|
21
|
+
<div class="sh-split-trigger-con" :style="{ top: `${offset}%` }" @mousedown="handleMousedown">
|
|
22
22
|
<slot name="trigger">
|
|
23
23
|
<trigger mode="horizontal" />
|
|
24
24
|
</slot>
|
|
@@ -31,8 +31,9 @@
|
|
|
31
31
|
</template>
|
|
32
32
|
|
|
33
33
|
<script>
|
|
34
|
+
import { defineComponent, computed, getCurrentInstance, ref, watch, onMounted, nextTick } from 'vue'
|
|
34
35
|
import trigger from './components/trigger.vue'
|
|
35
|
-
export default {
|
|
36
|
+
export default defineComponent({
|
|
36
37
|
name: 'ShSplit',
|
|
37
38
|
components: {
|
|
38
39
|
trigger
|
|
@@ -75,119 +76,124 @@ export default {
|
|
|
75
76
|
}
|
|
76
77
|
},
|
|
77
78
|
emits: ['update:modelValue', 'move-start', 'moveing', 'move-end'],
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
paneClasses() {
|
|
93
|
-
return
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
79
|
+
setup(props, context) {
|
|
80
|
+
const vm = getCurrentInstance()
|
|
81
|
+
const { $vUtils } = vm.proxy
|
|
82
|
+
const { emit, slots } = context
|
|
83
|
+
|
|
84
|
+
const splitRef = ref()
|
|
85
|
+
const offset = ref(0)
|
|
86
|
+
const initOffset = ref(0)
|
|
87
|
+
const oldOffset = ref(0)
|
|
88
|
+
const isMoving = ref(false)
|
|
89
|
+
const computedMin = ref(0)
|
|
90
|
+
const computedMax = ref(0)
|
|
91
|
+
const currentValue = ref(props.modelValue)
|
|
92
|
+
|
|
93
|
+
const paneClasses = computed(() => {
|
|
94
|
+
return {
|
|
95
|
+
'sh-split-pane': true,
|
|
96
|
+
'sh-split-pane-moving': props.isMoving
|
|
97
|
+
}
|
|
98
|
+
})
|
|
99
|
+
const isHorizontal = computed(() => {
|
|
100
|
+
return props.mode === 'horizontal'
|
|
101
|
+
})
|
|
102
|
+
const anotherOffset = computed(() => {
|
|
103
|
+
return 100 - offset.value
|
|
104
|
+
})
|
|
105
|
+
const valueIsPx = computed(() => {
|
|
106
|
+
return typeof props.modelValue === 'string'
|
|
107
|
+
})
|
|
108
|
+
const offsetSize = computed(() => {
|
|
109
|
+
return isHorizontal.value ? 'offsetWidth' : 'offsetHeight'
|
|
110
|
+
})
|
|
111
|
+
|
|
112
|
+
const px2percent = (numerator, denominator) => {
|
|
113
|
+
return parseFloat(numerator) / parseFloat(denominator)
|
|
111
114
|
}
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
115
|
+
const getComputedThresholdValue = type => {
|
|
116
|
+
let size = splitRef.value[offsetSize.value]
|
|
117
|
+
if (valueIsPx.value) return typeof props[type] === 'string' ? props[type] : size * props[type]
|
|
118
|
+
else return typeof props[type] === 'string' ? px2percent(props[type], size) : props[type]
|
|
116
119
|
}
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
mounted() {
|
|
120
|
-
this.computeOffset()
|
|
121
|
-
},
|
|
122
|
-
beforeUnmount() {},
|
|
123
|
-
methods: {
|
|
124
|
-
px2percent(numerator, denominator) {
|
|
125
|
-
return parseFloat(numerator) / parseFloat(denominator)
|
|
126
|
-
},
|
|
127
|
-
getComputedThresholdValue(type) {
|
|
128
|
-
let size = this.$refs.splitWrap[this.offsetSize]
|
|
129
|
-
if (this.valueIsPx) return typeof this[type] === 'string' ? this[type] : size * this[type]
|
|
130
|
-
else return typeof this[type] === 'string' ? this.px2percent(this[type], size) : this[type]
|
|
131
|
-
},
|
|
132
|
-
getMin(value1, value2) {
|
|
133
|
-
if (this.valueIsPx) return `${Math.min(parseFloat(value1), parseFloat(value2))}px`
|
|
120
|
+
const getMin = (value1, value2) => {
|
|
121
|
+
if (valueIsPx.value) return `${Math.min(parseFloat(value1), parseFloat(value2))}px`
|
|
134
122
|
else return Math.min(value1, value2)
|
|
135
|
-
}
|
|
136
|
-
getMax(value1, value2) {
|
|
137
|
-
if (
|
|
123
|
+
}
|
|
124
|
+
const getMax = (value1, value2) => {
|
|
125
|
+
if (valueIsPx.value) return `${Math.max(parseFloat(value1), parseFloat(value2))}px`
|
|
138
126
|
else return Math.max(value1, value2)
|
|
139
|
-
}
|
|
140
|
-
getAnotherOffset
|
|
127
|
+
}
|
|
128
|
+
const getAnotherOffset = value => {
|
|
141
129
|
let res = 0
|
|
142
|
-
if (
|
|
130
|
+
if (valueIsPx.value) res = `${splitRef.value[offsetSize.value] - parseFloat(value)}px`
|
|
143
131
|
else res = 1 - value
|
|
144
132
|
return res
|
|
145
|
-
}
|
|
146
|
-
handleMove
|
|
147
|
-
let pageOffset =
|
|
148
|
-
let offset = pageOffset -
|
|
149
|
-
let outerWidth =
|
|
150
|
-
let value =
|
|
151
|
-
let anotherValue =
|
|
152
|
-
if (parseFloat(value) <= parseFloat(
|
|
153
|
-
if (parseFloat(anotherValue) <= parseFloat(
|
|
154
|
-
e.atMin =
|
|
155
|
-
e.atMax =
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
}
|
|
159
|
-
handleUp() {
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
}
|
|
165
|
-
handleMousedown
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
}
|
|
173
|
-
computeOffset() {
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
return
|
|
178
|
-
}
|
|
179
|
-
resetOffset
|
|
180
|
-
if (val !==
|
|
181
|
-
|
|
182
|
-
|
|
133
|
+
}
|
|
134
|
+
const handleMove = e => {
|
|
135
|
+
let pageOffset = isHorizontal.value ? e.pageX : e.pageY
|
|
136
|
+
let offset = pageOffset - initOffset.value
|
|
137
|
+
let outerWidth = splitRef.value[offsetSize.value]
|
|
138
|
+
let value = valueIsPx.value ? `${parseFloat(oldOffset.value) + offset}px` : px2percent(outerWidth * oldOffset.value + offset, outerWidth)
|
|
139
|
+
let anotherValue = getAnotherOffset(value)
|
|
140
|
+
if (parseFloat(value) <= parseFloat(computedMin.value)) value = getMax(value, computedMin.value)
|
|
141
|
+
if (parseFloat(anotherValue) <= parseFloat(computedMax.value)) value = getAnotherOffset(getMax(anotherValue, computedMax.value))
|
|
142
|
+
e.atMin = currentValue.value === computedMin.value
|
|
143
|
+
e.atMax = valueIsPx.value ? getAnotherOffset(currentValue.value) === computedMax.value : getAnotherOffset(currentValue.value).toFixed(5) === computedMax.value.toFixed(5)
|
|
144
|
+
emitValue(value)
|
|
145
|
+
emit('moveing', e)
|
|
146
|
+
}
|
|
147
|
+
const handleUp = () => {
|
|
148
|
+
isMoving.value = false
|
|
149
|
+
$vUtils.offListener(document, 'mousemove', handleMove)
|
|
150
|
+
$vUtils.offListener(document, 'mouseup', handleUp)
|
|
151
|
+
emit('move-end')
|
|
152
|
+
}
|
|
153
|
+
const handleMousedown = e => {
|
|
154
|
+
initOffset.value = isHorizontal.value ? e.pageX : e.pageY
|
|
155
|
+
oldOffset.value = currentValue.value
|
|
156
|
+
isMoving.value = true
|
|
157
|
+
$vUtils.onListener(document, 'mousemove', handleMove)
|
|
158
|
+
$vUtils.onListener(document, 'mouseup', handleUp)
|
|
159
|
+
emit('move-start')
|
|
160
|
+
}
|
|
161
|
+
const computeOffset = () => {
|
|
162
|
+
computedMin.value = getComputedThresholdValue('min')
|
|
163
|
+
computedMax.value = getComputedThresholdValue('max')
|
|
164
|
+
offset.value = ((valueIsPx.value ? px2percent(currentValue.value, splitRef.value[offsetSize.value]) : currentValue.value) * 10000) / 100
|
|
165
|
+
// return nextTick()
|
|
166
|
+
}
|
|
167
|
+
const resetOffset = val => {
|
|
168
|
+
if (val !== currentValue.value) {
|
|
169
|
+
currentValue.value = val
|
|
170
|
+
computeOffset()
|
|
183
171
|
}
|
|
184
|
-
}
|
|
185
|
-
emitValue
|
|
186
|
-
|
|
187
|
-
|
|
172
|
+
}
|
|
173
|
+
const emitValue = value => {
|
|
174
|
+
resetOffset(value)
|
|
175
|
+
emit('update:modelValue', value)
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
watch(
|
|
179
|
+
() => props.modelValue,
|
|
180
|
+
val => {
|
|
181
|
+
resetOffset(val)
|
|
182
|
+
}
|
|
183
|
+
)
|
|
184
|
+
|
|
185
|
+
return {
|
|
186
|
+
splitRef,
|
|
187
|
+
isMoving,
|
|
188
|
+
isHorizontal,
|
|
189
|
+
anotherOffset,
|
|
190
|
+
paneClasses,
|
|
191
|
+
offset,
|
|
192
|
+
computeOffset,
|
|
193
|
+
handleMousedown
|
|
188
194
|
}
|
|
189
195
|
}
|
|
190
|
-
}
|
|
196
|
+
})
|
|
191
197
|
</script>
|
|
192
198
|
|
|
193
199
|
<style lang="scss">
|
|
@@ -49,9 +49,9 @@
|
|
|
49
49
|
</template>
|
|
50
50
|
|
|
51
51
|
<script>
|
|
52
|
-
import
|
|
52
|
+
import { defineComponent, computed, getCurrentInstance, ref, onBeforeMount } from 'vue'
|
|
53
53
|
import ExcelJS from 'exceljs'
|
|
54
|
-
export default {
|
|
54
|
+
export default defineComponent({
|
|
55
55
|
name: 'TableImport',
|
|
56
56
|
props: {
|
|
57
57
|
visible: {
|
|
@@ -103,70 +103,61 @@ export default {
|
|
|
103
103
|
}
|
|
104
104
|
},
|
|
105
105
|
emits: ['confirm', 'update:visible'],
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
},
|
|
119
|
-
tableColumns()
|
|
120
|
-
|
|
121
|
-
}
|
|
122
|
-
},
|
|
123
|
-
watch: {},
|
|
124
|
-
created() {
|
|
125
|
-
this.initCreated()
|
|
126
|
-
},
|
|
127
|
-
mounted() {},
|
|
128
|
-
beforeUnmount() {},
|
|
129
|
-
methods: {
|
|
106
|
+
setup(props, context) {
|
|
107
|
+
const { proxy } = getCurrentInstance()
|
|
108
|
+
const { $vUtils } = proxy
|
|
109
|
+
const { emit, slots } = context
|
|
110
|
+
const shtable = ref()
|
|
111
|
+
|
|
112
|
+
const importTableData = ref([])
|
|
113
|
+
const importErrorData = ref([])
|
|
114
|
+
const modalLoading = ref(false)
|
|
115
|
+
const showProgress = ref(false)
|
|
116
|
+
const progressPercent = ref(0)
|
|
117
|
+
|
|
118
|
+
const tableGlobalConfig = computed(() => Object.assign({ checkbox: false, seq: true, zoom: false, title: true, tableName: '导入预览' }, props.globalConfig))
|
|
119
|
+
const tableColumns = computed(() => props.columns.filter(item => !(['seq', 'checkbox', 'radio'].includes(item.type) || item.renderName === '$vGlobalOption')))
|
|
120
|
+
|
|
130
121
|
// 初始化
|
|
131
|
-
initCreated() {
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
}
|
|
122
|
+
const initCreated = () => {
|
|
123
|
+
showProgress.value = false
|
|
124
|
+
progressPercent.value = 0
|
|
125
|
+
importTableData.value = []
|
|
126
|
+
}
|
|
136
127
|
// 弹窗关闭
|
|
137
|
-
onModalClose() {
|
|
138
|
-
|
|
139
|
-
}
|
|
128
|
+
const onModalClose = () => {
|
|
129
|
+
emit('update:visible', false)
|
|
130
|
+
}
|
|
140
131
|
// 确认导入数据按钮
|
|
141
|
-
async
|
|
142
|
-
let importData = type === 'all' ?
|
|
132
|
+
const handleImportDataBtn = async (type = 'all') => {
|
|
133
|
+
let importData = type === 'all' ? importTableData.value : shtable.value.getSelectionData()
|
|
143
134
|
if (!importData || !Array.isArray(importData) || importData.length < 1) {
|
|
144
|
-
|
|
135
|
+
proxy.msginfo('未导入数据')
|
|
145
136
|
return false
|
|
146
137
|
}
|
|
147
|
-
if (
|
|
148
|
-
let validateErrMap = await
|
|
138
|
+
if (props.needValidate) {
|
|
139
|
+
let validateErrMap = await handleImportDataValidate(importData)
|
|
149
140
|
if (validateErrMap) {
|
|
150
|
-
|
|
141
|
+
proxy.msgerror('导入校验失败,请检查数据')
|
|
151
142
|
return validateErrMap
|
|
152
143
|
}
|
|
153
144
|
}
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
}
|
|
145
|
+
emit('confirm', importData)
|
|
146
|
+
onModalClose()
|
|
147
|
+
}
|
|
157
148
|
// 导入数据验证
|
|
158
|
-
async
|
|
159
|
-
return
|
|
160
|
-
}
|
|
149
|
+
const handleImportDataValidate = async rows => {
|
|
150
|
+
return shtable.value.validate(rows)
|
|
151
|
+
}
|
|
161
152
|
// 下载导入模板按钮
|
|
162
|
-
handleDownloadTemplateBtn() {
|
|
163
|
-
const parentTable =
|
|
164
|
-
if (typeof
|
|
165
|
-
|
|
153
|
+
const handleDownloadTemplateBtn = () => {
|
|
154
|
+
const parentTable = shtable.value.tableRef.value
|
|
155
|
+
if (typeof props.downloadTemplateCallback === 'function') {
|
|
156
|
+
props.downloadTemplateCallback()
|
|
166
157
|
}
|
|
167
158
|
let defaultOption = {
|
|
168
159
|
filename: '模板',
|
|
169
|
-
sheetName:
|
|
160
|
+
sheetName: props.globalConfig.filename || '模板',
|
|
170
161
|
type: 'xlsx',
|
|
171
162
|
original: false,
|
|
172
163
|
download: true,
|
|
@@ -175,59 +166,59 @@ export default {
|
|
|
175
166
|
columns: parentTable.getColumns().filter(item => item.type !== 'seq'),
|
|
176
167
|
data: [],
|
|
177
168
|
afterExportMethod: options => {
|
|
178
|
-
|
|
169
|
+
handleDownloadTemplateFinished(options)
|
|
179
170
|
}
|
|
180
171
|
}
|
|
181
|
-
parentTable.exportData(Object.assign(defaultOption,
|
|
182
|
-
}
|
|
172
|
+
parentTable.exportData(Object.assign(defaultOption, props.importConfig))
|
|
173
|
+
}
|
|
183
174
|
// 下载导入模板成功回调
|
|
184
|
-
handleDownloadTemplateFinished
|
|
185
|
-
if (typeof
|
|
186
|
-
|
|
175
|
+
const handleDownloadTemplateFinished = options => {
|
|
176
|
+
if (typeof props.downloadTemplateFinished === 'function') {
|
|
177
|
+
props.downloadTemplateFinished(options)
|
|
187
178
|
}
|
|
188
|
-
|
|
189
|
-
}
|
|
179
|
+
proxy.msgsuccess('下载模板完成!')
|
|
180
|
+
}
|
|
190
181
|
// 选择导入文件按钮
|
|
191
|
-
async
|
|
182
|
+
const handleImportFileBtn = async () => {
|
|
192
183
|
try {
|
|
193
|
-
const { file } = await
|
|
184
|
+
const { file } = await proxy.$vTable.readFile({
|
|
194
185
|
types: ['xlsx', 'xls']
|
|
195
186
|
})
|
|
196
|
-
if (typeof
|
|
197
|
-
|
|
187
|
+
if (typeof props.importFileCallback === 'function') {
|
|
188
|
+
props.importFileCallback(file)
|
|
198
189
|
}
|
|
199
|
-
let fileRes = await
|
|
200
|
-
let { results, errDatas } =
|
|
201
|
-
|
|
202
|
-
|
|
190
|
+
let fileRes = await readFile(file)
|
|
191
|
+
let { results, errDatas } = dealImportTableData(tableColumns.value, fileRes)
|
|
192
|
+
importTableData.value = results
|
|
193
|
+
importErrorData.value = errDatas
|
|
203
194
|
setTimeout(() => {
|
|
204
|
-
|
|
195
|
+
showProgress.value = false
|
|
205
196
|
}, 2000)
|
|
206
|
-
if (typeof
|
|
207
|
-
|
|
197
|
+
if (typeof props.importFileFinished === 'function') {
|
|
198
|
+
props.importFileFinished(options)
|
|
208
199
|
}
|
|
209
|
-
|
|
200
|
+
proxy.msgsuccess('导入完成!')
|
|
210
201
|
} catch (e) {
|
|
211
|
-
|
|
202
|
+
proxy.msgerror(e.message || e)
|
|
212
203
|
}
|
|
213
|
-
}
|
|
204
|
+
}
|
|
214
205
|
// 读取文件
|
|
215
|
-
async
|
|
206
|
+
const readFile = async file => {
|
|
216
207
|
return new Promise((resolve, reject) => {
|
|
217
208
|
const reader = new FileReader()
|
|
218
209
|
reader.readAsArrayBuffer(file)
|
|
219
210
|
reader.onloadstart = e => {
|
|
220
|
-
|
|
221
|
-
|
|
211
|
+
modalLoading.value = true
|
|
212
|
+
showProgress.value = true
|
|
222
213
|
}
|
|
223
214
|
reader.onprogress = e => {
|
|
224
|
-
|
|
215
|
+
progressPercent.value = Math.round((e.loaded / e.total) * 100)
|
|
225
216
|
}
|
|
226
217
|
reader.onerror = e => {
|
|
227
218
|
reject(new Error('文件读取出错'))
|
|
228
219
|
}
|
|
229
220
|
reader.onload = e => {
|
|
230
|
-
|
|
221
|
+
modalLoading.value = false
|
|
231
222
|
const workbook = new ExcelJS.Workbook()
|
|
232
223
|
const data = e.target.result
|
|
233
224
|
workbook.xlsx.load(data).then(wb => {
|
|
@@ -246,11 +237,10 @@ export default {
|
|
|
246
237
|
})
|
|
247
238
|
}
|
|
248
239
|
})
|
|
249
|
-
}
|
|
240
|
+
}
|
|
250
241
|
// 根据表格读取数据生成表格数据
|
|
251
|
-
dealImportTableData(columns, records) {
|
|
252
|
-
|
|
253
|
-
let fields = this.generateColumnsAll(columns)
|
|
242
|
+
const dealImportTableData = (columns, records) => {
|
|
243
|
+
let fields = generateColumnsAll(columns)
|
|
254
244
|
let errDatas = []
|
|
255
245
|
let results = records.map((row, rowIndex) => {
|
|
256
246
|
const item = {}
|
|
@@ -295,12 +285,12 @@ export default {
|
|
|
295
285
|
return item
|
|
296
286
|
})
|
|
297
287
|
return { results, errDatas }
|
|
298
|
-
}
|
|
288
|
+
}
|
|
299
289
|
// 生成全表头
|
|
300
|
-
generateColumnsAll(columns, resultColumns = []) {
|
|
290
|
+
const generateColumnsAll = (columns, resultColumns = []) => {
|
|
301
291
|
columns.forEach((column, index) => {
|
|
302
292
|
if (column.children && Array.isArray(column.children) && column.children.length) {
|
|
303
|
-
|
|
293
|
+
generateColumnsAll(column.children, resultColumns)
|
|
304
294
|
} else {
|
|
305
295
|
if (column.field) {
|
|
306
296
|
resultColumns.push({
|
|
@@ -314,8 +304,27 @@ export default {
|
|
|
314
304
|
})
|
|
315
305
|
return resultColumns
|
|
316
306
|
}
|
|
307
|
+
|
|
308
|
+
onBeforeMount(() => {
|
|
309
|
+
initCreated()
|
|
310
|
+
})
|
|
311
|
+
|
|
312
|
+
return {
|
|
313
|
+
shtable,
|
|
314
|
+
modalLoading,
|
|
315
|
+
showProgress,
|
|
316
|
+
progressPercent,
|
|
317
|
+
importErrorData,
|
|
318
|
+
tableColumns,
|
|
319
|
+
importTableData,
|
|
320
|
+
tableGlobalConfig,
|
|
321
|
+
onModalClose,
|
|
322
|
+
handleDownloadTemplateBtn,
|
|
323
|
+
handleImportFileBtn,
|
|
324
|
+
handleImportDataBtn
|
|
325
|
+
}
|
|
317
326
|
}
|
|
318
|
-
}
|
|
327
|
+
})
|
|
319
328
|
</script>
|
|
320
329
|
|
|
321
330
|
<style lang="scss" scoped>
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<vxe-colgroup v-if="isGroup" v-bind="groupConfig">
|
|
3
|
+
<template v-for="(child, childIndex) in column.children" :key="childIndex">
|
|
4
|
+
<sh-column :column="child" />
|
|
5
|
+
</template>
|
|
6
|
+
</vxe-colgroup>
|
|
7
|
+
<vxe-column v-else v-bind="columnConfig">
|
|
8
|
+
<template v-if="column.slots">{{ renderSlots }}</template>
|
|
9
|
+
</vxe-column>
|
|
10
|
+
</template>
|
|
11
|
+
|
|
12
|
+
<script>
|
|
13
|
+
import { computed, defineComponent, getCurrentInstance, inject, ref } from 'vue'
|
|
14
|
+
import { turnColumnItemFilters } from '../js/tableMethods'
|
|
15
|
+
export default defineComponent({
|
|
16
|
+
name: 'ShColumn',
|
|
17
|
+
props: {
|
|
18
|
+
column: {
|
|
19
|
+
type: Object
|
|
20
|
+
}
|
|
21
|
+
},
|
|
22
|
+
setup(props, context) {
|
|
23
|
+
const { proxy } = getCurrentInstance()
|
|
24
|
+
const { $vUtils } = proxy
|
|
25
|
+
const shTable = inject('ShTableInstance')
|
|
26
|
+
|
|
27
|
+
const isGroup = computed(() => {
|
|
28
|
+
return proxy.hasChildren(props.column)
|
|
29
|
+
})
|
|
30
|
+
const columnConfig = computed(() => {
|
|
31
|
+
let renderObj = { name: props.column.renderName, props: props.column.renderProps }
|
|
32
|
+
let config = Object.assign({}, shTable.columnObjConfig.value, props.column)
|
|
33
|
+
if (props.column.readonly) {
|
|
34
|
+
config.cellRender = config.cellRender || renderObj
|
|
35
|
+
} else {
|
|
36
|
+
config.editRender = config.editRender || renderObj
|
|
37
|
+
}
|
|
38
|
+
if (config.filter === true || Number(config.filter) === 1) {
|
|
39
|
+
shTable.turnColumnItemFilters(config, renderObj.props)
|
|
40
|
+
}
|
|
41
|
+
return $vUtils.omit(config, ['renderName', 'renderProps', 'renderRequire', 'requireProps'])
|
|
42
|
+
})
|
|
43
|
+
const groupConfig = computed(() => {
|
|
44
|
+
return $vUtils.omit(columnConfig.value, ['children', 'cellRender', 'editRender'])
|
|
45
|
+
})
|
|
46
|
+
const renderSlots = () => {
|
|
47
|
+
return Object.keys(column.slots).map(slotKey => {
|
|
48
|
+
return shTable.slots[slotKey]
|
|
49
|
+
})
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
return {
|
|
53
|
+
isGroup,
|
|
54
|
+
columnConfig,
|
|
55
|
+
groupConfig,
|
|
56
|
+
renderSlots
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
})
|
|
60
|
+
</script>
|
|
61
|
+
|
|
62
|
+
<style scoped lang="scss"></style>
|