@electerm/electerm-react 1.40.20 → 1.50.31

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 (104) hide show
  1. package/client/common/constants.js +57 -7
  2. package/client/common/new-terminal.js +2 -2
  3. package/client/components/auth/login.jsx +34 -57
  4. package/client/components/batch-op/batch-op.jsx +12 -11
  5. package/client/components/bookmark-form/index.jsx +2 -2
  6. package/client/components/bookmark-form/ssh-form.jsx +4 -1
  7. package/client/components/bookmark-form/tree-delete.jsx +5 -5
  8. package/client/components/context-menu/boomarks.jsx +8 -12
  9. package/client/components/context-menu/context-menu.jsx +10 -10
  10. package/client/components/context-menu/history.jsx +21 -24
  11. package/client/components/context-menu/menu-btn.jsx +11 -11
  12. package/client/components/context-menu/tabs.jsx +15 -19
  13. package/client/components/context-menu/zoom.jsx +25 -29
  14. package/client/components/footer/footer-entry.jsx +56 -56
  15. package/client/components/icons/split-icons.jsx +77 -0
  16. package/client/components/layout/layout-alg.js +260 -0
  17. package/client/components/layout/layout-item.jsx +94 -0
  18. package/client/components/layout/layout.jsx +167 -0
  19. package/client/components/layout/layout.styl +8 -0
  20. package/client/components/layout/layouts.jsx +72 -0
  21. package/client/components/layout/session-size-alg.js +31 -0
  22. package/client/components/main/custom-css.jsx +1 -1
  23. package/client/components/main/main.jsx +184 -110
  24. package/client/components/main/ui-theme.jsx +1 -1
  25. package/client/components/main/wrapper.styl +2 -4
  26. package/client/components/profile/profile-list.jsx +1 -3
  27. package/client/components/profile/profile-transport-mod.jsx +1 -1
  28. package/client/components/profile/profile-transport.jsx +6 -9
  29. package/client/components/quick-commands/quick-command-transport.jsx +6 -9
  30. package/client/components/quick-commands/quick-commands-box.jsx +144 -153
  31. package/client/components/quick-commands/quick-commands-select.jsx +10 -3
  32. package/client/components/rdp/rdp-session.jsx +3 -23
  33. package/client/components/rdp/resolution-edit.jsx +40 -42
  34. package/client/components/session/session.jsx +63 -328
  35. package/client/components/session/session.styl +1 -5
  36. package/client/components/session/sessions.jsx +140 -111
  37. package/client/components/setting-panel/bookmark-tree-list.jsx +1 -1
  38. package/client/components/setting-panel/setting-common.jsx +6 -4
  39. package/client/components/setting-panel/setting-modal.jsx +31 -31
  40. package/client/components/setting-panel/start-session-select.jsx +4 -4
  41. package/client/components/setting-panel/tab-settings.jsx +27 -5
  42. package/client/components/setting-sync/data-import.jsx +36 -39
  43. package/client/components/setting-sync/setting-sync-form.jsx +10 -10
  44. package/client/components/setting-sync/setting-sync.jsx +50 -52
  45. package/client/components/sftp/address-bookmark.jsx +57 -58
  46. package/client/components/sftp/confirm-modal-store.jsx +34 -40
  47. package/client/components/sftp/file-item.jsx +14 -3
  48. package/client/components/sftp/file-mode-modal.jsx +3 -0
  49. package/client/components/sftp/list-table-ui.jsx +4 -4
  50. package/client/components/sftp/sftp-entry.jsx +2 -2
  51. package/client/components/sftp/transfer-conflict-store.jsx +13 -17
  52. package/client/components/sftp/transport-action-store.jsx +38 -31
  53. package/client/components/sftp/transports-action-store.jsx +3 -3
  54. package/client/components/sftp/transports-ui-store.jsx +18 -23
  55. package/client/components/shortcuts/shortcut-handler.js +1 -0
  56. package/client/components/shortcuts/shortcuts-defaults.js +5 -5
  57. package/client/components/shortcuts/shortcuts.jsx +9 -12
  58. package/client/components/side-panel-r/right-side-panel.styl +40 -0
  59. package/client/components/side-panel-r/side-panel-r.jsx +102 -0
  60. package/client/components/sidebar/bookmark-select.jsx +40 -40
  61. package/client/components/sidebar/bookmark.jsx +63 -65
  62. package/client/components/sidebar/history.jsx +53 -50
  63. package/client/components/sidebar/index.jsx +195 -184
  64. package/client/components/sidebar/info-modal.jsx +202 -202
  65. package/client/components/sidebar/sidebar.styl +8 -2
  66. package/client/components/sidebar/transfer-history-modal.jsx +95 -100
  67. package/client/components/sidebar/transfer-list-control.jsx +2 -2
  68. package/client/components/sidebar/transfer-list.jsx +45 -42
  69. package/client/components/sidebar/transfer-modal.jsx +49 -52
  70. package/client/components/sidebar/transport-ui.jsx +1 -1
  71. package/client/components/tabs/index.jsx +261 -49
  72. package/client/components/tabs/tab.jsx +48 -66
  73. package/client/components/tabs/tabs.styl +6 -1
  74. package/client/components/tabs/window-control.jsx +46 -48
  75. package/client/components/terminal/attach-addon-custom.js +1 -1
  76. package/client/components/terminal/index.jsx +111 -113
  77. package/client/components/terminal/term-search.jsx +26 -24
  78. package/client/components/terminal-info/run-cmd.jsx +0 -25
  79. package/client/components/terminal-info/terminal-info.jsx +60 -0
  80. package/client/components/terminal-info/terminal-info.styl +1 -1
  81. package/client/components/tree-list/bookmark-transport.jsx +8 -9
  82. package/client/components/tree-list/tree-list.jsx +36 -26
  83. package/client/components/vnc/vnc-session.jsx +1 -6
  84. package/client/components/web/address-bar.jsx +50 -0
  85. package/client/components/web/web-session.jsx +32 -10
  86. package/client/entry/index.jsx +5 -6
  87. package/client/store/common.js +1 -1
  88. package/client/store/db-upgrade.js +1 -1
  89. package/client/store/event.js +2 -2
  90. package/client/store/index.js +21 -32
  91. package/client/store/init-state.js +15 -3
  92. package/client/store/load-data.js +1 -1
  93. package/client/store/quick-command.js +4 -4
  94. package/client/store/session.js +1 -1
  95. package/client/store/setting.js +10 -6
  96. package/client/store/system-menu.js +1 -10
  97. package/client/store/tab.js +91 -1
  98. package/client/store/transfer-list.js +5 -6
  99. package/client/store/watch.js +11 -6
  100. package/package.json +1 -1
  101. package/client/components/common/react-subx.jsx +0 -1
  102. package/client/components/common/resize-wrap.jsx +0 -222
  103. package/client/components/common/resize-wrap.styl +0 -9
  104. package/client/components/terminal-info/content.jsx +0 -152
@@ -134,7 +134,6 @@ class Store {
134
134
  get inActiveTerminal () {
135
135
  const { store } = window
136
136
  return !store.showModal &&
137
- store.termFocused &&
138
137
  store.currentTab &&
139
138
  (
140
139
  store.currentTab.pane === paneMap.ssh ||
@@ -211,14 +210,6 @@ class Store {
211
210
  ]
212
211
  }
213
212
 
214
- get config () {
215
- return JSON.parse(window.store._config || '{}')
216
- }
217
-
218
- get sftpSortSetting () {
219
- return JSON.parse(window.store._sftpSortSetting)
220
- }
221
-
222
213
  get onOperation () {
223
214
  const {
224
215
  store
@@ -229,26 +220,6 @@ class Store {
229
220
  store.showFileModal
230
221
  }
231
222
 
232
- get topMenuHeight () {
233
- return 0
234
- }
235
-
236
- get langs () {
237
- return JSON.parse(window.store._langs)
238
- }
239
-
240
- get upgradeInfo () {
241
- return JSON.parse(window.store._upgradeInfo)
242
- }
243
-
244
- get transferToConfirm () {
245
- return JSON.parse(window.store._transferToConfirm)
246
- }
247
-
248
- get settingItem () {
249
- return JSON.parse(window.store._settingItem)
250
- }
251
-
252
223
  get uiThemeConfig () {
253
224
  const { store } = window
254
225
  const themeConf = store.getUiThemeConfig()
@@ -293,7 +264,7 @@ class Store {
293
264
  }
294
265
  }
295
266
 
296
- const getterProps = [
267
+ const arrGetterProps = [
297
268
  'expandedKeys',
298
269
  'checkedKeys',
299
270
  'addressBookmarks',
@@ -314,7 +285,7 @@ const getterProps = [
314
285
  'resolutions'
315
286
  ]
316
287
 
317
- for (const prop of getterProps) {
288
+ for (const prop of arrGetterProps) {
318
289
  Object.defineProperty(Store.prototype, prop, {
319
290
  get: function () {
320
291
  return JSON.parse(window.store[`_${prop}`] || '[]').filter(d => d)
@@ -322,6 +293,24 @@ for (const prop of getterProps) {
322
293
  })
323
294
  }
324
295
 
296
+ const getterProps = [
297
+ 'langs',
298
+ 'config',
299
+ 'sftpSortSetting',
300
+ 'upgradeInfo',
301
+ 'transferToConfirm',
302
+ 'terminalInfoProps',
303
+ 'settingItem'
304
+ ]
305
+
306
+ for (const prop of getterProps) {
307
+ Object.defineProperty(Store.prototype, prop, {
308
+ get: function () {
309
+ return JSON.parse(window.store[`_${prop}`] || '{}')
310
+ }
311
+ })
312
+ }
313
+
325
314
  loadDataExtend(Store)
326
315
  eventExtend(Store)
327
316
  dbUpgradeExtend(Store)
@@ -346,6 +335,6 @@ transferExtend(Store)
346
335
  addressBookmarkExtend(Store)
347
336
 
348
337
  export const StateStore = Store
349
- const store = manage(new Store())
338
+ const store = manage(new Store(), 1)
350
339
 
351
340
  export default store
@@ -19,7 +19,8 @@ import {
19
19
  rightSidebarWidthKey,
20
20
  dismissDelKeyTipLsKey,
21
21
  qmSortByFrequencyKey,
22
- resolutionsLsKey
22
+ resolutionsLsKey,
23
+ splitMap
23
24
  } from '../common/constants'
24
25
  import { buildDefaultThemes } from '../common/terminal-theme'
25
26
  import * as ls from '../common/safe-local-storage'
@@ -38,6 +39,7 @@ function getDefaultBookmarkGroups (bookmarks) {
38
39
  }
39
40
 
40
41
  export default () => {
42
+ const layout = ls.getItem('layout') || splitMap.c1
41
43
  return {
42
44
  // common
43
45
  wsInited: false,
@@ -46,7 +48,6 @@ export default () => {
46
48
  lastDataUpdateTime: 0,
47
49
  _tabs: '[]',
48
50
  currentTabId: '',
49
- termFocused: false,
50
51
  _history: '[]',
51
52
  _bookmarks: '[]',
52
53
  _profiles: '[]',
@@ -90,6 +91,18 @@ export default () => {
90
91
  direction: 'desc'
91
92
  }
92
93
  }),
94
+ layout,
95
+ prevLayout: layout,
96
+ resizeTrigger: 0,
97
+ currentLayoutBatch: 0,
98
+ currentTabId0: '',
99
+ currentTabId1: '',
100
+ currentTabId2: '',
101
+ currentTabId3: '',
102
+ _terminalInfoProps: '{}',
103
+ rightPanelVisible: false,
104
+ rightPanelPinned: false,
105
+ rightPanelWidth: parseInt(ls.getItem(rightSidebarWidthKey), 10) || 500,
93
106
 
94
107
  // for settings related
95
108
  _setting: '',
@@ -98,7 +111,6 @@ export default () => {
98
111
  autofocustrigger: Date.now(),
99
112
  bookmarkId: undefined,
100
113
  showModal: 0,
101
- activeTerminalId: '',
102
114
 
103
115
  // setting sync related
104
116
  isSyncingSetting: false,
@@ -6,7 +6,7 @@ import { dbNames, update, getData, fetchInitData, insert, remove } from '../comm
6
6
  import parseInt10 from '../common/parse-int10'
7
7
  import { infoTabs, statusMap, defaultEnvLang } from '../common/constants'
8
8
  import fs from '../common/fs'
9
- import generate from '../common/uid'
9
+ import generate from '../common/id-with-stamp'
10
10
  import defaultSettings from '../common/default-setting'
11
11
  import encodes from '../components/bookmark-form/encodes'
12
12
  import runIdle from '../common/run-idle'
@@ -12,6 +12,7 @@ import delay from '../common/wait'
12
12
  import generate from '../common/uid'
13
13
  import postMessage from '../common/post-msg'
14
14
  import * as ls from '../common/safe-local-storage'
15
+ import { debounce } from 'lodash-es'
15
16
 
16
17
  export default Store => {
17
18
  Store.prototype.setQuickCommands = function (list) {
@@ -33,16 +34,15 @@ export default Store => {
33
34
  }
34
35
 
35
36
  Store.prototype.runQuickCommand = function (cmd, inputOnly = false) {
36
- const { activeTerminalId } = window.store
37
37
  postMessage({
38
38
  action: terminalActions.quickCommand,
39
39
  cmd,
40
40
  inputOnly,
41
- activeSplitId: activeTerminalId
41
+ currentTabId: window.store.currentTabId
42
42
  })
43
43
  }
44
44
 
45
- Store.prototype.runQuickCommandItem = async (id) => {
45
+ Store.prototype.runQuickCommandItem = debounce(async (id) => {
46
46
  const {
47
47
  store
48
48
  } = window
@@ -73,7 +73,7 @@ export default Store => {
73
73
  clickCount: ((qm.clickCount || 0) + 1)
74
74
  })
75
75
  }
76
- }
76
+ }, 200)
77
77
 
78
78
  Store.prototype.setQmSortByFrequency = function (v) {
79
79
  window.store.qmSortByFrequency = v
@@ -11,7 +11,7 @@ export default Store => {
11
11
  postMsg({
12
12
  action: terminalActions.zoom,
13
13
  zoomValue: delta > 0 ? 1 : -1,
14
- activeSplitId: window.store.activeTerminalId
14
+ currentTabId: window.store.currentTabId
15
15
  })
16
16
  }, 500)
17
17
  }
@@ -79,8 +79,10 @@ export default Store => {
79
79
  ...copy(item),
80
80
  from: 'history',
81
81
  srcId: item.id,
82
- ...newTerm(true, true)
82
+ ...newTerm(true, true),
83
+ batch: window.openTabBatch ?? store.currentLayoutBatch
83
84
  })
85
+ delete window.openTabBatch
84
86
  }
85
87
 
86
88
  Store.prototype.onSelectBookmark = function (id) {
@@ -94,14 +96,16 @@ export default Store => {
94
96
  if (!item) {
95
97
  return
96
98
  }
97
-
98
99
  store.addTab({
99
100
  ...item,
100
101
  from: 'bookmarks',
101
102
  srcId: item.id,
102
- ...newTerm(true, true)
103
+ ...newTerm(true, true),
104
+ batch: window.openTabBatch ?? store.currentLayoutBatch
103
105
  })
104
106
 
107
+ delete window.openTabBatch
108
+
105
109
  if (store.config.disableSshHistory) {
106
110
  return
107
111
  }
@@ -117,8 +121,8 @@ export default Store => {
117
121
  } else {
118
122
  const historyItem = {
119
123
  ...item,
120
- id: generate(), // History item gets a unique id
121
- bookmarkId, // Store original bookmark id for future matching
124
+ id: generate(),
125
+ bookmarkId,
122
126
  count: 1,
123
127
  lastUse: Date.now()
124
128
  }
@@ -186,7 +190,7 @@ export default Store => {
186
190
 
187
191
  Store.prototype.openSettingModal = function () {
188
192
  const { store } = window
189
- if (store.isSencondInstance) {
193
+ if (store.isSecondInstance) {
190
194
  return message.warning(
191
195
  e('sencondInstanceTip')
192
196
  )
@@ -3,7 +3,7 @@
3
3
  */
4
4
 
5
5
  import { Modal } from 'antd'
6
- import { isFunction, isString } from 'lodash-es'
6
+ import { isString } from 'lodash-es'
7
7
  import getInitItem from '../common/init-setting-item'
8
8
  import {
9
9
  settingMap,
@@ -44,15 +44,6 @@ export default Store => {
44
44
  window.store.zoom()
45
45
  }
46
46
 
47
- Store.prototype.onCloseAbout = function (cb) {
48
- const { store } = window
49
- store.showInfoModal = false
50
- if (isFunction(cb)) {
51
- cb()
52
- }
53
- store.focus()
54
- }
55
-
56
47
  Store.prototype.openAbout = function (tab) {
57
48
  const { store } = window
58
49
  store.showInfoModal = true
@@ -4,9 +4,15 @@
4
4
 
5
5
  import { uniq, debounce, findIndex } from 'lodash-es'
6
6
  import {
7
- tabActions
7
+ tabActions,
8
+ splitConfig,
9
+ statusMap,
10
+ paneMap
8
11
  } from '../common/constants'
9
12
  import postMsg from '../common/post-msg'
13
+ import * as ls from '../common/safe-local-storage'
14
+ import deepCopy from 'json-deep-copy'
15
+ import generate from '../common/id-with-stamp'
10
16
 
11
17
  export default Store => {
12
18
  Store.prototype.updateTabsStatus = function () {
@@ -19,6 +25,22 @@ export default Store => {
19
25
  })
20
26
  }
21
27
 
28
+ Store.prototype.updateStoreTabs = function (tabs0, batch0) {
29
+ if (!tabs0.length && batch0 !== undefined) {
30
+ const tabs = window.store.getTabs().filter(t => t.batch !== batch0)
31
+ window.store.setTabs(tabs)
32
+ return true
33
+ }
34
+ if (!tabs0.length) {
35
+ return false
36
+ }
37
+ const { batch } = tabs0[0]
38
+ const tabs = window.store.getTabs()
39
+ .filter(t => t.batch !== batch)
40
+ .concat(deepCopy(tabs0))
41
+ window.store.setTabs(tabs)
42
+ }
43
+
22
44
  Store.prototype.getTabs = function () {
23
45
  return window.store.getItems('tabs')
24
46
  }
@@ -27,6 +49,10 @@ export default Store => {
27
49
  return window.store.setItems('tabs', list)
28
50
  }
29
51
 
52
+ Store.prototype.delTab = function (id) {
53
+ return window.store.delItem({ id }, 'tabs')
54
+ }
55
+
30
56
  Store.prototype.initFirstTab = function () {
31
57
  postMsg({
32
58
  action: tabActions.initFirstTab
@@ -40,6 +66,7 @@ export default Store => {
40
66
  postMsg({
41
67
  action: tabActions.addTab,
42
68
  tab,
69
+ batch: tab?.batch ?? window.openTabBatch ?? window.store.currentLayoutBatch,
43
70
  index
44
71
  })
45
72
  }
@@ -71,4 +98,67 @@ export default Store => {
71
98
  }
72
99
  }
73
100
  }
101
+
102
+ Store.prototype.cloneToNextLayout = function () {
103
+ const { store } = window
104
+ const defaultStatus = statusMap.processing
105
+ const { currentTab, layout, currentLayoutBatch } = store
106
+ const ntb = deepCopy(currentTab)
107
+ Object.assign(ntb, {
108
+ id: generate(),
109
+ status: defaultStatus,
110
+ isTransporting: undefined,
111
+ pane: paneMap.terminal
112
+ })
113
+ let maxBatch = splitConfig[layout].children
114
+ if (maxBatch < 2) {
115
+ maxBatch = 2
116
+ }
117
+ ntb.batch = (currentLayoutBatch + 1) % maxBatch
118
+ store.addTab(ntb)
119
+ if (layout === 'c1') {
120
+ store.setLayout('c2')
121
+ }
122
+ }
123
+
124
+ Store.prototype.setLayout = function (layout) {
125
+ const {
126
+ store
127
+ } = window
128
+ const prevLayout = store.layout
129
+ if (prevLayout === layout) {
130
+ return
131
+ }
132
+ store.prevLayout = prevLayout
133
+ ls.setItem('layout', layout)
134
+ store.layout = layout
135
+ const len = splitConfig[layout].children
136
+ const prevLen = prevLayout ? splitConfig[prevLayout].children : 0
137
+ if (len < prevLen) {
138
+ const {
139
+ tabs
140
+ } = store
141
+ // Update tabs where batch > len - 1
142
+ const updatedTabs = tabs.map(tab => {
143
+ if (tab.batch > len - 1) {
144
+ return { ...tab, batch: len - 1 }
145
+ }
146
+ return tab
147
+ })
148
+ // Set the updated tabs back to the store
149
+ store.setTabs(updatedTabs)
150
+ setTimeout(
151
+ () => {
152
+ postMsg({
153
+ action: tabActions.changeCurrentTabId,
154
+ currentTabId: store.currentTabId
155
+ })
156
+ },
157
+ 1000
158
+ )
159
+ if (store.currentLayoutBatch > len - 1) {
160
+ store.currentLayoutBatch = len - 1
161
+ }
162
+ }
163
+ }
74
164
  }
@@ -48,7 +48,7 @@ export default Store => {
48
48
  return window.store.addItems(objs, 'fileTransfers')
49
49
  }
50
50
  Store.prototype.setFileTransfers = function (objs) {
51
- return window.store.setState('fileTransfers', objs)
51
+ return window.store.setState('fileTransfers', objs.filter(d => !d.cancel))
52
52
  }
53
53
  Store.prototype.addTransferList = function (objs) {
54
54
  const { store } = window
@@ -85,11 +85,10 @@ export default Store => {
85
85
  }))
86
86
  }
87
87
  Store.prototype.cancelAll = function () {
88
- const { store } = window
89
- store.setFileTransfers(store.fileTransfers.map(t => {
90
- t.cancel = true
91
- return t
92
- }))
88
+ const arr = document.querySelectorAll('.sftp-transport .transfer-control-cancel')
89
+ arr.forEach(d => {
90
+ d.click()
91
+ })
93
92
  }
94
93
  Store.prototype.cancelTransfer = function (itemId) {
95
94
  const { store } = window
@@ -18,12 +18,12 @@ import * as ls from '../common/safe-local-storage'
18
18
  import { debounce, isEmpty } from 'lodash-es'
19
19
 
20
20
  export default store => {
21
- autoRun(store, () => {
22
- store.focus()
23
- // store.termSearchOpen = false
24
- store.termSearchMatchCount = 0
25
- return store.currentTabId
26
- }, func => debounce(func, 100)).start()
21
+ // autoRun(store, () => {
22
+ // store.focus()
23
+ // // store.termSearchOpen = false
24
+ // store.termSearchMatchCount = 0
25
+ // return store.currentTabId
26
+ // }).start()
27
27
 
28
28
  // autoRun(store, () => {
29
29
  // if (store.menuOpened) {
@@ -99,6 +99,11 @@ export default store => {
99
99
  return store._checkedKeys
100
100
  }).start()
101
101
 
102
+ // autoRun(store, () => {
103
+ // window.store.onLayoutChange()
104
+ // return store.layout
105
+ // }).start()
106
+
102
107
  autoRun(store, () => {
103
108
  const tabs = store.getTabs()
104
109
  const { currentTabId } = store
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@electerm/electerm-react",
3
- "version": "1.40.20",
3
+ "version": "1.50.31",
4
4
  "description": "react components src for electerm",
5
5
  "main": "./client/components/main/main.jsx",
6
6
  "license": "MIT",
@@ -1 +0,0 @@
1
- export { Component } from 'manate/react'
@@ -1,222 +0,0 @@
1
- /**
2
- * make child component resizable by drag the horizontal or vertical handle
3
- * // todo: rerender check
4
- */
5
-
6
- import React from 'react'
7
- import PropTypes from 'prop-types'
8
- import classnames from 'classnames'
9
- import { isNull, pick, isUndefined } from 'lodash-es'
10
- import parseInt10 from '../../common/parse-int10'
11
- import generate from '../../common/uid'
12
- import memoizeOne from 'memoize-one'
13
- import {
14
- terminalSplitDirectionMap,
15
- minTerminalWidth,
16
- maxDragMove
17
- } from '../../common/constants'
18
- import './resize-wrap.styl'
19
-
20
- export default class ResizeWrap extends React.Component {
21
- static propTypes = {
22
- direction: PropTypes.oneOf(['horizontal', 'vertical']).isRequired,
23
- children: PropTypes.arrayOf(PropTypes.element).isRequired,
24
- minWidth: PropTypes.number,
25
- onEndDrag: PropTypes.func,
26
- noResizeEvent: PropTypes.bool
27
- }
28
-
29
- getChildIds = (props = this.props) => {
30
- return props.children.map(c => c.props.id)
31
- }
32
-
33
- getSplitIds = () => {
34
- const len = this.props.children.length - 1
35
- return this.getSplitIdsCache(len)
36
- }
37
-
38
- getSplitIdsCache = memoizeOne((len) => {
39
- return new Array(len)
40
- .fill(8).map(() => generate())
41
- })
42
-
43
- positionProps = [
44
- 'width',
45
- 'height',
46
- 'left',
47
- 'top'
48
- ]
49
-
50
- onDrag = (e) => {
51
- const dom = e.target
52
- const prev = dom.previousSibling
53
- const next = dom.nextSibling
54
- const { direction } = this.props
55
- const { startPosition } = this
56
- if (isNull(e.pageX)) {
57
- return
58
- }
59
- const currentPosition = {
60
- x: e.pageX,
61
- y: e.pageY
62
- }
63
-
64
- const types = ['dom', 'prev', 'next']
65
- const doms = [dom, prev, next]
66
- const styles = doms.map(d => {
67
- const { style } = d
68
- const obj = pick(style, this.positionProps)
69
- return Object.keys(obj).reduce((prev, k) => {
70
- const v = obj[k]
71
- return {
72
- ...prev,
73
- [k]: isUndefined(v)
74
- ? v
75
- : parseInt10(obj[k].replace('px', ''))
76
- }
77
- }, {})
78
- })
79
- let xDiff = currentPosition.x - startPosition.x
80
- let yDiff = currentPosition.y - startPosition.y
81
- if (Math.abs(xDiff) > maxDragMove) {
82
- return
83
- }
84
- const prevStyle = styles[1]
85
- const nextStyle = styles[2]
86
- const minW = this.props.minWidth || minTerminalWidth
87
- if (direction === terminalSplitDirectionMap.vertical) {
88
- if (yDiff > 0 && yDiff > nextStyle.height - minW) {
89
- yDiff = nextStyle.height - minW
90
- } else if (yDiff < 0 && yDiff < -(prevStyle.height - minW)) {
91
- yDiff = -(prevStyle.height - minW)
92
- }
93
- } else {
94
- if (xDiff > 0 && xDiff > nextStyle.width - minW) {
95
- xDiff = nextStyle.width - minW
96
- } else if (xDiff < 0 && xDiff < -(prevStyle.width - minW)) {
97
- xDiff = -(prevStyle.width - minW)
98
- }
99
- }
100
- doms.forEach((d, i) => {
101
- this.changePosition(d, direction, xDiff, yDiff, types[i], styles[i])
102
- })
103
- this.startPosition = currentPosition
104
- }
105
-
106
- onDragStart = (e) => {
107
- this.startPosition = {
108
- x: e.pageX,
109
- y: e.pageY
110
- }
111
- }
112
-
113
- changePosition = (
114
- dom,
115
- direction,
116
- xDiff,
117
- yDiff,
118
- type,
119
- style
120
- ) => {
121
- const realHeight = style.height
122
- const realWidth = style.width
123
- const realTop = style.top
124
- const realLeft = style.left
125
- if (type === 'prev' && direction === terminalSplitDirectionMap.vertical) {
126
- dom.style.height = (realHeight + yDiff) + 'px'
127
- } else if (type === 'prev') {
128
- dom.style.width = (realWidth + xDiff) + 'px'
129
- } else if (type === 'dom' && direction === terminalSplitDirectionMap.vertical) {
130
- dom.style.top = (realTop + yDiff) + 'px'
131
- } else if (type === 'dom') {
132
- dom.style.left = (realLeft + xDiff) + 'px'
133
- } else if (type === 'next' && direction === terminalSplitDirectionMap.vertical) {
134
- dom.style.top = (realTop + yDiff) + 'px'
135
- dom.style.height = (realHeight - yDiff) + 'px'
136
- } else {
137
- dom.style.width = (realWidth - xDiff) + 'px'
138
- dom.style.left = (realLeft + xDiff) + 'px'
139
- }
140
- }
141
-
142
- onDragEnd = () => {
143
- const {
144
- noResizeEvent,
145
- onDragEnd
146
- } = this.props
147
- if (onDragEnd) {
148
- onDragEnd()
149
- }
150
- if (noResizeEvent) {
151
- return
152
- }
153
- window.dispatchEvent(new CustomEvent('resize'))
154
- }
155
-
156
- buildHandleComponent = (prevComponent, direction, index, tid) => {
157
- const zIndex = this.props.children.length + 10
158
- const cls = classnames(
159
- `tw-${tid}`,
160
- 'term-dragger',
161
- `term-dragger-${index}`,
162
- `term-dragger-${direction}`
163
- )
164
- const { left, top, width, height } = prevComponent.props
165
- const style = direction === terminalSplitDirectionMap.vertical
166
- ? {
167
- left: 0,
168
- right: 0,
169
- zIndex,
170
- top: top + height - 2
171
- }
172
- : {
173
- top: 0,
174
- bottom: 0,
175
- zIndex,
176
- left: left + width - 2
177
- }
178
- const props = {
179
- style,
180
- ...pick(this, [
181
- 'onDoubleClick',
182
- 'onDrag',
183
- 'onDragStart',
184
- 'onDragEnd'
185
- ]),
186
- className: cls,
187
- draggable: true
188
- }
189
- return (
190
- <span
191
- key={tid}
192
- {...props}
193
- />
194
- )
195
- }
196
-
197
- render () {
198
- const {
199
- children,
200
- direction
201
- } = this.props
202
- const len = children.length
203
- if (len < 2) {
204
- return children
205
- }
206
- let splitIndex = 0
207
- const splitIds = this.getSplitIds()
208
- const newArr = children.reduce((prev, c, i) => {
209
- let split = null
210
- if (i !== len - 1) {
211
- split = this.buildHandleComponent(c, direction, i, splitIds[splitIndex])
212
- splitIndex++
213
- }
214
- return [
215
- ...prev,
216
- c,
217
- split
218
- ].filter(d => d)
219
- }, [])
220
- return newArr
221
- }
222
- }