tabulator-tables 5.4.3 → 5.5.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.
Files changed (253) hide show
  1. package/.babelrc.json +3 -3
  2. package/.editorconfig +6 -6
  3. package/.eslintignore +3 -3
  4. package/.eslintrc.js +28 -28
  5. package/.github/ISSUE_TEMPLATE/bug_report.md +58 -58
  6. package/.github/ISSUE_TEMPLATE/documentation.md +14 -14
  7. package/.github/ISSUE_TEMPLATE/feature_request.md +24 -24
  8. package/.github/ISSUE_TEMPLATE/question.md +12 -12
  9. package/.github/workflows/bad-files-check.yml +39 -39
  10. package/.github/workflows/lint-and-test.yml +30 -30
  11. package/CODE_OF_CONDUCT.md +46 -46
  12. package/CONTRIBUTING.md +22 -22
  13. package/LICENSE +20 -20
  14. package/README.md +76 -76
  15. package/bower.json +40 -40
  16. package/build/Bundler.js +185 -185
  17. package/build/rollup.js +6 -6
  18. package/dist/css/tabulator.css +80 -53
  19. package/dist/css/tabulator.css.map +1 -1
  20. package/dist/css/tabulator.min.css +1 -1
  21. package/dist/css/tabulator.min.css.map +1 -1
  22. package/dist/css/tabulator_bootstrap3.css +89 -58
  23. package/dist/css/tabulator_bootstrap3.css.map +1 -1
  24. package/dist/css/tabulator_bootstrap3.min.css +1 -1
  25. package/dist/css/tabulator_bootstrap3.min.css.map +1 -1
  26. package/dist/css/tabulator_bootstrap4.css +106 -73
  27. package/dist/css/tabulator_bootstrap4.css.map +1 -1
  28. package/dist/css/tabulator_bootstrap4.min.css +1 -1
  29. package/dist/css/tabulator_bootstrap4.min.css.map +1 -1
  30. package/dist/css/tabulator_bootstrap5.css +110 -75
  31. package/dist/css/tabulator_bootstrap5.css.map +1 -1
  32. package/dist/css/tabulator_bootstrap5.min.css +1 -1
  33. package/dist/css/tabulator_bootstrap5.min.css.map +1 -1
  34. package/dist/css/tabulator_bulma.css +95 -62
  35. package/dist/css/tabulator_bulma.css.map +1 -1
  36. package/dist/css/tabulator_bulma.min.css +1 -1
  37. package/dist/css/tabulator_bulma.min.css.map +1 -1
  38. package/dist/css/tabulator_materialize.css +93 -63
  39. package/dist/css/tabulator_materialize.css.map +1 -1
  40. package/dist/css/tabulator_materialize.min.css +1 -1
  41. package/dist/css/tabulator_materialize.min.css.map +1 -1
  42. package/dist/css/tabulator_midnight.css +90 -59
  43. package/dist/css/tabulator_midnight.css.map +1 -1
  44. package/dist/css/tabulator_midnight.min.css +1 -1
  45. package/dist/css/tabulator_midnight.min.css.map +1 -1
  46. package/dist/css/tabulator_modern.css +96 -62
  47. package/dist/css/tabulator_modern.css.map +1 -1
  48. package/dist/css/tabulator_modern.min.css +1 -1
  49. package/dist/css/tabulator_modern.min.css.map +1 -1
  50. package/dist/css/tabulator_semanticui.css +233 -182
  51. package/dist/css/tabulator_semanticui.css.map +1 -1
  52. package/dist/css/tabulator_semanticui.min.css +1 -1
  53. package/dist/css/tabulator_semanticui.min.css.map +1 -1
  54. package/dist/css/tabulator_simple.css +80 -53
  55. package/dist/css/tabulator_simple.css.map +1 -1
  56. package/dist/css/tabulator_simple.min.css +1 -1
  57. package/dist/css/tabulator_simple.min.css.map +1 -1
  58. package/dist/css/tabulator_site.css +88 -57
  59. package/dist/css/tabulator_site.css.map +1 -1
  60. package/dist/css/tabulator_site.min.css +1 -1
  61. package/dist/css/tabulator_site.min.css.map +1 -1
  62. package/dist/js/jquery_wrapper.js +55 -55
  63. package/dist/js/tabulator.js +26054 -25713
  64. package/dist/js/tabulator.js.map +1 -1
  65. package/dist/js/tabulator.min.js +2 -2
  66. package/dist/js/tabulator.min.js.map +1 -1
  67. package/dist/js/tabulator_esm.js +26131 -25790
  68. package/dist/js/tabulator_esm.js.map +1 -1
  69. package/dist/js/tabulator_esm.min.js +2 -2
  70. package/dist/js/tabulator_esm.min.js.map +1 -1
  71. package/package.json +65 -65
  72. package/src/js/builds/esm.js +14 -14
  73. package/src/js/builds/jquery_wrapper.js +55 -55
  74. package/src/js/core/ColumnManager.js +745 -730
  75. package/src/js/core/CoreFeature.js +138 -138
  76. package/src/js/core/FooterManager.js +101 -101
  77. package/src/js/core/Module.js +141 -141
  78. package/src/js/core/RowManager.js +1128 -1101
  79. package/src/js/core/Tabulator.js +895 -892
  80. package/src/js/core/TabulatorFull.js +10 -10
  81. package/src/js/core/cell/Cell.js +295 -295
  82. package/src/js/core/cell/CellComponent.js +78 -76
  83. package/src/js/core/column/Column.js +949 -949
  84. package/src/js/core/column/ColumnComponent.js +152 -152
  85. package/src/js/core/column/defaults/options.js +17 -17
  86. package/src/js/core/defaults/options.js +65 -65
  87. package/src/js/core/modules/core.js +2 -2
  88. package/src/js/core/modules/optional.js +34 -34
  89. package/src/js/core/rendering/Renderer.js +203 -203
  90. package/src/js/core/rendering/renderers/BasicHorizontal.js +24 -19
  91. package/src/js/core/rendering/renderers/BasicVertical.js +83 -79
  92. package/src/js/core/rendering/renderers/VirtualDomHorizontal.js +582 -577
  93. package/src/js/core/rendering/renderers/VirtualDomVertical.js +634 -580
  94. package/src/js/core/row/PseudoRow.js +44 -44
  95. package/src/js/core/row/Row.js +457 -457
  96. package/src/js/core/row/RowComponent.js +93 -93
  97. package/src/js/core/tools/Alert.js +61 -61
  98. package/src/js/core/tools/ComponentFunctionBinder.js +32 -32
  99. package/src/js/core/tools/DataLoader.js +119 -119
  100. package/src/js/core/tools/DeprecationAdvisor.js +46 -46
  101. package/src/js/core/tools/ExternalEventBus.js +104 -104
  102. package/src/js/core/tools/Helpers.js +46 -46
  103. package/src/js/core/tools/InteractionMonitor.js +321 -321
  104. package/src/js/core/tools/InternalEventBus.js +161 -161
  105. package/src/js/core/tools/ModuleBinder.js +104 -104
  106. package/src/js/core/tools/OptionsList.js +44 -40
  107. package/src/js/core/tools/Popup.js +304 -304
  108. package/src/js/core/tools/TableRegistry.js +61 -61
  109. package/src/js/modules/Accessor/Accessor.js +115 -115
  110. package/src/js/modules/Ajax/Ajax.js +143 -143
  111. package/src/js/modules/Ajax/defaults/config.js +2 -2
  112. package/src/js/modules/Ajax/defaults/contentTypeFormatters.js +44 -44
  113. package/src/js/modules/Ajax/defaults/loaderPromise.js +86 -86
  114. package/src/js/modules/Ajax/defaults/urlGenerator.js +43 -43
  115. package/src/js/modules/Clipboard/Clipboard.js +279 -279
  116. package/src/js/modules/Clipboard/defaults/pasteActions.js +10 -10
  117. package/src/js/modules/Clipboard/defaults/pasteParsers.js +74 -74
  118. package/src/js/modules/ColumnCalcs/CalcComponent.js +47 -47
  119. package/src/js/modules/ColumnCalcs/ColumnCalcs.js +581 -568
  120. package/src/js/modules/ColumnCalcs/defaults/calculations.js +92 -85
  121. package/src/js/modules/Comms/Comms.js +51 -51
  122. package/src/js/modules/DataTree/DataTree.js +603 -603
  123. package/src/js/modules/Download/Download.js +148 -148
  124. package/src/js/modules/Download/defaults/downloaders/csv.js +61 -61
  125. package/src/js/modules/Download/defaults/downloaders/html.js +4 -4
  126. package/src/js/modules/Download/defaults/downloaders/json.js +33 -33
  127. package/src/js/modules/Download/defaults/downloaders/jsonLines.js +31 -31
  128. package/src/js/modules/Download/defaults/downloaders/pdf.js +111 -111
  129. package/src/js/modules/Download/defaults/downloaders/xlsx.js +102 -99
  130. package/src/js/modules/Download/defaults/downloaders.js +14 -14
  131. package/src/js/modules/Edit/Edit.js +734 -736
  132. package/src/js/modules/Edit/List.js +1048 -1033
  133. package/src/js/modules/Edit/defaults/editors/autocomplete.js +11 -11
  134. package/src/js/modules/Edit/defaults/editors/date.js +138 -110
  135. package/src/js/modules/Edit/defaults/editors/datetime.js +125 -97
  136. package/src/js/modules/Edit/defaults/editors/input.js +76 -74
  137. package/src/js/modules/Edit/defaults/editors/list.js +6 -6
  138. package/src/js/modules/Edit/defaults/editors/number.js +109 -107
  139. package/src/js/modules/Edit/defaults/editors/progress.js +126 -126
  140. package/src/js/modules/Edit/defaults/editors/range.js +80 -78
  141. package/src/js/modules/Edit/defaults/editors/select.js +9 -9
  142. package/src/js/modules/Edit/defaults/editors/star.js +145 -145
  143. package/src/js/modules/Edit/defaults/editors/textarea.js +122 -120
  144. package/src/js/modules/Edit/defaults/editors/tickCross.js +94 -96
  145. package/src/js/modules/Edit/defaults/editors/time.js +126 -98
  146. package/src/js/modules/Edit/defaults/editors.js +28 -28
  147. package/src/js/modules/Edit/inputMask.js +73 -73
  148. package/src/js/modules/Export/Export.js +626 -623
  149. package/src/js/modules/Export/ExportColumn.js +10 -10
  150. package/src/js/modules/Export/ExportRow.js +9 -9
  151. package/src/js/modules/Filter/Filter.js +903 -892
  152. package/src/js/modules/Filter/defaults/filters.js +107 -107
  153. package/src/js/modules/Format/Format.js +215 -212
  154. package/src/js/modules/Format/defaults/formatters/buttonCross.js +2 -2
  155. package/src/js/modules/Format/defaults/formatters/buttonTick.js +2 -2
  156. package/src/js/modules/Format/defaults/formatters/color.js +3 -3
  157. package/src/js/modules/Format/defaults/formatters/datetime.js +36 -36
  158. package/src/js/modules/Format/defaults/formatters/datetimediff.js +40 -40
  159. package/src/js/modules/Format/defaults/formatters/handle.js +3 -3
  160. package/src/js/modules/Format/defaults/formatters/html.js +2 -2
  161. package/src/js/modules/Format/defaults/formatters/image.js +39 -39
  162. package/src/js/modules/Format/defaults/formatters/link.js +77 -77
  163. package/src/js/modules/Format/defaults/formatters/lookup.js +9 -9
  164. package/src/js/modules/Format/defaults/formatters/money.js +43 -36
  165. package/src/js/modules/Format/defaults/formatters/plaintext.js +2 -2
  166. package/src/js/modules/Format/defaults/formatters/progress.js +132 -132
  167. package/src/js/modules/Format/defaults/formatters/responsiveCollapse.js +43 -43
  168. package/src/js/modules/Format/defaults/formatters/rowSelection.js +59 -59
  169. package/src/js/modules/Format/defaults/formatters/rownum.js +9 -9
  170. package/src/js/modules/Format/defaults/formatters/star.js +37 -37
  171. package/src/js/modules/Format/defaults/formatters/textarea.js +3 -3
  172. package/src/js/modules/Format/defaults/formatters/tickCross.js +21 -21
  173. package/src/js/modules/Format/defaults/formatters/traffic.js +46 -46
  174. package/src/js/modules/Format/defaults/formatters.js +42 -42
  175. package/src/js/modules/FrozenColumns/FrozenColumns.js +299 -299
  176. package/src/js/modules/FrozenRows/FrozenRows.js +169 -159
  177. package/src/js/modules/GroupRows/Group.js +597 -598
  178. package/src/js/modules/GroupRows/GroupComponent.js +70 -66
  179. package/src/js/modules/GroupRows/GroupRows.js +639 -639
  180. package/src/js/modules/History/History.js +171 -171
  181. package/src/js/modules/History/defaults/redoers.js +24 -24
  182. package/src/js/modules/History/defaults/undoers.js +24 -24
  183. package/src/js/modules/HtmlTableImport/HtmlTableImport.js +181 -181
  184. package/src/js/modules/Import/Import.js +193 -193
  185. package/src/js/modules/Import/defaults/importers/array.js +4 -4
  186. package/src/js/modules/Import/defaults/importers/csv.js +62 -62
  187. package/src/js/modules/Import/defaults/importers/json.js +7 -7
  188. package/src/js/modules/Import/defaults/importers.js +8 -8
  189. package/src/js/modules/Interaction/Interaction.js +337 -325
  190. package/src/js/modules/Keybindings/Keybindings.js +172 -172
  191. package/src/js/modules/Keybindings/defaults/actions.js +118 -118
  192. package/src/js/modules/Keybindings/defaults/bindings.js +12 -12
  193. package/src/js/modules/Layout/Layout.js +49 -49
  194. package/src/js/modules/Layout/defaults/modes/fitColumns.js +171 -171
  195. package/src/js/modules/Layout/defaults/modes/fitData.js +9 -9
  196. package/src/js/modules/Layout/defaults/modes/fitDataGeneral.js +9 -9
  197. package/src/js/modules/Layout/defaults/modes/fitDataStretch.js +39 -39
  198. package/src/js/modules/Layout/defaults/modes.js +11 -11
  199. package/src/js/modules/Localize/Localize.js +185 -185
  200. package/src/js/modules/Localize/defaults/langs.js +36 -36
  201. package/src/js/modules/Menu/Menu.js +302 -302
  202. package/src/js/modules/MoveColumns/MoveColumns.js +299 -299
  203. package/src/js/modules/MoveRows/MoveRows.js +635 -635
  204. package/src/js/modules/Mutator/Mutator.js +161 -161
  205. package/src/js/modules/Page/Page.js +881 -881
  206. package/src/js/modules/Page/defaults/pageCounters/pages.js +32 -32
  207. package/src/js/modules/Page/defaults/pageCounters/rows.js +39 -39
  208. package/src/js/modules/Page/defaults/pageCounters.js +7 -7
  209. package/src/js/modules/Persistence/Persistence.js +472 -458
  210. package/src/js/modules/Persistence/defaults/readers.js +29 -29
  211. package/src/js/modules/Persistence/defaults/writers.js +12 -12
  212. package/src/js/modules/Popup/Popup.js +231 -231
  213. package/src/js/modules/Print/Print.js +137 -137
  214. package/src/js/modules/ReactiveData/ReactiveData.js +408 -408
  215. package/src/js/modules/ResizeColumns/ResizeColumns.js +309 -309
  216. package/src/js/modules/ResizeRows/ResizeRows.js +111 -111
  217. package/src/js/modules/ResizeTable/ResizeTable.js +159 -159
  218. package/src/js/modules/ResponsiveLayout/ResponsiveLayout.js +348 -345
  219. package/src/js/modules/SelectRow/SelectRow.js +474 -444
  220. package/src/js/modules/Sort/Sort.js +470 -470
  221. package/src/js/modules/Sort/defaults/sorters/alphanum.js +43 -43
  222. package/src/js/modules/Sort/defaults/sorters/array.js +53 -53
  223. package/src/js/modules/Sort/defaults/sorters/boolean.js +6 -6
  224. package/src/js/modules/Sort/defaults/sorters/date.js +9 -9
  225. package/src/js/modules/Sort/defaults/sorters/datetime.js +43 -43
  226. package/src/js/modules/Sort/defaults/sorters/exists.js +6 -6
  227. package/src/js/modules/Sort/defaults/sorters/number.js +39 -39
  228. package/src/js/modules/Sort/defaults/sorters/string.js +33 -33
  229. package/src/js/modules/Sort/defaults/sorters/time.js +9 -9
  230. package/src/js/modules/Sort/defaults/sorters.js +20 -20
  231. package/src/js/modules/Tooltip/Tooltip.js +130 -130
  232. package/src/js/modules/Validate/Validate.js +305 -305
  233. package/src/js/modules/Validate/defaults/validators.js +138 -138
  234. package/src/scss/tabulator.scss +1496 -1467
  235. package/src/scss/themes/bootstrap/functions4.scss +118 -118
  236. package/src/scss/themes/bootstrap/functions5.scss +302 -302
  237. package/src/scss/themes/bootstrap/tabulator_bootstrap3.scss +288 -284
  238. package/src/scss/themes/bootstrap/tabulator_bootstrap4.scss +552 -544
  239. package/src/scss/themes/bootstrap/tabulator_bootstrap5.scss +584 -574
  240. package/src/scss/themes/bootstrap/variables3.scss +870 -870
  241. package/src/scss/themes/bootstrap/variables4.scss +930 -930
  242. package/src/scss/themes/bootstrap/variables5.scss +1641 -1641
  243. package/src/scss/themes/bulma/tabulator_bulma.scss +258 -252
  244. package/src/scss/themes/bulma/variables.scss +197 -197
  245. package/src/scss/themes/materialize/tabulator_materialize.scss +269 -265
  246. package/src/scss/themes/materialize/variables.scss +70 -70
  247. package/src/scss/themes/semanticui/tabulator_semanticui.scss +586 -561
  248. package/src/scss/themes/semanticui/variables.scss +839 -839
  249. package/src/scss/themes/semanticui/variables_table.scss +247 -247
  250. package/src/scss/themes/tabulator_midnight.scss +162 -158
  251. package/src/scss/themes/tabulator_modern.scss +239 -231
  252. package/src/scss/themes/tabulator_simple.scss +102 -102
  253. package/src/scss/themes/tabulator_site.scss +193 -189
@@ -1,445 +1,475 @@
1
- import Module from '../../core/Module.js';
2
-
3
- class SelectRow extends Module{
4
-
5
- constructor(table){
6
- super(table);
7
-
8
- this.selecting = false; //flag selecting in progress
9
- this.lastClickedRow = false; //last clicked row
10
- this.selectPrev = []; //hold previously selected element for drag drop selection
11
- this.selectedRows = []; //hold selected rows
12
- this.headerCheckboxElement = null; // hold header select element
13
-
14
- this.registerTableOption("selectable", "highlight"); //highlight rows on hover
15
- this.registerTableOption("selectableRangeMode", "drag"); //highlight rows on hover
16
- this.registerTableOption("selectableRollingSelection", true); //roll selection once maximum number of selectable rows is reached
17
- this.registerTableOption("selectablePersistence", true); // maintain selection when table view is updated
18
- this.registerTableOption("selectableCheck", function(data, row){return true;}); //check whether row is selectable
19
-
20
- this.registerTableFunction("selectRow", this.selectRows.bind(this));
21
- this.registerTableFunction("deselectRow", this.deselectRows.bind(this));
22
- this.registerTableFunction("toggleSelectRow", this.toggleRow.bind(this));
23
- this.registerTableFunction("getSelectedRows", this.getSelectedRows.bind(this));
24
- this.registerTableFunction("getSelectedData", this.getSelectedData.bind(this));
25
-
26
- //register component functions
27
- this.registerComponentFunction("row", "select", this.selectRows.bind(this));
28
- this.registerComponentFunction("row", "deselect", this.deselectRows.bind(this));
29
- this.registerComponentFunction("row", "toggleSelect", this.toggleRow.bind(this));
30
- this.registerComponentFunction("row", "isSelected", this.isRowSelected.bind(this));
31
- }
32
-
33
- initialize(){
34
- if(this.table.options.selectable !== false){
35
- this.subscribe("row-init", this.initializeRow.bind(this));
36
- this.subscribe("row-deleting", this.rowDeleted.bind(this));
37
- this.subscribe("rows-wipe", this.clearSelectionData.bind(this));
38
- this.subscribe("rows-retrieve", this.rowRetrieve.bind(this));
39
-
40
- if(this.table.options.selectable && !this.table.options.selectablePersistence){
41
- this.subscribe("data-refreshing", this.deselectRows.bind(this));
42
- }
43
- }
44
- }
45
-
46
- rowRetrieve(type, prevValue){
47
- return type === "selected" ? this.selectedRows : prevValue;
48
- }
49
-
50
- rowDeleted(row){
51
- this._deselectRow(row, true);
52
- }
53
-
54
- clearSelectionData(silent){
55
- this.selecting = false;
56
- this.lastClickedRow = false;
57
- this.selectPrev = [];
58
- this.selectedRows = [];
59
-
60
- if(silent !== true){
61
- this._rowSelectionChanged();
62
- }
63
- }
64
-
65
- initializeRow(row){
66
- var self = this,
67
- element = row.getElement();
68
-
69
- // trigger end of row selection
70
- var endSelect = function(){
71
-
72
- setTimeout(function(){
73
- self.selecting = false;
74
- }, 50);
75
-
76
- document.body.removeEventListener("mouseup", endSelect);
77
- };
78
-
79
- row.modules.select = {selected:false};
80
-
81
- //set row selection class
82
- if(self.checkRowSelectability(row)){
83
- element.classList.add("tabulator-selectable");
84
- element.classList.remove("tabulator-unselectable");
85
-
86
- if(self.table.options.selectable && self.table.options.selectable != "highlight"){
87
- if(self.table.options.selectableRangeMode === "click"){
88
- element.addEventListener("click", this.handleComplexRowClick.bind(this, row));
89
- }else{
90
- element.addEventListener("click", function(e){
91
- if(!self.table.modExists("edit") || !self.table.modules.edit.getCurrentCell()){
92
- self.table._clearSelection();
93
- }
94
-
95
- if(!self.selecting){
96
- self.toggleRow(row);
97
- }
98
- });
99
-
100
- element.addEventListener("mousedown", function(e){
101
- if(e.shiftKey){
102
- self.table._clearSelection();
103
-
104
- self.selecting = true;
105
-
106
- self.selectPrev = [];
107
-
108
- document.body.addEventListener("mouseup", endSelect);
109
- document.body.addEventListener("keyup", endSelect);
110
-
111
- self.toggleRow(row);
112
-
113
- return false;
114
- }
115
- });
116
-
117
- element.addEventListener("mouseenter", function(e){
118
- if(self.selecting){
119
- self.table._clearSelection();
120
- self.toggleRow(row);
121
-
122
- if(self.selectPrev[1] == row){
123
- self.toggleRow(self.selectPrev[0]);
124
- }
125
- }
126
- });
127
-
128
- element.addEventListener("mouseout", function(e){
129
- if(self.selecting){
130
- self.table._clearSelection();
131
- self.selectPrev.unshift(row);
132
- }
133
- });
134
- }
135
- }
136
-
137
- }else{
138
- element.classList.add("tabulator-unselectable");
139
- element.classList.remove("tabulator-selectable");
140
- }
141
- }
142
-
143
- handleComplexRowClick(row, e){
144
- if(e.shiftKey){
145
- this.table._clearSelection();
146
- this.lastClickedRow = this.lastClickedRow || row;
147
-
148
- var lastClickedRowIdx = this.table.rowManager.getDisplayRowIndex(this.lastClickedRow);
149
- var rowIdx = this.table.rowManager.getDisplayRowIndex(row);
150
-
151
- var fromRowIdx = lastClickedRowIdx <= rowIdx ? lastClickedRowIdx : rowIdx;
152
- var toRowIdx = lastClickedRowIdx >= rowIdx ? lastClickedRowIdx : rowIdx;
153
-
154
- var rows = this.table.rowManager.getDisplayRows().slice(0);
155
- var toggledRows = rows.splice(fromRowIdx, toRowIdx - fromRowIdx + 1);
156
-
157
- if(e.ctrlKey || e.metaKey){
158
- toggledRows.forEach((toggledRow)=>{
159
- if(toggledRow !== this.lastClickedRow){
160
-
161
- if(this.table.options.selectable !== true && !this.isRowSelected(row)){
162
- if(this.selectedRows.length < this.table.options.selectable){
163
- this.toggleRow(toggledRow);
164
- }
165
- }else{
166
- this.toggleRow(toggledRow);
167
- }
168
- }
169
- });
170
- this.lastClickedRow = row;
171
- }else{
172
- this.deselectRows(undefined, true);
173
-
174
- if(this.table.options.selectable !== true){
175
- if(toggledRows.length > this.table.options.selectable){
176
- toggledRows = toggledRows.slice(0, this.table.options.selectable);
177
- }
178
- }
179
-
180
- this.selectRows(toggledRows);
181
- }
182
- this.table._clearSelection();
183
- }
184
- else if(e.ctrlKey || e.metaKey){
185
- this.toggleRow(row);
186
- this.lastClickedRow = row;
187
- }else{
188
- this.deselectRows(undefined, true);
189
- this.selectRows(row);
190
- this.lastClickedRow = row;
191
- }
192
- }
193
-
194
- checkRowSelectability(row){
195
- if(row.type === "row"){
196
- return this.table.options.selectableCheck.call(this.table, row.getComponent());
197
- }
198
-
199
- return false;
200
- }
201
-
202
- //toggle row selection
203
- toggleRow(row){
204
- if(this.checkRowSelectability(row)){
205
- if(row.modules.select && row.modules.select.selected){
206
- this._deselectRow(row);
207
- }else{
208
- this._selectRow(row);
209
- }
210
- }
211
- }
212
-
213
- //select a number of rows
214
- selectRows(rows){
215
- var rowMatch;
216
-
217
- switch(typeof rows){
218
- case "undefined":
219
- this.table.rowManager.rows.forEach((row) => {
220
- this._selectRow(row, true, true);
221
- });
222
-
223
- this._rowSelectionChanged();
224
- break;
225
-
226
- case "string":
227
- rowMatch = this.table.rowManager.findRow(rows);
228
-
229
- if(rowMatch){
230
- this._selectRow(rowMatch, true, true);
231
- this._rowSelectionChanged();
232
- }else{
233
- rowMatch = this.table.rowManager.getRows(rows);
234
-
235
- rowMatch.forEach((row) => {
236
- this._selectRow(row, true, true);
237
- });
238
-
239
- if(rowMatch.length){
240
- this._rowSelectionChanged();
241
- }
242
- }
243
- break;
244
-
245
- default:
246
- if(Array.isArray(rows)){
247
- rows.forEach((row) => {
248
- this._selectRow(row, true, true);
249
- });
250
-
251
- this._rowSelectionChanged();
252
- }else{
253
- this._selectRow(rows, false, true);
254
- }
255
- break;
256
- }
257
- }
258
-
259
- //select an individual row
260
- _selectRow(rowInfo, silent, force){
261
- //handle max row count
262
- if(!isNaN(this.table.options.selectable) && this.table.options.selectable !== true && !force){
263
- if(this.selectedRows.length >= this.table.options.selectable){
264
- if(this.table.options.selectableRollingSelection){
265
- this._deselectRow(this.selectedRows[0]);
266
- }else{
267
- return false;
268
- }
269
- }
270
- }
271
-
272
- var row = this.table.rowManager.findRow(rowInfo);
273
-
274
- if(row){
275
- if(this.selectedRows.indexOf(row) == -1){
276
- row.getElement().classList.add("tabulator-selected");
277
- if(!row.modules.select){
278
- row.modules.select = {};
279
- }
280
-
281
- row.modules.select.selected = true;
282
- if(row.modules.select.checkboxEl){
283
- row.modules.select.checkboxEl.checked = true;
284
- }
285
-
286
- this.selectedRows.push(row);
287
-
288
- if(this.table.options.dataTreeSelectPropagate){
289
- this.childRowSelection(row, true);
290
- }
291
-
292
- this.dispatchExternal("rowSelected", row.getComponent());
293
-
294
- this._rowSelectionChanged(silent);
295
- }
296
- }else{
297
- if(!silent){
298
- console.warn("Selection Error - No such row found, ignoring selection:" + rowInfo);
299
- }
300
- }
301
- }
302
-
303
- isRowSelected(row){
304
- return this.selectedRows.indexOf(row) !== -1;
305
- }
306
-
307
- //deselect a number of rows
308
- deselectRows(rows, silent){
309
- var self = this,
310
- rowCount;
311
-
312
- if(typeof rows == "undefined"){
313
-
314
- rowCount = self.selectedRows.length;
315
-
316
- for(let i = 0; i < rowCount; i++){
317
- self._deselectRow(self.selectedRows[0], true);
318
- }
319
-
320
- if(rowCount){
321
- self._rowSelectionChanged(silent);
322
- }
323
-
324
- }else{
325
- if(Array.isArray(rows)){
326
- rows.forEach(function(row){
327
- self._deselectRow(row, true);
328
- });
329
-
330
- self._rowSelectionChanged(silent);
331
- }else{
332
- self._deselectRow(rows, silent);
333
- }
334
- }
335
- }
336
-
337
- //deselect an individual row
338
- _deselectRow(rowInfo, silent){
339
- var self = this,
340
- row = self.table.rowManager.findRow(rowInfo),
341
- index;
342
-
343
- if(row){
344
- index = self.selectedRows.findIndex(function(selectedRow){
345
- return selectedRow == row;
346
- });
347
-
348
- if(index > -1){
349
-
350
- row.getElement().classList.remove("tabulator-selected");
351
- if(!row.modules.select){
352
- row.modules.select = {};
353
- }
354
-
355
- row.modules.select.selected = false;
356
- if(row.modules.select.checkboxEl){
357
- row.modules.select.checkboxEl.checked = false;
358
- }
359
- self.selectedRows.splice(index, 1);
360
-
361
- if(this.table.options.dataTreeSelectPropagate){
362
- this.childRowSelection(row, false);
363
- }
364
-
365
- this.dispatchExternal("rowDeselected", row.getComponent());
366
-
367
- self._rowSelectionChanged(silent);
368
- }
369
- }else{
370
- if(!silent){
371
- console.warn("Deselection Error - No such row found, ignoring selection:" + rowInfo);
372
- }
373
- }
374
- }
375
-
376
- getSelectedData(){
377
- var data = [];
378
-
379
- this.selectedRows.forEach(function(row){
380
- data.push(row.getData());
381
- });
382
-
383
- return data;
384
- }
385
-
386
- getSelectedRows(){
387
-
388
- var rows = [];
389
-
390
- this.selectedRows.forEach(function(row){
391
- rows.push(row.getComponent());
392
- });
393
-
394
- return rows;
395
- }
396
-
397
- _rowSelectionChanged(silent){
398
- if(this.headerCheckboxElement){
399
- if(this.selectedRows.length === 0){
400
- this.headerCheckboxElement.checked = false;
401
- this.headerCheckboxElement.indeterminate = false;
402
- } else if(this.table.rowManager.rows.length === this.selectedRows.length){
403
- this.headerCheckboxElement.checked = true;
404
- this.headerCheckboxElement.indeterminate = false;
405
- } else {
406
- this.headerCheckboxElement.indeterminate = true;
407
- this.headerCheckboxElement.checked = false;
408
- }
409
- }
410
-
411
- if(!silent){
412
- this.dispatchExternal("rowSelectionChanged", this.getSelectedData(), this.getSelectedRows());
413
- }
414
- }
415
-
416
- registerRowSelectCheckbox (row, element) {
417
- if(!row._row.modules.select){
418
- row._row.modules.select = {};
419
- }
420
-
421
- row._row.modules.select.checkboxEl = element;
422
- }
423
-
424
- registerHeaderSelectCheckbox (element) {
425
- this.headerCheckboxElement = element;
426
- }
427
-
428
- childRowSelection(row, select){
429
- var children = this.table.modules.dataTree.getChildren(row, true);
430
-
431
- if(select){
432
- for(let child of children){
433
- this._selectRow(child, true);
434
- }
435
- }else{
436
- for(let child of children){
437
- this._deselectRow(child, true);
438
- }
439
- }
440
- }
441
- }
442
-
443
- SelectRow.moduleName = "selectRow";
444
-
1
+ import Module from '../../core/Module.js';
2
+
3
+ class SelectRow extends Module{
4
+
5
+ constructor(table){
6
+ super(table);
7
+
8
+ this.selecting = false; //flag selecting in progress
9
+ this.lastClickedRow = false; //last clicked row
10
+ this.selectPrev = []; //hold previously selected element for drag drop selection
11
+ this.selectedRows = []; //hold selected rows
12
+ this.headerCheckboxElement = null; // hold header select element
13
+
14
+ this.registerTableOption("selectable", "highlight"); //highlight rows on hover
15
+ this.registerTableOption("selectableRangeMode", "drag"); //highlight rows on hover
16
+ this.registerTableOption("selectableRollingSelection", true); //roll selection once maximum number of selectable rows is reached
17
+ this.registerTableOption("selectablePersistence", true); // maintain selection when table view is updated
18
+ this.registerTableOption("selectableCheck", function(data, row){return true;}); //check whether row is selectable
19
+
20
+ this.registerTableFunction("selectRow", this.selectRows.bind(this));
21
+ this.registerTableFunction("deselectRow", this.deselectRows.bind(this));
22
+ this.registerTableFunction("toggleSelectRow", this.toggleRow.bind(this));
23
+ this.registerTableFunction("getSelectedRows", this.getSelectedRows.bind(this));
24
+ this.registerTableFunction("getSelectedData", this.getSelectedData.bind(this));
25
+
26
+ //register component functions
27
+ this.registerComponentFunction("row", "select", this.selectRows.bind(this));
28
+ this.registerComponentFunction("row", "deselect", this.deselectRows.bind(this));
29
+ this.registerComponentFunction("row", "toggleSelect", this.toggleRow.bind(this));
30
+ this.registerComponentFunction("row", "isSelected", this.isRowSelected.bind(this));
31
+ }
32
+
33
+ initialize(){
34
+ if(this.table.options.selectable !== false){
35
+ this.subscribe("row-init", this.initializeRow.bind(this));
36
+ this.subscribe("row-deleting", this.rowDeleted.bind(this));
37
+ this.subscribe("rows-wipe", this.clearSelectionData.bind(this));
38
+ this.subscribe("rows-retrieve", this.rowRetrieve.bind(this));
39
+
40
+ if(this.table.options.selectable && !this.table.options.selectablePersistence){
41
+ this.subscribe("data-refreshing", this.deselectRows.bind(this));
42
+ }
43
+ }
44
+ }
45
+
46
+ rowRetrieve(type, prevValue){
47
+ return type === "selected" ? this.selectedRows : prevValue;
48
+ }
49
+
50
+ rowDeleted(row){
51
+ this._deselectRow(row, true);
52
+ }
53
+
54
+ clearSelectionData(silent){
55
+ var prevSelected = this.selectedRows.length;
56
+
57
+ this.selecting = false;
58
+ this.lastClickedRow = false;
59
+ this.selectPrev = [];
60
+ this.selectedRows = [];
61
+
62
+ if(prevSelected && silent !== true){
63
+ this._rowSelectionChanged();
64
+ }
65
+ }
66
+
67
+ initializeRow(row){
68
+ var self = this,
69
+ element = row.getElement();
70
+
71
+ // trigger end of row selection
72
+ var endSelect = function(){
73
+
74
+ setTimeout(function(){
75
+ self.selecting = false;
76
+ }, 50);
77
+
78
+ document.body.removeEventListener("mouseup", endSelect);
79
+ };
80
+
81
+ row.modules.select = {selected:false};
82
+
83
+ //set row selection class
84
+ if(self.checkRowSelectability(row)){
85
+ element.classList.add("tabulator-selectable");
86
+ element.classList.remove("tabulator-unselectable");
87
+
88
+ if(self.table.options.selectable && self.table.options.selectable != "highlight"){
89
+ if(self.table.options.selectableRangeMode === "click"){
90
+ element.addEventListener("click", this.handleComplexRowClick.bind(this, row));
91
+ }else{
92
+ element.addEventListener("click", function(e){
93
+ if(!self.table.modExists("edit") || !self.table.modules.edit.getCurrentCell()){
94
+ self.table._clearSelection();
95
+ }
96
+
97
+ if(!self.selecting){
98
+ self.toggleRow(row);
99
+ }
100
+ });
101
+
102
+ element.addEventListener("mousedown", function(e){
103
+ if(e.shiftKey){
104
+ self.table._clearSelection();
105
+
106
+ self.selecting = true;
107
+
108
+ self.selectPrev = [];
109
+
110
+ document.body.addEventListener("mouseup", endSelect);
111
+ document.body.addEventListener("keyup", endSelect);
112
+
113
+ self.toggleRow(row);
114
+
115
+ return false;
116
+ }
117
+ });
118
+
119
+ element.addEventListener("mouseenter", function(e){
120
+ if(self.selecting){
121
+ self.table._clearSelection();
122
+ self.toggleRow(row);
123
+
124
+ if(self.selectPrev[1] == row){
125
+ self.toggleRow(self.selectPrev[0]);
126
+ }
127
+ }
128
+ });
129
+
130
+ element.addEventListener("mouseout", function(e){
131
+ if(self.selecting){
132
+ self.table._clearSelection();
133
+ self.selectPrev.unshift(row);
134
+ }
135
+ });
136
+ }
137
+ }
138
+
139
+ }else{
140
+ element.classList.add("tabulator-unselectable");
141
+ element.classList.remove("tabulator-selectable");
142
+ }
143
+ }
144
+
145
+ handleComplexRowClick(row, e){
146
+ if(e.shiftKey){
147
+ this.table._clearSelection();
148
+ this.lastClickedRow = this.lastClickedRow || row;
149
+
150
+ var lastClickedRowIdx = this.table.rowManager.getDisplayRowIndex(this.lastClickedRow);
151
+ var rowIdx = this.table.rowManager.getDisplayRowIndex(row);
152
+
153
+ var fromRowIdx = lastClickedRowIdx <= rowIdx ? lastClickedRowIdx : rowIdx;
154
+ var toRowIdx = lastClickedRowIdx >= rowIdx ? lastClickedRowIdx : rowIdx;
155
+
156
+ var rows = this.table.rowManager.getDisplayRows().slice(0);
157
+ var toggledRows = rows.splice(fromRowIdx, toRowIdx - fromRowIdx + 1);
158
+
159
+ if(e.ctrlKey || e.metaKey){
160
+ toggledRows.forEach((toggledRow)=>{
161
+ if(toggledRow !== this.lastClickedRow){
162
+
163
+ if(this.table.options.selectable !== true && !this.isRowSelected(row)){
164
+ if(this.selectedRows.length < this.table.options.selectable){
165
+ this.toggleRow(toggledRow);
166
+ }
167
+ }else{
168
+ this.toggleRow(toggledRow);
169
+ }
170
+ }
171
+ });
172
+ this.lastClickedRow = row;
173
+ }else{
174
+ this.deselectRows(undefined, true);
175
+
176
+ if(this.table.options.selectable !== true){
177
+ if(toggledRows.length > this.table.options.selectable){
178
+ toggledRows = toggledRows.slice(0, this.table.options.selectable);
179
+ }
180
+ }
181
+
182
+ this.selectRows(toggledRows);
183
+ }
184
+ this.table._clearSelection();
185
+ }
186
+ else if(e.ctrlKey || e.metaKey){
187
+ this.toggleRow(row);
188
+ this.lastClickedRow = row;
189
+ }else{
190
+ this.deselectRows(undefined, true);
191
+ this.selectRows(row);
192
+ this.lastClickedRow = row;
193
+ }
194
+ }
195
+
196
+ checkRowSelectability(row){
197
+ if(row && row.type === "row"){
198
+ return this.table.options.selectableCheck.call(this.table, row.getComponent());
199
+ }
200
+
201
+ return false;
202
+ }
203
+
204
+ //toggle row selection
205
+ toggleRow(row){
206
+ if(this.checkRowSelectability(row)){
207
+ if(row.modules.select && row.modules.select.selected){
208
+ this._deselectRow(row);
209
+ }else{
210
+ this._selectRow(row);
211
+ }
212
+ }
213
+ }
214
+
215
+ //select a number of rows
216
+ selectRows(rows){
217
+ var changes = [],
218
+ rowMatch, change;
219
+
220
+ switch(typeof rows){
221
+ case "undefined":
222
+ rowMatch = this.table.rowManager.rows;
223
+ break;
224
+
225
+ case "string":
226
+ rowMatch = this.table.rowManager.findRow(rows);
227
+
228
+ if(!rowMatch){
229
+ rowMatch = this.table.rowManager.getRows(rows);
230
+ }
231
+ break;
232
+
233
+ default:
234
+ rowMatch = rows;
235
+ break;
236
+ }
237
+
238
+ if(Array.isArray(rowMatch)){
239
+ if(rowMatch.length){
240
+ rowMatch.forEach((row) => {
241
+ change = this._selectRow(row, true, true);
242
+
243
+ if(change){
244
+ changes.push(change);
245
+ }
246
+ });
247
+
248
+ this._rowSelectionChanged(false, changes);
249
+ }
250
+ }else{
251
+ if(rowMatch){
252
+ this._selectRow(rowMatch, false, true);
253
+ }
254
+ }
255
+ }
256
+
257
+ //select an individual row
258
+ _selectRow(rowInfo, silent, force){
259
+ //handle max row count
260
+ if(!isNaN(this.table.options.selectable) && this.table.options.selectable !== true && !force){
261
+ if(this.selectedRows.length >= this.table.options.selectable){
262
+ if(this.table.options.selectableRollingSelection){
263
+ this._deselectRow(this.selectedRows[0]);
264
+ }else{
265
+ return false;
266
+ }
267
+ }
268
+ }
269
+
270
+ var row = this.table.rowManager.findRow(rowInfo);
271
+
272
+ if(row){
273
+ if(this.selectedRows.indexOf(row) == -1){
274
+ row.getElement().classList.add("tabulator-selected");
275
+ if(!row.modules.select){
276
+ row.modules.select = {};
277
+ }
278
+
279
+ row.modules.select.selected = true;
280
+ if(row.modules.select.checkboxEl){
281
+ row.modules.select.checkboxEl.checked = true;
282
+ }
283
+
284
+ this.selectedRows.push(row);
285
+
286
+ if(this.table.options.dataTreeSelectPropagate){
287
+ this.childRowSelection(row, true);
288
+ }
289
+
290
+ this.dispatchExternal("rowSelected", row.getComponent());
291
+
292
+ this._rowSelectionChanged(silent, row);
293
+
294
+ return row;
295
+ }
296
+ }else{
297
+ if(!silent){
298
+ console.warn("Selection Error - No such row found, ignoring selection:" + rowInfo);
299
+ }
300
+ }
301
+ }
302
+
303
+ isRowSelected(row){
304
+ return this.selectedRows.indexOf(row) !== -1;
305
+ }
306
+
307
+ //deselect a number of rows
308
+ deselectRows(rows, silent){
309
+ var changes = [],
310
+ rowMatch, change;
311
+
312
+ switch(typeof rows){
313
+ case "undefined":
314
+ rowMatch = Object.assign([], this.selectedRows);
315
+ break;
316
+
317
+ case "string":
318
+ rowMatch = this.table.rowManager.findRow(rows);
319
+
320
+ if(!rowMatch){
321
+ rowMatch = this.table.rowManager.getRows(rows);
322
+ }
323
+ break;
324
+
325
+ default:
326
+ rowMatch = rows;
327
+ break;
328
+ }
329
+
330
+ if(Array.isArray(rowMatch)){
331
+ if(rowMatch.length){
332
+ rowMatch.forEach((row) => {
333
+ change = this._deselectRow(row, true, true);
334
+
335
+ if(change){
336
+ changes.push(change);
337
+ }
338
+ });
339
+
340
+ this._rowSelectionChanged(silent, [], changes);
341
+ }
342
+ }else{
343
+ if(rowMatch){
344
+ this._deselectRow(rowMatch, silent, true);
345
+ }
346
+ }
347
+ }
348
+
349
+ //deselect an individual row
350
+ _deselectRow(rowInfo, silent){
351
+ var self = this,
352
+ row = self.table.rowManager.findRow(rowInfo),
353
+ index, element;
354
+
355
+ if(row){
356
+ index = self.selectedRows.findIndex(function(selectedRow){
357
+ return selectedRow == row;
358
+ });
359
+
360
+ if(index > -1){
361
+
362
+ element = row.getElement();
363
+
364
+ if(element){
365
+ element.classList.remove("tabulator-selected");
366
+ }
367
+
368
+ if(!row.modules.select){
369
+ row.modules.select = {};
370
+ }
371
+
372
+ row.modules.select.selected = false;
373
+ if(row.modules.select.checkboxEl){
374
+ row.modules.select.checkboxEl.checked = false;
375
+ }
376
+ self.selectedRows.splice(index, 1);
377
+
378
+ if(this.table.options.dataTreeSelectPropagate){
379
+ this.childRowSelection(row, false);
380
+ }
381
+
382
+ this.dispatchExternal("rowDeselected", row.getComponent());
383
+
384
+ self._rowSelectionChanged(silent, undefined, row);
385
+
386
+ return row;
387
+ }
388
+ }else{
389
+ if(!silent){
390
+ console.warn("Deselection Error - No such row found, ignoring selection:" + rowInfo);
391
+ }
392
+ }
393
+ }
394
+
395
+ getSelectedData(){
396
+ var data = [];
397
+
398
+ this.selectedRows.forEach(function(row){
399
+ data.push(row.getData());
400
+ });
401
+
402
+ return data;
403
+ }
404
+
405
+ getSelectedRows(){
406
+ var rows = [];
407
+
408
+ this.selectedRows.forEach(function(row){
409
+ rows.push(row.getComponent());
410
+ });
411
+
412
+ return rows;
413
+ }
414
+
415
+ _rowSelectionChanged(silent, selected = [], deselected = []){
416
+ if(this.headerCheckboxElement){
417
+ if(this.selectedRows.length === 0){
418
+ this.headerCheckboxElement.checked = false;
419
+ this.headerCheckboxElement.indeterminate = false;
420
+ } else if(this.table.rowManager.rows.length === this.selectedRows.length){
421
+ this.headerCheckboxElement.checked = true;
422
+ this.headerCheckboxElement.indeterminate = false;
423
+ } else {
424
+ this.headerCheckboxElement.indeterminate = true;
425
+ this.headerCheckboxElement.checked = false;
426
+ }
427
+ }
428
+
429
+ if(!silent){
430
+ if(!Array.isArray(selected)){
431
+ selected = [selected];
432
+ }
433
+
434
+ selected = selected.map(row => row.getComponent());
435
+
436
+ if(!Array.isArray(deselected)){
437
+ deselected = [deselected];
438
+ }
439
+
440
+ deselected = deselected.map(row => row.getComponent());
441
+
442
+ this.dispatchExternal("rowSelectionChanged", this.getSelectedData(), this.getSelectedRows(), selected, deselected);
443
+ }
444
+ }
445
+
446
+ registerRowSelectCheckbox (row, element) {
447
+ if(!row._row.modules.select){
448
+ row._row.modules.select = {};
449
+ }
450
+
451
+ row._row.modules.select.checkboxEl = element;
452
+ }
453
+
454
+ registerHeaderSelectCheckbox (element) {
455
+ this.headerCheckboxElement = element;
456
+ }
457
+
458
+ childRowSelection(row, select){
459
+ var children = this.table.modules.dataTree.getChildren(row, true);
460
+
461
+ if(select){
462
+ for(let child of children){
463
+ this._selectRow(child, true);
464
+ }
465
+ }else{
466
+ for(let child of children){
467
+ this._deselectRow(child, true);
468
+ }
469
+ }
470
+ }
471
+ }
472
+
473
+ SelectRow.moduleName = "selectRow";
474
+
445
475
  export default SelectRow;