vxe-table 3.20.5 → 3.20.6

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 (141) hide show
  1. package/LICENSE +20 -20
  2. package/README.md +106 -106
  3. package/es/index.esm.js +1 -2
  4. package/es/style.css +1 -1
  5. package/es/table/src/methods.js +20 -0
  6. package/es/table/src/table.js +36 -0
  7. package/es/table/src/util.js +3 -4
  8. package/es/table/style.css +48 -18
  9. package/es/ui/index.js +1 -1
  10. package/es/ui/src/log.js +1 -1
  11. package/es/vxe-table/style.css +48 -18
  12. package/lib/index.common.js +1 -2
  13. package/lib/index.umd.js +3251 -1876
  14. package/lib/index.umd.min.js +1 -1
  15. package/lib/style.css +1 -1
  16. package/lib/table/src/methods.js +2 -1
  17. package/lib/table/src/methods.min.js +1 -1
  18. package/lib/table/src/table.js +44 -0
  19. package/lib/table/src/table.min.js +1 -1
  20. package/lib/table/src/util.js +4 -6
  21. package/lib/table/src/util.min.js +1 -1
  22. package/lib/table/style/style.css +48 -18
  23. package/lib/ui/index.js +1 -1
  24. package/lib/ui/index.min.js +1 -1
  25. package/lib/ui/src/log.js +1 -1
  26. package/lib/ui/src/log.min.js +1 -1
  27. package/lib/v-x-e-table/index.js +1 -2
  28. package/lib/v-x-e-table/index.min.js +1 -1
  29. package/lib/vxe-colgroup/index.js +1 -2
  30. package/lib/vxe-colgroup/index.min.js +1 -1
  31. package/lib/vxe-column/index.js +1 -2
  32. package/lib/vxe-column/index.min.js +1 -1
  33. package/lib/vxe-grid/index.js +1 -2
  34. package/lib/vxe-grid/index.min.js +1 -1
  35. package/lib/vxe-table/index.js +1 -2
  36. package/lib/vxe-table/index.min.js +1 -1
  37. package/lib/vxe-table/style/style.css +48 -18
  38. package/lib/vxe-toolbar/index.js +1 -2
  39. package/lib/vxe-toolbar/index.min.js +1 -1
  40. package/lib/vxe-ui/index.js +1 -2
  41. package/lib/vxe-ui/index.min.js +1 -1
  42. package/lib/vxe-v-x-e-table/index.js +1 -2
  43. package/lib/vxe-v-x-e-table/index.min.js +1 -1
  44. package/package.json +93 -93
  45. package/packages/colgroup/index.ts +22 -22
  46. package/packages/column/index.ts +22 -22
  47. package/packages/components.ts +42 -42
  48. package/packages/grid/index.ts +22 -22
  49. package/packages/grid/src/grid.ts +1935 -1935
  50. package/packages/index.ts +4 -4
  51. package/packages/locale/lang/ar-EG.ts +832 -832
  52. package/packages/locale/lang/de-DE.ts +832 -832
  53. package/packages/locale/lang/en-US.ts +832 -832
  54. package/packages/locale/lang/es-ES.ts +832 -832
  55. package/packages/locale/lang/fr-FR.ts +832 -832
  56. package/packages/locale/lang/hu-HU.ts +832 -832
  57. package/packages/locale/lang/hy-AM.ts +832 -832
  58. package/packages/locale/lang/id-ID.ts +832 -832
  59. package/packages/locale/lang/it-IT.ts +832 -832
  60. package/packages/locale/lang/ja-JP.ts +832 -832
  61. package/packages/locale/lang/ko-KR.ts +832 -832
  62. package/packages/locale/lang/ms-MY.ts +832 -832
  63. package/packages/locale/lang/nb-NO.ts +832 -832
  64. package/packages/locale/lang/pt-BR.ts +832 -832
  65. package/packages/locale/lang/ru-RU.ts +832 -832
  66. package/packages/locale/lang/th-TH.ts +832 -832
  67. package/packages/locale/lang/ug-CN.ts +832 -832
  68. package/packages/locale/lang/uk-UA.ts +832 -832
  69. package/packages/locale/lang/uz-UZ.ts +832 -832
  70. package/packages/locale/lang/vi-VN.ts +832 -832
  71. package/packages/locale/lang/zh-CHT.ts +832 -832
  72. package/packages/locale/lang/zh-CN.ts +832 -832
  73. package/packages/locale/lang/zh-HK.ts +3 -3
  74. package/packages/locale/lang/zh-MO.ts +3 -3
  75. package/packages/locale/lang/zh-TC.ts +3 -3
  76. package/packages/locale/lang/zh-TW.ts +3 -3
  77. package/packages/table/index.ts +49 -49
  78. package/packages/table/module/custom/mixin.ts +369 -369
  79. package/packages/table/module/custom/panel.ts +1461 -1461
  80. package/packages/table/module/edit/mixin.ts +1123 -1123
  81. package/packages/table/module/export/export-panel.ts +658 -658
  82. package/packages/table/module/export/import-panel.ts +319 -319
  83. package/packages/table/module/export/mixin.ts +1693 -1693
  84. package/packages/table/module/export/util.ts +24 -24
  85. package/packages/table/module/filter/mixin.ts +507 -507
  86. package/packages/table/module/filter/panel.ts +329 -329
  87. package/packages/table/module/keyboard/mixin.ts +513 -513
  88. package/packages/table/module/menu/mixin.ts +329 -329
  89. package/packages/table/module/menu/panel.ts +212 -212
  90. package/packages/table/module/validator/mixin.ts +626 -626
  91. package/packages/table/render/index.ts +1456 -1456
  92. package/packages/table/src/body.ts +969 -969
  93. package/packages/table/src/cell.ts +1285 -1285
  94. package/packages/table/src/column.ts +205 -205
  95. package/packages/table/src/columnInfo.ts +228 -228
  96. package/packages/table/src/footer.ts +388 -388
  97. package/packages/table/src/group.ts +51 -51
  98. package/packages/table/src/header.ts +602 -602
  99. package/packages/table/src/methods.ts +12939 -12920
  100. package/packages/table/src/props.ts +311 -311
  101. package/packages/table/src/store.ts +15 -15
  102. package/packages/table/src/table.ts +2502 -2460
  103. package/packages/table/src/util.ts +1012 -1012
  104. package/packages/toolbar/index.ts +18 -18
  105. package/packages/toolbar/src/toolbar.ts +856 -856
  106. package/packages/ui/index.ts +530 -530
  107. package/packages/ui/src/anime.ts +52 -52
  108. package/packages/ui/src/comp.ts +3 -3
  109. package/packages/ui/src/dom.ts +236 -236
  110. package/packages/ui/src/log.ts +8 -8
  111. package/packages/ui/src/utils.ts +56 -56
  112. package/packages/ui/src/vn.ts +65 -65
  113. package/packages/v-x-e-table/index.ts +4 -4
  114. package/styles/all.scss +7 -7
  115. package/styles/base.scss +16 -16
  116. package/styles/components/grid.scss +89 -89
  117. package/styles/components/icon.scss +225 -225
  118. package/styles/components/old-icon.scss +715 -715
  119. package/styles/components/table-module/all.scss +6 -6
  120. package/styles/components/table-module/custom.scss +527 -527
  121. package/styles/components/table-module/export.scss +130 -130
  122. package/styles/components/table-module/filter.scss +130 -130
  123. package/styles/components/table-module/menu.scss +81 -81
  124. package/styles/components/table.scss +2679 -2679
  125. package/styles/components/toolbar.scss +119 -119
  126. package/styles/default.scss +2 -2
  127. package/styles/helpers/baseMixin.scss +95 -95
  128. package/styles/index.scss +3 -3
  129. package/styles/modules.scss +5 -5
  130. package/styles/theme/base.scss +93 -93
  131. package/styles/theme/dark.scss +49 -49
  132. package/styles/theme/light.scss +44 -44
  133. package/styles/variable.scss +43 -43
  134. package/types/all.d.ts +53 -53
  135. package/types/index.d.ts +4 -4
  136. /package/es/{iconfont.1773710661615.ttf → iconfont.1773972972913.ttf} +0 -0
  137. /package/es/{iconfont.1773710661615.woff → iconfont.1773972972913.woff} +0 -0
  138. /package/es/{iconfont.1773710661615.woff2 → iconfont.1773972972913.woff2} +0 -0
  139. /package/lib/{iconfont.1773710661615.ttf → iconfont.1773972972913.ttf} +0 -0
  140. /package/lib/{iconfont.1773710661615.woff → iconfont.1773972972913.woff} +0 -0
  141. /package/lib/{iconfont.1773710661615.woff2 → iconfont.1773972972913.woff2} +0 -0
@@ -1,329 +1,329 @@
1
- import XEUtils from 'xe-utils'
2
- import { VxeUI } from '../../../ui'
3
- import { getDomNode, getAbsolutePos, getEventTargetNode } from '../../../ui/src/dom'
4
- import { isEnableConf, hasChildrenList } from '../../../ui/src/utils'
5
- import { warnLog } from '../../../ui/src/log'
6
-
7
- import type { VxeTableConstructor, VxeTablePrivateMethods, TableInternalData, TableReactData, VxeTableDefines } from '../../../../types'
8
-
9
- const { menus, globalEvents, GLOBAL_EVENT_KEYS } = VxeUI
10
-
11
- export default {
12
- methods: {
13
- /**
14
- * 关闭快捷菜单
15
- */
16
- _closeMenu () {
17
- const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
18
- const reactData = $xeTable as unknown as TableReactData
19
-
20
- Object.assign(reactData.ctxMenuStore, {
21
- visible: false,
22
- selected: null,
23
- selectChild: null,
24
- showChild: false
25
- })
26
- return $xeTable.$nextTick()
27
- },
28
- // 处理菜单的移动
29
- moveCtxMenu (evnt: KeyboardEvent, ctxMenuStore: any, property: 'selectChild' | 'selected', hasOper: boolean, operRest: any, menuList: any[]) {
30
- const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
31
-
32
- let selectItem
33
- const selectIndex = XEUtils.findIndexOf(menuList, item => ctxMenuStore[property] === item)
34
- if (hasOper) {
35
- if (operRest && hasChildrenList(ctxMenuStore.selected)) {
36
- ctxMenuStore.showChild = true
37
- } else {
38
- ctxMenuStore.showChild = false
39
- ctxMenuStore.selectChild = null
40
- }
41
- } else if (globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.ARROW_UP)) {
42
- for (let len = selectIndex - 1; len >= 0; len--) {
43
- if (menuList[len].visible !== false) {
44
- selectItem = menuList[len]
45
- break
46
- }
47
- }
48
- ctxMenuStore[property] = selectItem || menuList[menuList.length - 1]
49
- } else if (globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.ARROW_DOWN)) {
50
- for (let index = selectIndex + 1; index < menuList.length; index++) {
51
- if (menuList[index].visible !== false) {
52
- selectItem = menuList[index]
53
- break
54
- }
55
- }
56
- ctxMenuStore[property] = selectItem || menuList[0]
57
- } else if (ctxMenuStore[property] && (globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.ENTER) || globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.SPACEBAR))) {
58
- $xeTable.ctxMenuLinkEvent(evnt, ctxMenuStore[property])
59
- }
60
- },
61
- /**
62
- * 快捷菜单事件处理
63
- */
64
- handleGlobalContextmenuEvent (evnt: any) {
65
- const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
66
- const $xeGrid = $xeTable.$xeGrid
67
- const $xeGantt = $xeTable.$xeGantt
68
- const props = $xeTable
69
- const reactData = $xeTable as unknown as TableReactData
70
- const internalData = $xeTable as unknown as TableInternalData
71
-
72
- const { xID } = $xeTable
73
-
74
- const { mouseConfig, menuConfig } = props
75
- const { editStore, ctxMenuStore } = reactData
76
- const { visibleColumn } = internalData
77
- const tableFilter = $xeTable.$refs.refTableFilter
78
- const tableMenu = $xeTable.$refs.refTableMenu
79
- const mouseOpts = $xeTable.computeMouseOpts
80
- const menuOpts = $xeTable.computeMenuOpts
81
- const el = $xeTable.$refs.refElem as HTMLDivElement
82
- const { selected } = editStore
83
- const layoutList = ['header', 'body', 'footer']
84
- if (isEnableConf(menuConfig)) {
85
- if (ctxMenuStore.visible && tableMenu && getEventTargetNode(evnt, (tableMenu as any).$el).flag) {
86
- evnt.preventDefault()
87
- return
88
- }
89
- if (internalData._keyCtx) {
90
- const type = 'body'
91
- const params: any = { source: 'table', type, $table: $xeTable, $grid: $xeGrid, $gantt: $xeGantt, keyboard: true, columns: visibleColumn.slice(0), $event: evnt }
92
- // 如果开启单元格区域
93
- if (mouseConfig && mouseOpts.area) {
94
- const activeArea = $xeTable.getActiveCellArea()
95
- if (activeArea && activeArea.row && activeArea.column) {
96
- params.row = activeArea.row
97
- params.column = activeArea.column
98
- $xeTable.handleOpenMenuEvent(evnt, type, params)
99
- return
100
- }
101
- } else if (mouseConfig && mouseOpts.selected) {
102
- // 如果启用键盘导航且已选中单元格
103
- if (selected.row && selected.column) {
104
- params.row = selected.row
105
- params.column = selected.column
106
- $xeTable.handleOpenMenuEvent(evnt, type, params)
107
- return
108
- }
109
- }
110
- }
111
- // 分别匹配表尾、内容、表尾的快捷菜单
112
- for (let index = 0; index < layoutList.length; index++) {
113
- const layout = layoutList[index] as 'header' | 'body' | 'footer'
114
- const columnTargetNode = getEventTargetNode(evnt, el, `vxe-${layout}--column`, (target: any) => {
115
- // target=td|th,直接向上找 table 去匹配即可
116
- return target.parentNode.parentNode.parentNode.getAttribute('xid') === xID
117
- })
118
- const params: any = { source: 'table', type: layout, $table: $xeTable, $grid: $xeGrid, $gantt: $xeGantt, columns: visibleColumn.slice(0), $event: evnt }
119
- if (columnTargetNode.flag) {
120
- const cell = columnTargetNode.targetElem
121
- const columnNodeRest = $xeTable.getColumnNode(cell)
122
- const column = columnNodeRest ? columnNodeRest.item : null
123
- let typePrefix = `${layout}-`
124
- if (column) {
125
- Object.assign(params, { column, columnIndex: $xeTable.getColumnIndex(column), cell })
126
- }
127
- if (layout === 'body') {
128
- const rowNodeRest = $xeTable.getRowNode(cell.parentNode)
129
- const row = rowNodeRest ? rowNodeRest.item : null
130
- typePrefix = ''
131
- if (row) {
132
- params.row = row
133
- params.rowIndex = $xeTable.getRowIndex(row)
134
- }
135
- }
136
- const eventType = `${typePrefix}cell-menu` as 'cell-menu' | 'header-cell-menu' | 'footer-cell-menu'
137
- $xeTable.handleOpenMenuEvent(evnt, layout, params)
138
- // 在 v4 中废弃事件 cell-context-menu、header-cell-context-menu、footer-cell-context-menu
139
- if ($xeTable.$listeners[`${typePrefix}cell-context-menu`]) {
140
- warnLog('vxe.error.delEvent', [`${typePrefix}cell-context-menu`, `${typePrefix}cell-menu`])
141
- $xeTable.dispatchEvent(`${typePrefix}cell-context-menu` as any, params, evnt)
142
- } else {
143
- $xeTable.dispatchEvent(eventType, params, evnt)
144
- }
145
- return
146
- } else if (getEventTargetNode(evnt, el, `vxe-table--${layout}-wrapper`, target => target.getAttribute('xid') === xID).flag || (layout === 'body' && getEventTargetNode(evnt, el, 'vxe-table--empty-place-wrapper', target => target.getAttribute('xid') === xID).flag)) {
147
- if (menuOpts.trigger === 'cell') {
148
- evnt.preventDefault()
149
- } else {
150
- $xeTable.handleOpenMenuEvent(evnt, layout, params)
151
- }
152
- return
153
- }
154
- }
155
- }
156
- if (tableFilter && !getEventTargetNode(evnt, (tableFilter as any).$el).flag) {
157
- $xeTable.closeFilter()
158
- }
159
- $xeTable.closeMenu()
160
- },
161
- /**
162
- * 显示快捷菜单
163
- */
164
- handleOpenMenuEvent (evnt: any, type: 'header' | 'body' | 'footer', params: any) {
165
- const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
166
- const $xeGrid = $xeTable.$xeGrid
167
- const $xeGantt = $xeTable.$xeGantt
168
- const $xeGGWrapper = $xeGrid || $xeGantt
169
- const reactData = $xeTable as unknown as TableReactData
170
- const internalData = $xeTable as unknown as TableInternalData
171
-
172
- const { ctxMenuStore } = reactData
173
- const isContentMenu = $xeTable.computeIsContentMenu
174
- const menuOpts = $xeTable.computeMenuOpts
175
- const config = menuOpts[type]
176
- const { zIndex, transfer, visibleMethod } = menuOpts
177
- if (config) {
178
- const { options, disabled } = config
179
- if (disabled) {
180
- evnt.preventDefault()
181
- } else if (isContentMenu && options && options.length) {
182
- params.options = options
183
- $xeTable.preventEvent(evnt, 'event.showMenu', params, () => {
184
- if (!visibleMethod || visibleMethod(params)) {
185
- evnt.preventDefault()
186
- $xeTable.updateZindex()
187
- const el = $xeGGWrapper ? $xeGGWrapper.$refs.refElem as HTMLDivElement : $xeTable.$refs.refElem as HTMLDivElement
188
- const tableRect = el.getBoundingClientRect()
189
- const { scrollTop, scrollLeft, visibleHeight, visibleWidth } = getDomNode()
190
-
191
- let top = evnt.clientY - tableRect.y
192
- let left = evnt.clientX - tableRect.x
193
- if (transfer) {
194
- top = evnt.clientY + scrollTop
195
- left = evnt.clientX + scrollLeft
196
- }
197
-
198
- const handleVisible = () => {
199
- internalData._currMenuParams = params
200
- Object.assign(ctxMenuStore, {
201
- visible: true,
202
- list: options,
203
- selected: null,
204
- selectChild: null,
205
- showChild: false,
206
- style: {
207
- zIndex: zIndex || internalData.tZindex,
208
- top: `${top}px`,
209
- left: `${left}px`
210
- }
211
- })
212
- $xeTable.$nextTick(() => {
213
- const tableMenu = $xeTable.$refs.refTableMenu
214
- const ctxElem = (tableMenu as any).$el
215
- const clientHeight = ctxElem.clientHeight
216
- const clientWidth = ctxElem.clientWidth
217
- const { boundingTop, boundingLeft } = getAbsolutePos(ctxElem)
218
- const offsetTop = boundingTop + clientHeight - visibleHeight
219
- const offsetLeft = boundingLeft + clientWidth - visibleWidth
220
- if (offsetTop > -10) {
221
- ctxMenuStore.style.top = `${Math.max(scrollTop + 2, top - clientHeight - 2)}px`
222
- }
223
- if (offsetLeft > -10) {
224
- ctxMenuStore.style.left = `${Math.max(scrollLeft + 2, left - clientWidth - 2)}px`
225
- }
226
- })
227
- }
228
- const { keyboard, row, column } = params
229
- if (keyboard && row && column) {
230
- $xeTable.scrollToRow(row, column).then(() => {
231
- const cell = $xeTable.getCellElement(row, column)
232
- if (cell) {
233
- const { boundingTop, boundingLeft } = getAbsolutePos(cell)
234
- top = boundingTop + scrollTop + Math.floor(cell.offsetHeight / 2)
235
- left = boundingLeft + scrollLeft + Math.floor(cell.offsetWidth / 2)
236
- }
237
- handleVisible()
238
- })
239
- } else {
240
- handleVisible()
241
- }
242
- } else {
243
- $xeTable.closeMenu()
244
- }
245
- })
246
- }
247
- }
248
- $xeTable.closeFilter()
249
- },
250
- ctxMenuMouseoverEvent (evnt: Event, item: any, child: any) {
251
- const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
252
- const reactData = $xeTable as unknown as TableReactData
253
-
254
- const menuElem = evnt.currentTarget as HTMLDivElement
255
- const { ctxMenuStore } = reactData
256
- evnt.preventDefault()
257
- evnt.stopPropagation()
258
- ctxMenuStore.selected = item
259
- ctxMenuStore.selectChild = child
260
- if (!child) {
261
- ctxMenuStore.showChild = hasChildrenList(item)
262
- if (ctxMenuStore.showChild) {
263
- $xeTable.$nextTick(() => {
264
- const childWrapperElem = menuElem.nextElementSibling as HTMLDivElement
265
- if (childWrapperElem) {
266
- const { boundingTop, boundingLeft, visibleHeight, visibleWidth } = getAbsolutePos(menuElem)
267
- const posTop = boundingTop + menuElem.offsetHeight
268
- const posLeft = boundingLeft + menuElem.offsetWidth
269
- let left = ''
270
- let right = ''
271
- // 是否超出右侧
272
- if (posLeft + childWrapperElem.offsetWidth > visibleWidth - 10) {
273
- left = 'auto'
274
- right = `${menuElem.offsetWidth}px`
275
- }
276
- // 是否超出底部
277
- let top = ''
278
- let bottom = ''
279
- if (posTop + childWrapperElem.offsetHeight > visibleHeight - 10) {
280
- top = 'auto'
281
- bottom = '0'
282
- }
283
- childWrapperElem.style.left = left
284
- childWrapperElem.style.right = right
285
- childWrapperElem.style.top = top
286
- childWrapperElem.style.bottom = bottom
287
- }
288
- })
289
- }
290
- }
291
- },
292
- ctxMenuMouseoutEvent (evnt: Event, item: VxeTableDefines.MenuFirstOption | VxeTableDefines.MenuChildOption) {
293
- const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
294
- const reactData = $xeTable as unknown as TableReactData
295
-
296
- const { ctxMenuStore } = reactData
297
- if (!item.children) {
298
- ctxMenuStore.selected = null
299
- }
300
- ctxMenuStore.selectChild = null
301
- },
302
- /**
303
- * 快捷菜单点击事件
304
- */
305
- ctxMenuLinkEvent (evnt: Event, menu: VxeTableDefines.MenuFirstOption | VxeTableDefines.MenuChildOption) {
306
- const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
307
- const $xeGrid = $xeTable.$xeGrid
308
- const $xeGantt = $xeTable.$xeGantt
309
- const internalData = $xeTable as unknown as TableInternalData
310
-
311
- // 如果一级菜单有配置 code 则允许点击,否则不能点击
312
- if (!menu.loading && !menu.disabled && (menu.code || !menu.children || !menu.children.length)) {
313
- const gMenuOpts = menus.get(menu.code)
314
- const params = Object.assign({}, internalData._currMenuParams, { menu, $table: $xeTable, $grid: $xeGrid, $gantt: $xeGantt, $event: evnt })
315
- if (gMenuOpts && gMenuOpts.menuMethod) {
316
- gMenuOpts.menuMethod(params, evnt)
317
- }
318
- // 在 v4 中废弃事件 context-menu-click
319
- if ($xeTable.$listeners['context-menu-click']) {
320
- warnLog('vxe.error.delEvent', ['context-menu-click', 'menu-click'])
321
- $xeTable.dispatchEvent('context-menu-click' as any, params, evnt)
322
- } else {
323
- $xeTable.dispatchEvent('menu-click', params, evnt)
324
- }
325
- $xeTable.closeMenu()
326
- }
327
- }
328
- }
329
- }
1
+ import XEUtils from 'xe-utils'
2
+ import { VxeUI } from '../../../ui'
3
+ import { getDomNode, getAbsolutePos, getEventTargetNode } from '../../../ui/src/dom'
4
+ import { isEnableConf, hasChildrenList } from '../../../ui/src/utils'
5
+ import { warnLog } from '../../../ui/src/log'
6
+
7
+ import type { VxeTableConstructor, VxeTablePrivateMethods, TableInternalData, TableReactData, VxeTableDefines } from '../../../../types'
8
+
9
+ const { menus, globalEvents, GLOBAL_EVENT_KEYS } = VxeUI
10
+
11
+ export default {
12
+ methods: {
13
+ /**
14
+ * 关闭快捷菜单
15
+ */
16
+ _closeMenu () {
17
+ const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
18
+ const reactData = $xeTable as unknown as TableReactData
19
+
20
+ Object.assign(reactData.ctxMenuStore, {
21
+ visible: false,
22
+ selected: null,
23
+ selectChild: null,
24
+ showChild: false
25
+ })
26
+ return $xeTable.$nextTick()
27
+ },
28
+ // 处理菜单的移动
29
+ moveCtxMenu (evnt: KeyboardEvent, ctxMenuStore: any, property: 'selectChild' | 'selected', hasOper: boolean, operRest: any, menuList: any[]) {
30
+ const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
31
+
32
+ let selectItem
33
+ const selectIndex = XEUtils.findIndexOf(menuList, item => ctxMenuStore[property] === item)
34
+ if (hasOper) {
35
+ if (operRest && hasChildrenList(ctxMenuStore.selected)) {
36
+ ctxMenuStore.showChild = true
37
+ } else {
38
+ ctxMenuStore.showChild = false
39
+ ctxMenuStore.selectChild = null
40
+ }
41
+ } else if (globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.ARROW_UP)) {
42
+ for (let len = selectIndex - 1; len >= 0; len--) {
43
+ if (menuList[len].visible !== false) {
44
+ selectItem = menuList[len]
45
+ break
46
+ }
47
+ }
48
+ ctxMenuStore[property] = selectItem || menuList[menuList.length - 1]
49
+ } else if (globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.ARROW_DOWN)) {
50
+ for (let index = selectIndex + 1; index < menuList.length; index++) {
51
+ if (menuList[index].visible !== false) {
52
+ selectItem = menuList[index]
53
+ break
54
+ }
55
+ }
56
+ ctxMenuStore[property] = selectItem || menuList[0]
57
+ } else if (ctxMenuStore[property] && (globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.ENTER) || globalEvents.hasKey(evnt, GLOBAL_EVENT_KEYS.SPACEBAR))) {
58
+ $xeTable.ctxMenuLinkEvent(evnt, ctxMenuStore[property])
59
+ }
60
+ },
61
+ /**
62
+ * 快捷菜单事件处理
63
+ */
64
+ handleGlobalContextmenuEvent (evnt: any) {
65
+ const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
66
+ const $xeGrid = $xeTable.$xeGrid
67
+ const $xeGantt = $xeTable.$xeGantt
68
+ const props = $xeTable
69
+ const reactData = $xeTable as unknown as TableReactData
70
+ const internalData = $xeTable as unknown as TableInternalData
71
+
72
+ const { xID } = $xeTable
73
+
74
+ const { mouseConfig, menuConfig } = props
75
+ const { editStore, ctxMenuStore } = reactData
76
+ const { visibleColumn } = internalData
77
+ const tableFilter = $xeTable.$refs.refTableFilter
78
+ const tableMenu = $xeTable.$refs.refTableMenu
79
+ const mouseOpts = $xeTable.computeMouseOpts
80
+ const menuOpts = $xeTable.computeMenuOpts
81
+ const el = $xeTable.$refs.refElem as HTMLDivElement
82
+ const { selected } = editStore
83
+ const layoutList = ['header', 'body', 'footer']
84
+ if (isEnableConf(menuConfig)) {
85
+ if (ctxMenuStore.visible && tableMenu && getEventTargetNode(evnt, (tableMenu as any).$el).flag) {
86
+ evnt.preventDefault()
87
+ return
88
+ }
89
+ if (internalData._keyCtx) {
90
+ const type = 'body'
91
+ const params: any = { source: 'table', type, $table: $xeTable, $grid: $xeGrid, $gantt: $xeGantt, keyboard: true, columns: visibleColumn.slice(0), $event: evnt }
92
+ // 如果开启单元格区域
93
+ if (mouseConfig && mouseOpts.area) {
94
+ const activeArea = $xeTable.getActiveCellArea()
95
+ if (activeArea && activeArea.row && activeArea.column) {
96
+ params.row = activeArea.row
97
+ params.column = activeArea.column
98
+ $xeTable.handleOpenMenuEvent(evnt, type, params)
99
+ return
100
+ }
101
+ } else if (mouseConfig && mouseOpts.selected) {
102
+ // 如果启用键盘导航且已选中单元格
103
+ if (selected.row && selected.column) {
104
+ params.row = selected.row
105
+ params.column = selected.column
106
+ $xeTable.handleOpenMenuEvent(evnt, type, params)
107
+ return
108
+ }
109
+ }
110
+ }
111
+ // 分别匹配表尾、内容、表尾的快捷菜单
112
+ for (let index = 0; index < layoutList.length; index++) {
113
+ const layout = layoutList[index] as 'header' | 'body' | 'footer'
114
+ const columnTargetNode = getEventTargetNode(evnt, el, `vxe-${layout}--column`, (target: any) => {
115
+ // target=td|th,直接向上找 table 去匹配即可
116
+ return target.parentNode.parentNode.parentNode.getAttribute('xid') === xID
117
+ })
118
+ const params: any = { source: 'table', type: layout, $table: $xeTable, $grid: $xeGrid, $gantt: $xeGantt, columns: visibleColumn.slice(0), $event: evnt }
119
+ if (columnTargetNode.flag) {
120
+ const cell = columnTargetNode.targetElem
121
+ const columnNodeRest = $xeTable.getColumnNode(cell)
122
+ const column = columnNodeRest ? columnNodeRest.item : null
123
+ let typePrefix = `${layout}-`
124
+ if (column) {
125
+ Object.assign(params, { column, columnIndex: $xeTable.getColumnIndex(column), cell })
126
+ }
127
+ if (layout === 'body') {
128
+ const rowNodeRest = $xeTable.getRowNode(cell.parentNode)
129
+ const row = rowNodeRest ? rowNodeRest.item : null
130
+ typePrefix = ''
131
+ if (row) {
132
+ params.row = row
133
+ params.rowIndex = $xeTable.getRowIndex(row)
134
+ }
135
+ }
136
+ const eventType = `${typePrefix}cell-menu` as 'cell-menu' | 'header-cell-menu' | 'footer-cell-menu'
137
+ $xeTable.handleOpenMenuEvent(evnt, layout, params)
138
+ // 在 v4 中废弃事件 cell-context-menu、header-cell-context-menu、footer-cell-context-menu
139
+ if ($xeTable.$listeners[`${typePrefix}cell-context-menu`]) {
140
+ warnLog('vxe.error.delEvent', [`${typePrefix}cell-context-menu`, `${typePrefix}cell-menu`])
141
+ $xeTable.dispatchEvent(`${typePrefix}cell-context-menu` as any, params, evnt)
142
+ } else {
143
+ $xeTable.dispatchEvent(eventType, params, evnt)
144
+ }
145
+ return
146
+ } else if (getEventTargetNode(evnt, el, `vxe-table--${layout}-wrapper`, target => target.getAttribute('xid') === xID).flag || (layout === 'body' && getEventTargetNode(evnt, el, 'vxe-table--empty-place-wrapper', target => target.getAttribute('xid') === xID).flag)) {
147
+ if (menuOpts.trigger === 'cell') {
148
+ evnt.preventDefault()
149
+ } else {
150
+ $xeTable.handleOpenMenuEvent(evnt, layout, params)
151
+ }
152
+ return
153
+ }
154
+ }
155
+ }
156
+ if (tableFilter && !getEventTargetNode(evnt, (tableFilter as any).$el).flag) {
157
+ $xeTable.closeFilter()
158
+ }
159
+ $xeTable.closeMenu()
160
+ },
161
+ /**
162
+ * 显示快捷菜单
163
+ */
164
+ handleOpenMenuEvent (evnt: any, type: 'header' | 'body' | 'footer', params: any) {
165
+ const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
166
+ const $xeGrid = $xeTable.$xeGrid
167
+ const $xeGantt = $xeTable.$xeGantt
168
+ const $xeGGWrapper = $xeGrid || $xeGantt
169
+ const reactData = $xeTable as unknown as TableReactData
170
+ const internalData = $xeTable as unknown as TableInternalData
171
+
172
+ const { ctxMenuStore } = reactData
173
+ const isContentMenu = $xeTable.computeIsContentMenu
174
+ const menuOpts = $xeTable.computeMenuOpts
175
+ const config = menuOpts[type]
176
+ const { zIndex, transfer, visibleMethod } = menuOpts
177
+ if (config) {
178
+ const { options, disabled } = config
179
+ if (disabled) {
180
+ evnt.preventDefault()
181
+ } else if (isContentMenu && options && options.length) {
182
+ params.options = options
183
+ $xeTable.preventEvent(evnt, 'event.showMenu', params, () => {
184
+ if (!visibleMethod || visibleMethod(params)) {
185
+ evnt.preventDefault()
186
+ $xeTable.updateZindex()
187
+ const el = $xeGGWrapper ? $xeGGWrapper.$refs.refElem as HTMLDivElement : $xeTable.$refs.refElem as HTMLDivElement
188
+ const tableRect = el.getBoundingClientRect()
189
+ const { scrollTop, scrollLeft, visibleHeight, visibleWidth } = getDomNode()
190
+
191
+ let top = evnt.clientY - tableRect.y
192
+ let left = evnt.clientX - tableRect.x
193
+ if (transfer) {
194
+ top = evnt.clientY + scrollTop
195
+ left = evnt.clientX + scrollLeft
196
+ }
197
+
198
+ const handleVisible = () => {
199
+ internalData._currMenuParams = params
200
+ Object.assign(ctxMenuStore, {
201
+ visible: true,
202
+ list: options,
203
+ selected: null,
204
+ selectChild: null,
205
+ showChild: false,
206
+ style: {
207
+ zIndex: zIndex || internalData.tZindex,
208
+ top: `${top}px`,
209
+ left: `${left}px`
210
+ }
211
+ })
212
+ $xeTable.$nextTick(() => {
213
+ const tableMenu = $xeTable.$refs.refTableMenu
214
+ const ctxElem = (tableMenu as any).$el
215
+ const clientHeight = ctxElem.clientHeight
216
+ const clientWidth = ctxElem.clientWidth
217
+ const { boundingTop, boundingLeft } = getAbsolutePos(ctxElem)
218
+ const offsetTop = boundingTop + clientHeight - visibleHeight
219
+ const offsetLeft = boundingLeft + clientWidth - visibleWidth
220
+ if (offsetTop > -10) {
221
+ ctxMenuStore.style.top = `${Math.max(scrollTop + 2, top - clientHeight - 2)}px`
222
+ }
223
+ if (offsetLeft > -10) {
224
+ ctxMenuStore.style.left = `${Math.max(scrollLeft + 2, left - clientWidth - 2)}px`
225
+ }
226
+ })
227
+ }
228
+ const { keyboard, row, column } = params
229
+ if (keyboard && row && column) {
230
+ $xeTable.scrollToRow(row, column).then(() => {
231
+ const cell = $xeTable.getCellElement(row, column)
232
+ if (cell) {
233
+ const { boundingTop, boundingLeft } = getAbsolutePos(cell)
234
+ top = boundingTop + scrollTop + Math.floor(cell.offsetHeight / 2)
235
+ left = boundingLeft + scrollLeft + Math.floor(cell.offsetWidth / 2)
236
+ }
237
+ handleVisible()
238
+ })
239
+ } else {
240
+ handleVisible()
241
+ }
242
+ } else {
243
+ $xeTable.closeMenu()
244
+ }
245
+ })
246
+ }
247
+ }
248
+ $xeTable.closeFilter()
249
+ },
250
+ ctxMenuMouseoverEvent (evnt: Event, item: any, child: any) {
251
+ const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
252
+ const reactData = $xeTable as unknown as TableReactData
253
+
254
+ const menuElem = evnt.currentTarget as HTMLDivElement
255
+ const { ctxMenuStore } = reactData
256
+ evnt.preventDefault()
257
+ evnt.stopPropagation()
258
+ ctxMenuStore.selected = item
259
+ ctxMenuStore.selectChild = child
260
+ if (!child) {
261
+ ctxMenuStore.showChild = hasChildrenList(item)
262
+ if (ctxMenuStore.showChild) {
263
+ $xeTable.$nextTick(() => {
264
+ const childWrapperElem = menuElem.nextElementSibling as HTMLDivElement
265
+ if (childWrapperElem) {
266
+ const { boundingTop, boundingLeft, visibleHeight, visibleWidth } = getAbsolutePos(menuElem)
267
+ const posTop = boundingTop + menuElem.offsetHeight
268
+ const posLeft = boundingLeft + menuElem.offsetWidth
269
+ let left = ''
270
+ let right = ''
271
+ // 是否超出右侧
272
+ if (posLeft + childWrapperElem.offsetWidth > visibleWidth - 10) {
273
+ left = 'auto'
274
+ right = `${menuElem.offsetWidth}px`
275
+ }
276
+ // 是否超出底部
277
+ let top = ''
278
+ let bottom = ''
279
+ if (posTop + childWrapperElem.offsetHeight > visibleHeight - 10) {
280
+ top = 'auto'
281
+ bottom = '0'
282
+ }
283
+ childWrapperElem.style.left = left
284
+ childWrapperElem.style.right = right
285
+ childWrapperElem.style.top = top
286
+ childWrapperElem.style.bottom = bottom
287
+ }
288
+ })
289
+ }
290
+ }
291
+ },
292
+ ctxMenuMouseoutEvent (evnt: Event, item: VxeTableDefines.MenuFirstOption | VxeTableDefines.MenuChildOption) {
293
+ const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
294
+ const reactData = $xeTable as unknown as TableReactData
295
+
296
+ const { ctxMenuStore } = reactData
297
+ if (!item.children) {
298
+ ctxMenuStore.selected = null
299
+ }
300
+ ctxMenuStore.selectChild = null
301
+ },
302
+ /**
303
+ * 快捷菜单点击事件
304
+ */
305
+ ctxMenuLinkEvent (evnt: Event, menu: VxeTableDefines.MenuFirstOption | VxeTableDefines.MenuChildOption) {
306
+ const $xeTable = this as unknown as VxeTableConstructor & VxeTablePrivateMethods
307
+ const $xeGrid = $xeTable.$xeGrid
308
+ const $xeGantt = $xeTable.$xeGantt
309
+ const internalData = $xeTable as unknown as TableInternalData
310
+
311
+ // 如果一级菜单有配置 code 则允许点击,否则不能点击
312
+ if (!menu.loading && !menu.disabled && (menu.code || !menu.children || !menu.children.length)) {
313
+ const gMenuOpts = menus.get(menu.code)
314
+ const params = Object.assign({}, internalData._currMenuParams, { menu, $table: $xeTable, $grid: $xeGrid, $gantt: $xeGantt, $event: evnt })
315
+ if (gMenuOpts && gMenuOpts.menuMethod) {
316
+ gMenuOpts.menuMethod(params, evnt)
317
+ }
318
+ // 在 v4 中废弃事件 context-menu-click
319
+ if ($xeTable.$listeners['context-menu-click']) {
320
+ warnLog('vxe.error.delEvent', ['context-menu-click', 'menu-click'])
321
+ $xeTable.dispatchEvent('context-menu-click' as any, params, evnt)
322
+ } else {
323
+ $xeTable.dispatchEvent('menu-click', params, evnt)
324
+ }
325
+ $xeTable.closeMenu()
326
+ }
327
+ }
328
+ }
329
+ }