@ddwl/ddwl-ui 1.2.3-beta.1 → 1.2.3-beta.2

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.
Files changed (144) hide show
  1. package/dist/app.common.js +30684 -0
  2. package/dist/app.css +18 -0
  3. package/dist/app.umd.js +30703 -0
  4. package/dist/app.umd.min.js +18 -0
  5. package/dist/demo.html +1 -0
  6. package/package.json +5 -4
  7. package/src/assets/video-play.jpeg +0 -0
  8. package/src/lib/install/index.js +14 -0
  9. package/src/lib/slots/buttonGroup.vue +113 -0
  10. package/src/lib/slots/dict.vue +46 -0
  11. package/src/lib/slots/file.vue +36 -0
  12. package/src/lib/slots/icon.vue +74 -0
  13. package/src/lib/slots/index.js +11 -0
  14. package/src/lib/theme/alert.css +1 -0
  15. package/src/lib/theme/aside.css +1 -0
  16. package/src/lib/theme/autocomplete.css +1 -0
  17. package/src/lib/theme/avatar.css +1 -0
  18. package/src/lib/theme/backtop.css +1 -0
  19. package/src/lib/theme/badge.css +1 -0
  20. package/src/lib/theme/base.css +1 -0
  21. package/src/lib/theme/breadcrumb-item.css +0 -0
  22. package/src/lib/theme/breadcrumb.css +1 -0
  23. package/src/lib/theme/button-group.css +0 -0
  24. package/src/lib/theme/button.css +1 -0
  25. package/src/lib/theme/calendar.css +1 -0
  26. package/src/lib/theme/card.css +1 -0
  27. package/src/lib/theme/carousel-item.css +1 -0
  28. package/src/lib/theme/carousel.css +1 -0
  29. package/src/lib/theme/cascader-panel.css +1 -0
  30. package/src/lib/theme/cascader.css +1 -0
  31. package/src/lib/theme/checkbox-button.css +0 -0
  32. package/src/lib/theme/checkbox-group.css +0 -0
  33. package/src/lib/theme/checkbox.css +1 -0
  34. package/src/lib/theme/col.css +1 -0
  35. package/src/lib/theme/collapse-item.css +0 -0
  36. package/src/lib/theme/collapse.css +1 -0
  37. package/src/lib/theme/color-picker.css +1 -0
  38. package/src/lib/theme/container.css +1 -0
  39. package/src/lib/theme/date-picker.css +1 -0
  40. package/src/lib/theme/descriptions-item.css +1 -0
  41. package/src/lib/theme/descriptions.css +1 -0
  42. package/src/lib/theme/dialog.css +1 -0
  43. package/src/lib/theme/display.css +1 -0
  44. package/src/lib/theme/divider.css +1 -0
  45. package/src/lib/theme/drawer.css +1 -0
  46. package/src/lib/theme/dropdown-item.css +0 -0
  47. package/src/lib/theme/dropdown-menu.css +0 -0
  48. package/src/lib/theme/dropdown.css +1 -0
  49. package/src/lib/theme/empty.css +1 -0
  50. package/src/lib/theme/fonts/element-icons.ttf +0 -0
  51. package/src/lib/theme/fonts/element-icons.woff +0 -0
  52. package/src/lib/theme/footer.css +1 -0
  53. package/src/lib/theme/form-item.css +0 -0
  54. package/src/lib/theme/form.css +1 -0
  55. package/src/lib/theme/header.css +1 -0
  56. package/src/lib/theme/icon.css +1 -0
  57. package/src/lib/theme/image.css +1 -0
  58. package/src/lib/theme/index.css +1 -0
  59. package/src/lib/theme/infinite-scroll.css +0 -0
  60. package/src/lib/theme/infiniteScroll.css +0 -0
  61. package/src/lib/theme/input-number.css +1 -0
  62. package/src/lib/theme/input.css +1 -0
  63. package/src/lib/theme/link.css +1 -0
  64. package/src/lib/theme/loading.css +1 -0
  65. package/src/lib/theme/main.css +1 -0
  66. package/src/lib/theme/menu-item-group.css +0 -0
  67. package/src/lib/theme/menu-item.css +0 -0
  68. package/src/lib/theme/menu.css +1 -0
  69. package/src/lib/theme/message-box.css +1 -0
  70. package/src/lib/theme/message.css +1 -0
  71. package/src/lib/theme/notification.css +1 -0
  72. package/src/lib/theme/option-group.css +1 -0
  73. package/src/lib/theme/option.css +1 -0
  74. package/src/lib/theme/page-header.css +1 -0
  75. package/src/lib/theme/pagination.css +1 -0
  76. package/src/lib/theme/popconfirm.css +1 -0
  77. package/src/lib/theme/popover.css +1 -0
  78. package/src/lib/theme/popper.css +1 -0
  79. package/src/lib/theme/progress.css +1 -0
  80. package/src/lib/theme/radio-button.css +1 -0
  81. package/src/lib/theme/radio-group.css +1 -0
  82. package/src/lib/theme/radio.css +1 -0
  83. package/src/lib/theme/rate.css +1 -0
  84. package/src/lib/theme/reset.css +1 -0
  85. package/src/lib/theme/result.css +1 -0
  86. package/src/lib/theme/row.css +1 -0
  87. package/src/lib/theme/scrollbar.css +1 -0
  88. package/src/lib/theme/select-dropdown.css +1 -0
  89. package/src/lib/theme/select.css +1 -0
  90. package/src/lib/theme/skeleton-item.css +1 -0
  91. package/src/lib/theme/skeleton.css +1 -0
  92. package/src/lib/theme/slider.css +1 -0
  93. package/src/lib/theme/spinner.css +1 -0
  94. package/src/lib/theme/step.css +1 -0
  95. package/src/lib/theme/steps.css +1 -0
  96. package/src/lib/theme/submenu.css +0 -0
  97. package/src/lib/theme/switch.css +1 -0
  98. package/src/lib/theme/tab-pane.css +0 -0
  99. package/src/lib/theme/table-column.css +1 -0
  100. package/src/lib/theme/table.css +1 -0
  101. package/src/lib/theme/tabs.css +1 -0
  102. package/src/lib/theme/tag.css +1 -0
  103. package/src/lib/theme/time-picker.css +1 -0
  104. package/src/lib/theme/time-select.css +1 -0
  105. package/src/lib/theme/timeline-item.css +1 -0
  106. package/src/lib/theme/timeline.css +1 -0
  107. package/src/lib/theme/tooltip.css +1 -0
  108. package/src/lib/theme/transfer.css +1 -0
  109. package/src/lib/theme/tree.css +1 -0
  110. package/src/lib/theme/upload.css +1 -0
  111. package/src/main.js +70 -0
  112. package/src/packages/button/index.vue +36 -0
  113. package/src/packages/checkbox-group/index.vue +57 -0
  114. package/src/packages/descriptions/index.vue +124 -0
  115. package/src/packages/dialog/index.vue +172 -0
  116. package/src/packages/dialog-confirm/index.vue +99 -0
  117. package/src/packages/drawer/index.vue +136 -0
  118. package/src/packages/file-preview/index.vue +275 -0
  119. package/src/packages/file-preview/static/audio.png +0 -0
  120. package/src/packages/file-preview/static/video.png +0 -0
  121. package/src/packages/filter-tree/index.vue +292 -0
  122. package/src/packages/form/index.vue +149 -0
  123. package/src/packages/form-item/index.vue +199 -0
  124. package/src/packages/import-file/index.vue +173 -0
  125. package/src/packages/menu/index.vue +66 -0
  126. package/src/packages/menu/menuItem.vue +90 -0
  127. package/src/packages/popconfirm/index.vue +39 -0
  128. package/src/packages/radio-group/index.vue +57 -0
  129. package/src/packages/render/index.vue +14 -0
  130. package/src/packages/search-form/index.vue +257 -0
  131. package/src/packages/search-input/index.vue +68 -0
  132. package/src/packages/search-table/index.vue +93 -0
  133. package/src/packages/select/index.vue +74 -0
  134. package/src/packages/svg-icon/index.vue +43 -0
  135. package/src/packages/table/drag.png +0 -0
  136. package/src/packages/table/index.vue +453 -0
  137. package/src/packages/upload/index.vue +350 -0
  138. package/src/utils/constant.js +4 -0
  139. package/src/utils/index.js +77 -0
  140. package/src/utils/treeLib.js +190 -0
  141. package/dist/index.html +0 -1
  142. package/dist/js/app.js +0 -1
  143. package/dist/js/chunk-vendors.js +0 -17
  144. package/dist/static/css/app.2ec4a629.css +0 -1
@@ -0,0 +1,173 @@
1
+ <template>
2
+ <d-dialog
3
+ v-model="visible"
4
+ form-refs="importForm"
5
+ :width="width"
6
+ :title="title"
7
+ submit-btn-text="导入"
8
+ submit-btn-icon="el-icon-upload2"
9
+ @submit="submit"
10
+ >
11
+ <el-form
12
+ ref="importForm"
13
+ :model="form"
14
+ :inline="true"
15
+ >
16
+ <el-form-item
17
+ class="import-form-item"
18
+ prop="file"
19
+ label="选择文件"
20
+ :rules="[
21
+ { required: true, message: '请选择文件' }
22
+ ]"
23
+ >
24
+ <div class="custom-file-input">
25
+ <div class="custom-file-content">
26
+ {{ form.file ? form.file.name : '请选择' }}
27
+ </div>
28
+ <el-upload
29
+ :file-list="fileList"
30
+ :show-file-list="false"
31
+ :auto-upload="false"
32
+ action=""
33
+ :on-change="uploadChange"
34
+ >
35
+ <el-button
36
+ type="primary"
37
+ icon="el-icon-folder"
38
+ />
39
+ </el-upload>
40
+ </div>
41
+ </el-form-item>
42
+ <el-button
43
+ v-show="templateUrl"
44
+ icon="el-icon-paperclip"
45
+ type="text"
46
+ @click="downloadFile"
47
+ >
48
+ 模板下载
49
+ </el-button>
50
+ </el-form>
51
+ <slot>
52
+ <p>1. 支持导入格式为{{ fileType.join('、') }}的文件,且文件大小不可超过{{ fileSize }}M</p>
53
+ <p>2. 模板的表头不可更改,不可删除</p>
54
+ <p>3. 若导入数据存在编码一致的情况则会更新原有数据</p>
55
+ <p>4. 若导入过程中有问题,需调整模板内容后再重新导入</p>
56
+ </slot>
57
+ </d-dialog>
58
+ </template>
59
+
60
+ <script>
61
+ import DDialog from '../dialog'
62
+
63
+ export default {
64
+ name: 'DImportFile',
65
+ components: { DDialog },
66
+ model: {
67
+ prop: 'modelValue',
68
+ event: 'change'
69
+ },
70
+ props: {
71
+ modelValue: {
72
+ default: false,
73
+ type: Boolean
74
+ },
75
+ width: {
76
+ default: '520px',
77
+ type: String
78
+ },
79
+ title: {
80
+ default: '',
81
+ type: String
82
+ },
83
+ templateUrl: {
84
+ default: '',
85
+ type: String
86
+ },
87
+ fileType: {
88
+ default: () => ['xlsx', 'xls'],
89
+ type: Array
90
+ },
91
+ fileSize: {
92
+ default: 5,
93
+ type: Number
94
+ }
95
+ },
96
+ data () {
97
+ return {
98
+ fileList: [],
99
+ form: {
100
+ file: ''
101
+ }
102
+ }
103
+ },
104
+ computed: {
105
+ visible: {
106
+ get () {
107
+ return this.modelValue
108
+ },
109
+ set (value) {
110
+ this.form.file = ''
111
+ this.fileList = []
112
+ this.$refs.importForm.clearValidate()
113
+ this.$emit('change', value)
114
+ }
115
+ }
116
+ },
117
+ methods: {
118
+ downloadFile () {
119
+ let token
120
+ try {
121
+ token = JSON.parse(window.localStorage.getItem('userInfo')).token
122
+ } catch (e) {
123
+ token = ''
124
+ }
125
+ window.location.href = `${this.templateUrl}?authToken=${token}`
126
+ },
127
+ uploadChange (file, fileList) {
128
+ const isLimit = file.size / 1024 / 1024 < this.fileSize
129
+ const isType = this.fileType.includes(file.name.substr(file.name.lastIndexOf('.') + 1).toLocaleLowerCase())
130
+ if (!isType) {
131
+ this.$message.error(`请上传正确的文件格式(${this.fileType.join('、')})`)
132
+ return false
133
+ }
134
+ if (!isLimit) {
135
+ this.$message.error(`上传文件大小不能超过${this.fileSize}MB`)
136
+ return false
137
+ }
138
+ this.fileList = fileList
139
+ this.form.file = file.raw
140
+ },
141
+ async submit (callback) {
142
+ if (!this.form.file) {
143
+ this.$message.error('请选择导入文件')
144
+ callback(new Error(false))
145
+ return
146
+ }
147
+ try {
148
+ this.$emit('submit', this.form.file, callback)
149
+ } catch (e) {
150
+ callback(new Error(false))
151
+ }
152
+ }
153
+ }
154
+ }
155
+ </script>
156
+
157
+ <style lang="scss" scoped>
158
+ .custom-file-input {
159
+ display: flex;
160
+ width: 230px;
161
+ .custom-file-content {
162
+ width: 100%;
163
+ height: 32px;
164
+ border: 1px solid #dcdfe6;
165
+ border-right: none;
166
+ border-radius: 2px 0 0 2px;
167
+ padding: 0 8px;
168
+ white-space: nowrap;
169
+ overflow: hidden;
170
+ text-overflow: ellipsis;
171
+ }
172
+ }
173
+ </style>
@@ -0,0 +1,66 @@
1
+ <!-- 菜单 -->
2
+ <template>
3
+ <el-menu
4
+ class="d-menu"
5
+ :default-active="isVertical ? $route.path : activeMenu"
6
+ :router="isVertical"
7
+ unique-opened
8
+ :mode="mode"
9
+ @select="menuSelect">
10
+ <menu-item v-for="item in data" :key="item.name" :data="item" :mode="mode"></menu-item>
11
+ </el-menu>
12
+ </template>
13
+
14
+ <script>
15
+ import MenuItem from './menuItem.vue'
16
+ export default {
17
+ name: 'DMenu',
18
+ components: { MenuItem },
19
+ props: {
20
+ data: {
21
+ type: Array,
22
+ default: () => []
23
+ },
24
+ mode: {
25
+ type: String,
26
+ default: 'vertical'
27
+ }
28
+ },
29
+ data () {
30
+ return {
31
+ activeMenu: ''
32
+ }
33
+ },
34
+ computed: {
35
+ isVertical () {
36
+ return this.mode === 'vertical'
37
+ }
38
+ },
39
+ watch: {
40
+ '$route.path': {
41
+ handler (path) {
42
+ if (!this.isVertical) {
43
+ if (this.activeMenu && path.substring(0, this.activeMenu.length) === this.activeMenu) return
44
+ const data = this.data.find(item => path.substring(0, item.path.length) === item.path)
45
+ this.activeMenu = data?.path
46
+ this.$emit('select', data, false)
47
+ }
48
+ },
49
+ immediate: true
50
+ }
51
+ },
52
+ methods: {
53
+ menuSelect (index) {
54
+ if (this.isVertical) return
55
+ const data = this.data.find(item => item.path === index)
56
+ this.$emit('select', data, true)
57
+ }
58
+ }
59
+ }
60
+ </script>
61
+
62
+ <style lang='scss' scoped>
63
+ .d-menu {
64
+ height: 100%;
65
+ }
66
+ </style>
@@ -0,0 +1,90 @@
1
+ <!-- 菜单子项 -->
2
+ <template>
3
+ <el-submenu
4
+ v-if="mode === 'vertical' && data.children && data.children.length"
5
+ :index="data.path"
6
+ >
7
+ <template slot="title">
8
+ <img
9
+ v-if="data.meta.icon"
10
+ class="mr8 menu-icon"
11
+ :src="data.meta.icon"
12
+ >
13
+ <span>{{ data.meta.title }}</span>
14
+ </template>
15
+ <menu-item
16
+ v-for="item in data.children"
17
+ :key="item.name"
18
+ :data="item"
19
+ />
20
+ </el-submenu>
21
+ <el-menu-item
22
+ v-else
23
+ :index="data.path"
24
+ >
25
+ <template slot="title">
26
+ <div
27
+ v-if="data.meta.icon"
28
+ class="menu-icon-box"
29
+ >
30
+ <img
31
+ class="menu-icon"
32
+ :src="data.meta.icon"
33
+ >
34
+ </div>
35
+ <span
36
+ v-if="data.meta.isNewWindow"
37
+ class="ml6 ellipsis flex-1"
38
+ @click.stop="openNewWindow(data)"
39
+ >{{ data.meta.title }}</span>
40
+ <span
41
+ v-else
42
+ class="ml6 ellipsis flex-1"
43
+ >{{ data.meta.title }}</span>
44
+ </template>
45
+ </el-menu-item>
46
+ </template>
47
+
48
+ <script>
49
+ export default {
50
+ name: 'MenuItem',
51
+ components: {},
52
+ props: {
53
+ data: {
54
+ type: Object,
55
+ default: () => ({})
56
+ },
57
+ mode: {
58
+ type: String,
59
+ default: 'vertical'
60
+ }
61
+ },
62
+ data () {
63
+ return {
64
+ }
65
+ },
66
+ computed: {},
67
+ created () {},
68
+ methods: {
69
+ openNewWindow (data) {
70
+ window.open(data.path, '_blank')
71
+ }
72
+ }
73
+ }
74
+ </script>
75
+
76
+ <style lang='scss' scoped>
77
+ .menu-icon-box {
78
+ width: 26px;
79
+ height: 26px;
80
+ border-radius: 50%;
81
+ background-color: #fff;
82
+ display: flex;
83
+ align-items: center;
84
+ justify-content: center;
85
+ }
86
+ .menu-icon {
87
+ width: 16px;
88
+ height: 16px;
89
+ }
90
+ </style>
@@ -0,0 +1,39 @@
1
+ <!-- 二次确认气泡 -->
2
+ <template>
3
+ <el-popconfirm
4
+ :title="title"
5
+ cancel-button-type=""
6
+ icon="el-icon-warning"
7
+ @confirm="confirm"
8
+ >
9
+ <span slot="reference" :class="`${type}-text-btn`">{{ buttonName }}</span>
10
+ </el-popconfirm>
11
+ </template>
12
+
13
+ <script>
14
+ export default {
15
+ name: 'DPopconfirm',
16
+ props: {
17
+ title: {
18
+ default: '您确定删除该信息?',
19
+ type: String
20
+ },
21
+ buttonName: {
22
+ default: '删除',
23
+ type: String
24
+ },
25
+ type: {
26
+ default: 'primary',
27
+ type: String
28
+ }
29
+ },
30
+ data () {
31
+ return {}
32
+ },
33
+ methods: {
34
+ confirm () {
35
+ this.$emit('confirm')
36
+ }
37
+ }
38
+ }
39
+ </script>
@@ -0,0 +1,57 @@
1
+ <!-- 单选框组 -->
2
+ <template>
3
+ <el-radio-group
4
+ v-model="value"
5
+ v-bind="$attrs"
6
+ v-on="$listeners"
7
+ >
8
+ <el-radio
9
+ v-for="item in options"
10
+ :key="item.value"
11
+ :label="item.value"
12
+ >
13
+ {{ item.label }}
14
+ </el-radio>
15
+ </el-radio-group>
16
+ </template>
17
+
18
+ <script>
19
+ export default {
20
+ name: 'DRadioGroup',
21
+ components: {},
22
+ model: {
23
+ prop: 'modelValue',
24
+ event: 'modelChange'
25
+ },
26
+ props: {
27
+ modelValue: {
28
+ type: [String, Number],
29
+ default: ''
30
+ },
31
+ options: {
32
+ type: Array,
33
+ default: () => []
34
+ }
35
+ },
36
+ data () {
37
+ return {
38
+ }
39
+ },
40
+ computed: {
41
+ value: {
42
+ get () {
43
+ return this.modelValue
44
+ },
45
+ set (value) {
46
+ this.$emit('modelChange', value)
47
+ }
48
+ }
49
+ },
50
+ watch: {},
51
+ created () {},
52
+ methods: {}
53
+ }
54
+ </script>
55
+
56
+ <style lang='scss' scoped>
57
+ </style>
@@ -0,0 +1,14 @@
1
+ <!-- eslint-disable vue/require-default-prop -->
2
+ <script>
3
+ export default {
4
+ name: 'DRender',
5
+ functional: true,
6
+ props: {
7
+ scope: Object,
8
+ render: Function
9
+ },
10
+ render: (h, ctx) => {
11
+ return ctx.props.render ? ctx.props.render(ctx.props.scope, h) : ''
12
+ }
13
+ }
14
+ </script>
@@ -0,0 +1,257 @@
1
+ <!-- 搜索组件 -->
2
+ <template>
3
+ <div class="d-search-form">
4
+ <el-row class="flex-wrap" :gutter="gutter">
5
+ <el-col
6
+ v-for="(item, index) in list"
7
+ v-show="showCol(index)"
8
+ :key="item.prop"
9
+ :span="item.span || Math.floor(24 / cell)"
10
+ class="col-item"
11
+ >
12
+ <div class="search-item">
13
+ <div class="search-item-label">
14
+ {{ item.label }}
15
+ </div>
16
+ <form-item v-model="form[item.prop]" :config="item" />
17
+ </div>
18
+ </el-col>
19
+ <el-col :span="hiddenIndex === list.length || expend ? emptySpan : 0" style="height: 68px;">
20
+ <span />
21
+ </el-col>
22
+ <el-col v-if="hasSlot && expend && !suffixSlot" :span="24 - submitSpan" class="mb16">
23
+ <slot />
24
+ </el-col>
25
+ <el-col :span="submitSpan">
26
+ <div
27
+ :style="{
28
+ 'margin-top': hasSlot && expend && !suffixSlot ? '0px' : '24px'
29
+ }"
30
+ class="d-search-form-btn"
31
+ >
32
+ <el-button type="primary" :disabled="searchLoading" @click="search">
33
+ 查询
34
+ </el-button>
35
+ <el-button :disabled="searchLoading" @click="reset">
36
+ 重置
37
+ </el-button>
38
+ <el-button
39
+ v-if="list.length > hiddenIndex"
40
+ class="expend-btn"
41
+ :class="`el-icon-arrow-${expend ? 'up' : 'down'}`"
42
+ @click="changeStatus"
43
+ />
44
+ </div>
45
+ </el-col>
46
+ <el-col v-if="hasSlot && (!expend || suffixSlot)" :span="20" class="mb16">
47
+ <slot />
48
+ </el-col>
49
+ </el-row>
50
+ </div>
51
+ </template>
52
+
53
+ <script>
54
+ import FormItem from '../form-item'
55
+ import { cloneDeep } from 'lodash'
56
+
57
+ // 初始化表单
58
+ let initForm = {}
59
+
60
+ export default {
61
+ name: 'DSearchForm',
62
+ components: {
63
+ FormItem
64
+ },
65
+ model: {
66
+ prop: 'value',
67
+ event: 'change'
68
+ },
69
+ props: {
70
+ config: {
71
+ require: true,
72
+ default: () => [],
73
+ type: Array
74
+ },
75
+ cell: {
76
+ default: 6,
77
+ type: Number
78
+ },
79
+ gutter: {
80
+ default: 16,
81
+ type: Number
82
+ },
83
+ value: {
84
+ default: () => {},
85
+ type: Object
86
+ },
87
+ searchData: {
88
+ default: null,
89
+ type: Function
90
+ },
91
+ buttonSpan: {
92
+ default: 0,
93
+ type: Number
94
+ }
95
+ },
96
+ data () {
97
+ return {
98
+ list: [],
99
+ hiddenIndex: 0,
100
+ emptySpan: 0,
101
+ expend: false,
102
+ searchLoading: false,
103
+ // 判断是否有插槽节点,目前只在组件初始化完成时判断
104
+ hasSlot: false,
105
+ suffixSlot: true
106
+ }
107
+ },
108
+ computed: {
109
+ form: {
110
+ get () {
111
+ return this.value
112
+ },
113
+ set (value) {
114
+ this.$emit('change', value)
115
+ }
116
+ },
117
+ submitSpan () {
118
+ return this.buttonSpan || 24 / this.cell
119
+ },
120
+ spanList () {
121
+ return this.list.map(item => item.span || Math.floor(24 / this.cell)) || []
122
+ },
123
+ showCol () {
124
+ return (index) => {
125
+ return this.expend || index < this.hiddenIndex
126
+ }
127
+ }
128
+ },
129
+ watch: {
130
+ config: {
131
+ handler () {
132
+ this.list = this.config.filter(item => !item.hidden)
133
+ },
134
+ deep: true,
135
+ immediate: true
136
+ },
137
+ spanList: {
138
+ handler (val, oldVal) {
139
+ if (!val.length || JSON.stringify(val) === JSON.stringify(oldVal)) {
140
+ return
141
+ }
142
+ this.calcSpan()
143
+ },
144
+ deep: true,
145
+ immediate: true
146
+ }
147
+ },
148
+ created () {
149
+ initForm = cloneDeep(this.value)
150
+ this.$nextTick(() => {
151
+ this.hasSlot = !!(this.$slots.default && this.$slots.default.length)
152
+ this.calcSpan()
153
+ })
154
+ },
155
+ methods: {
156
+ /**
157
+ * @description: 查询
158
+ */
159
+ async search () {
160
+ this.$emit('search')
161
+ if (this.searchData) {
162
+ try {
163
+ this.searchLoading = true
164
+ await this.searchData({ pageNum: 1 }, this.form)
165
+ this.searchLoading = false
166
+ } catch (e) {
167
+ this.searchLoading = false
168
+ }
169
+ }
170
+ },
171
+ /**
172
+ * @description: 重置
173
+ */
174
+ async reset () {
175
+ this.form = cloneDeep(initForm)
176
+ this.$emit('search')
177
+ if (this.searchData) {
178
+ this.resetLoading = true
179
+ await this.searchData({ pageNum: 1 }, this.form)
180
+ this.resetLoading = false
181
+ }
182
+ },
183
+ /**
184
+ * @description: 展开/收起
185
+ */
186
+ changeStatus () {
187
+ this.expend = !this.expend
188
+ this.$emit('expand-change', this.expend)
189
+ },
190
+ calcSpan () {
191
+ let hiddenIndex = 1
192
+ const total = this.spanList.length ? this.spanList.reduce((a, b, index) => {
193
+ const sum = a + b
194
+ if (hiddenIndex < 2) {
195
+ if (24 - sum < this.submitSpan) {
196
+ hiddenIndex = index
197
+ }
198
+ if (24 - sum >= this.submitSpan && index === this.spanList.length - 1) {
199
+ hiddenIndex = index + 1
200
+ }
201
+ }
202
+ return sum
203
+ }) : 0
204
+ this.hiddenIndex = hiddenIndex
205
+
206
+ const offsetSpan = 24 - total % 24
207
+ if (this.hasSlot) {
208
+ if (offsetSpan < this.submitSpan || offsetSpan === 24) {
209
+ this.suffixSlot = false
210
+ this.emptySpan = 0
211
+ } else {
212
+ this.suffixSlot = true
213
+ this.emptySpan = offsetSpan >= this.submitSpan ? offsetSpan - this.submitSpan : 24 - this.submitSpan
214
+ }
215
+ } else {
216
+ this.emptySpan = offsetSpan >= this.submitSpan ? offsetSpan - this.submitSpan : 24 - this.submitSpan
217
+ }
218
+ }
219
+ }
220
+ }
221
+ </script>
222
+
223
+ <style lang="scss" scoped>
224
+ .d-search-form {
225
+ margin-bottom: 4px;
226
+ .col-item {
227
+ align-items: end;
228
+ }
229
+ .el-select {
230
+ width: 100%;
231
+ .el-input_inner {
232
+ height: 32px;
233
+ }
234
+ }
235
+ &-btn {
236
+ text-align: right;
237
+ margin-bottom: 16px;
238
+ }
239
+ &-overflow {
240
+ margin-top: 24px;
241
+ }
242
+ .expend-btn {
243
+ padding: 4px 8px;
244
+ }
245
+ }
246
+ .search-item {
247
+ margin-bottom: 12px;
248
+ &-label {
249
+ margin-bottom: 4px;
250
+ font-weight: 400;
251
+ color: #333333;
252
+ }
253
+ :deep(.el-input__inner) {
254
+ height: 32px !important;
255
+ }
256
+ }
257
+ </style>