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,640 +1,640 @@
1
- import Module from '../../core/Module.js';
2
-
3
- import Group from './Group.js';
4
-
5
- class GroupRows extends Module{
6
-
7
- constructor(table){
8
- super(table);
9
-
10
- this.groupIDLookups = false; //enable table grouping and set field to group by
11
- this.startOpen = [function(){return false;}]; //starting state of group
12
- this.headerGenerator = [function(){return "";}];
13
- this.groupList = []; //ordered list of groups
14
- this.allowedValues = false;
15
- this.groups = {}; //hold row groups
16
-
17
- this.displayHandler = this.getRows.bind(this);
18
-
19
- this.blockRedraw = false;
20
-
21
- //register table options
22
- this.registerTableOption("groupBy", false); //enable table grouping and set field to group by
23
- this.registerTableOption("groupStartOpen", true); //starting state of group
24
- this.registerTableOption("groupValues", false);
25
- this.registerTableOption("groupUpdateOnCellEdit", false);
26
- this.registerTableOption("groupHeader", false); //header generation function
27
- this.registerTableOption("groupHeaderPrint", null);
28
- this.registerTableOption("groupHeaderClipboard", null);
29
- this.registerTableOption("groupHeaderHtmlOutput", null);
30
- this.registerTableOption("groupHeaderDownload", null);
31
- this.registerTableOption("groupToggleElement", "arrow");
32
- this.registerTableOption("groupClosedShowCalcs", false);
33
-
34
- //register table functions
35
- this.registerTableFunction("setGroupBy", this.setGroupBy.bind(this));
36
- this.registerTableFunction("setGroupValues", this.setGroupValues.bind(this));
37
- this.registerTableFunction("setGroupStartOpen", this.setGroupStartOpen.bind(this));
38
- this.registerTableFunction("setGroupHeader", this.setGroupHeader.bind(this));
39
- this.registerTableFunction("getGroups", this.userGetGroups.bind(this));
40
- this.registerTableFunction("getGroupedData", this.userGetGroupedData.bind(this));
41
-
42
- //register component functions
43
- this.registerComponentFunction("row", "getGroup", this.rowGetGroup.bind(this));
44
- }
45
-
46
- //initialize group configuration
47
- initialize(){
48
- this.subscribe("table-destroy", this._blockRedrawing.bind(this));
49
- this.subscribe("rows-wipe", this._blockRedrawing.bind(this));
50
- this.subscribe("rows-wiped", this._restore_redrawing.bind(this));
51
-
52
- if(this.table.options.groupBy){
53
- if(this.table.options.groupUpdateOnCellEdit){
54
- this.subscribe("cell-value-updated", this.cellUpdated.bind(this));
55
- this.subscribe("row-data-changed", this.reassignRowToGroup.bind(this), 0);
56
- }
57
-
58
- this.subscribe("table-built", this.configureGroupSetup.bind(this));
59
-
60
- this.subscribe("row-deleting", this.rowDeleting.bind(this));
61
- this.subscribe("row-deleted", this.rowsUpdated.bind(this));
62
- this.subscribe("scroll-horizontal", this.scrollHeaders.bind(this));
63
- this.subscribe("rows-wipe", this.wipe.bind(this));
64
- this.subscribe("rows-added", this.rowsUpdated.bind(this));
65
- this.subscribe("row-moving", this.rowMoving.bind(this));
66
- this.subscribe("row-adding-index", this.rowAddingIndex.bind(this));
67
-
68
- this.subscribe("rows-sample", this.rowSample.bind(this));
69
-
70
- this.subscribe("render-virtual-fill", this.virtualRenderFill.bind(this));
71
-
72
- this.registerDisplayHandler(this.displayHandler, 20);
73
-
74
- this.initialized = true;
75
- }
76
- }
77
-
78
- _blockRedrawing(){
79
- this.blockRedraw = true;
80
- }
81
-
82
- _restore_redrawing(){
83
- this.blockRedraw = false;
84
- }
85
-
86
- configureGroupSetup(){
87
- if(this.table.options.groupBy){
88
- var groupBy = this.table.options.groupBy,
89
- startOpen = this.table.options.groupStartOpen,
90
- groupHeader = this.table.options.groupHeader;
91
-
92
- this.allowedValues = this.table.options.groupValues;
93
-
94
- if(Array.isArray(groupBy) && Array.isArray(groupHeader) && groupBy.length > groupHeader.length){
95
- console.warn("Error creating group headers, groupHeader array is shorter than groupBy array");
96
- }
97
-
98
- this.headerGenerator = [function(){return "";}];
99
- this.startOpen = [function(){return false;}]; //starting state of group
100
-
101
- this.langBind("groups|item", (langValue, lang) => {
102
- this.headerGenerator[0] = (value, count, data) => { //header layout function
103
- return (typeof value === "undefined" ? "" : value) + "<span>(" + count + " " + ((count === 1) ? langValue : lang.groups.items) + ")</span>";
104
- };
105
- });
106
-
107
- this.groupIDLookups = [];
108
-
109
- if(groupBy){
110
- if(this.table.modExists("columnCalcs") && this.table.options.columnCalcs != "table" && this.table.options.columnCalcs != "both"){
111
- this.table.modules.columnCalcs.removeCalcs();
112
- }
113
- }else{
114
- if(this.table.modExists("columnCalcs") && this.table.options.columnCalcs != "group"){
115
-
116
- var cols = this.table.columnManager.getRealColumns();
117
-
118
- cols.forEach((col) => {
119
- if(col.definition.topCalc){
120
- this.table.modules.columnCalcs.initializeTopRow();
121
- }
122
-
123
- if(col.definition.bottomCalc){
124
- this.table.modules.columnCalcs.initializeBottomRow();
125
- }
126
- });
127
- }
128
- }
129
-
130
- if(!Array.isArray(groupBy)){
131
- groupBy = [groupBy];
132
- }
133
-
134
- groupBy.forEach((group, i) => {
135
- var lookupFunc, column;
136
-
137
- if(typeof group == "function"){
138
- lookupFunc = group;
139
- }else{
140
- column = this.table.columnManager.getColumnByField(group);
141
-
142
- if(column){
143
- lookupFunc = function(data){
144
- return column.getFieldValue(data);
145
- };
146
- }else{
147
- lookupFunc = function(data){
148
- return data[group];
149
- };
150
- }
151
- }
152
-
153
- this.groupIDLookups.push({
154
- field: typeof group === "function" ? false : group,
155
- func:lookupFunc,
156
- values:this.allowedValues ? this.allowedValues[i] : false,
157
- });
158
- });
159
-
160
- if(startOpen){
161
- if(!Array.isArray(startOpen)){
162
- startOpen = [startOpen];
163
- }
164
-
165
- startOpen.forEach((level) => {
166
- level = typeof level == "function" ? level : function(){return true;};
167
- });
168
-
169
- this.startOpen = startOpen;
170
- }
171
-
172
- if(groupHeader){
173
- this.headerGenerator = Array.isArray(groupHeader) ? groupHeader : [groupHeader];
174
- }
175
- }else{
176
- this.groupList = [];
177
- this.groups = {};
178
- }
179
- }
180
-
181
- rowSample(rows, prevValue){
182
- if(this.table.options.groupBy){
183
- var group = this.getGroups(false)[0];
184
-
185
- prevValue.push(group.getRows(false)[0]);
186
- }
187
-
188
- return prevValue;
189
- }
190
-
191
- virtualRenderFill(){
192
- var el = this.table.rowManager.tableElement;
193
- var rows = this.table.rowManager.getVisibleRows();
194
-
195
- if(this.table.options.groupBy){
196
- rows = rows.filter((row) => {
197
- return row.type !== "group";
198
- });
199
-
200
- el.style.minWidth = !rows.length ? this.table.columnManager.getWidth() + "px" : "";
201
- }else{
202
- return rows;
203
- }
204
- }
205
-
206
- rowAddingIndex(row, index, top){
207
- if(this.table.options.groupBy){
208
- this.assignRowToGroup(row);
209
-
210
- var groupRows = row.modules.group.rows;
211
-
212
- if(groupRows.length > 1){
213
- if(!index || (index && groupRows.indexOf(index) == -1)){
214
- if(top){
215
- if(groupRows[0] !== row){
216
- index = groupRows[0];
217
- this.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);
218
- }
219
- }else{
220
- if(groupRows[groupRows.length -1] !== row){
221
- index = groupRows[groupRows.length -1];
222
- this.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);
223
- }
224
- }
225
- }else{
226
- this.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);
227
- }
228
- }
229
-
230
- return index;
231
- }
232
- }
233
-
234
- trackChanges(){
235
- this.dispatch("group-changed");
236
- }
237
-
238
- ///////////////////////////////////
239
- ///////// Table Functions /////////
240
- ///////////////////////////////////
241
-
242
- setGroupBy(groups){
243
- this.table.options.groupBy = groups;
244
-
245
- if(!this.initialized){
246
- this.initialize();
247
- }
248
-
249
- this.configureGroupSetup();
250
-
251
- if(!groups && this.table.modExists("columnCalcs") && this.table.options.columnCalcs === true){
252
- this.table.modules.columnCalcs.reinitializeCalcs();
253
- }
254
-
255
- this.refreshData();
256
-
257
- this.trackChanges();
258
- }
259
-
260
- setGroupValues(groupValues){
261
- this.table.options.groupValues = groupValues;
262
- this.configureGroupSetup();
263
- this.refreshData();
264
-
265
- this.trackChanges();
266
- }
267
-
268
- setGroupStartOpen(values){
269
- this.table.options.groupStartOpen = values;
270
- this.configureGroupSetup();
271
-
272
- if(this.table.options.groupBy){
273
- this.refreshData();
274
-
275
- this.trackChanges();
276
- }else{
277
- console.warn("Grouping Update - cant refresh view, no groups have been set");
278
- }
279
- }
280
-
281
- setGroupHeader(values){
282
- this.table.options.groupHeader = values;
283
- this.configureGroupSetup();
284
-
285
- if(this.table.options.groupBy){
286
- this.refreshData();
287
-
288
- this.trackChanges();
289
- }else{
290
- console.warn("Grouping Update - cant refresh view, no groups have been set");
291
- }
292
- }
293
-
294
- userGetGroups(values){
295
- return this.getGroups(true);
296
- }
297
-
298
- // get grouped table data in the same format as getData()
299
- userGetGroupedData(){
300
- return this.table.options.groupBy ? this.getGroupedData() : this.getData();
301
- }
302
-
303
-
304
- ///////////////////////////////////////
305
- ///////// Component Functions /////////
306
- ///////////////////////////////////////
307
-
308
- rowGetGroup(row){
309
- return row.modules.group ? row.modules.group.getComponent() : false;
310
- }
311
-
312
- ///////////////////////////////////
313
- ///////// Internal Logic //////////
314
- ///////////////////////////////////
315
-
316
- rowMoving(from, to, after){
317
- if(this.table.options.groupBy){
318
- if(!after && to instanceof Group){
319
- to = this.table.rowManager.prevDisplayRow(from) || to;
320
- }
321
-
322
- var toGroup = to instanceof Group ? to : to.modules.group;
323
- var fromGroup = from instanceof Group ? from : from.modules.group;
324
-
325
- if(toGroup === fromGroup){
326
- this.table.rowManager.moveRowInArray(toGroup.rows, from, to, after);
327
- }else{
328
- if(fromGroup){
329
- fromGroup.removeRow(from);
330
- }
331
-
332
- toGroup.insertRow(from, to, after);
333
- }
334
- }
335
- }
336
-
337
-
338
- rowDeleting(row){
339
- //remove from group
340
- if(this.table.options.groupBy && row.modules.group){
341
- row.modules.group.removeRow(row);
342
- }
343
- }
344
-
345
- rowsUpdated(row){
346
- if(this.table.options.groupBy){
347
- this.updateGroupRows(true);
348
- }
349
- }
350
-
351
- cellUpdated(cell){
352
- if(this.table.options.groupBy){
353
- this.reassignRowToGroup(cell.row);
354
- }
355
- }
356
-
357
- //return appropriate rows with group headers
358
- getRows(rows){
359
- if(this.table.options.groupBy && this.groupIDLookups.length){
360
-
361
- this.dispatchExternal("dataGrouping");
362
-
363
- this.generateGroups(rows);
364
-
365
- if(this.subscribedExternal("dataGrouped")){
366
- this.dispatchExternal("dataGrouped", this.getGroups(true));
367
- }
368
-
369
- return this.updateGroupRows();
370
-
371
- }else{
372
- return rows.slice(0);
373
- }
374
- }
375
-
376
- getGroups(component){
377
- var groupComponents = [];
378
-
379
- this.groupList.forEach(function(group){
380
- groupComponents.push(component ? group.getComponent() : group);
381
- });
382
-
383
- return groupComponents;
384
- }
385
-
386
- getChildGroups(group){
387
- var groupComponents = [];
388
-
389
- if(!group){
390
- group = this;
391
- }
392
-
393
- group.groupList.forEach((child) => {
394
- if(child.groupList.length){
395
- groupComponents = groupComponents.concat(this.getChildGroups(child));
396
- }else{
397
- groupComponents.push(child);
398
- }
399
- });
400
-
401
- return groupComponents;
402
- }
403
-
404
- wipe(){
405
- if(this.table.options.groupBy){
406
- this.groupList.forEach(function(group){
407
- group.wipe();
408
- });
409
-
410
- this.groupList = [];
411
- this.groups = {};
412
- }
413
- }
414
-
415
- pullGroupListData(groupList) {
416
- var groupListData = [];
417
-
418
- groupList.forEach((group) => {
419
- var groupHeader = {};
420
- groupHeader.level = 0;
421
- groupHeader.rowCount = 0;
422
- groupHeader.headerContent = "";
423
- var childData = [];
424
-
425
- if (group.hasSubGroups) {
426
- childData = this.pullGroupListData(group.groupList);
427
-
428
- groupHeader.level = group.level;
429
- groupHeader.rowCount = childData.length - group.groupList.length; // data length minus number of sub-headers
430
- groupHeader.headerContent = group.generator(group.key, groupHeader.rowCount, group.rows, group);
431
-
432
- groupListData.push(groupHeader);
433
- groupListData = groupListData.concat(childData);
434
- }
435
-
436
- else {
437
- groupHeader.level = group.level;
438
- groupHeader.headerContent = group.generator(group.key, group.rows.length, group.rows, group);
439
- groupHeader.rowCount = group.getRows().length;
440
-
441
- groupListData.push(groupHeader);
442
-
443
- group.getRows().forEach((row) => {
444
- groupListData.push(row.getData("data"));
445
- });
446
- }
447
- });
448
-
449
- return groupListData;
450
- }
451
-
452
- getGroupedData(){
453
-
454
- return this.pullGroupListData(this.groupList);
455
- }
456
-
457
- getRowGroup(row){
458
- var match = false;
459
-
460
- if(this.options("dataTree")){
461
- row = this.table.modules.dataTree.getTreeParentRoot(row);
462
- }
463
-
464
- this.groupList.forEach((group) => {
465
- var result = group.getRowGroup(row);
466
-
467
- if(result){
468
- match = result;
469
- }
470
- });
471
-
472
- return match;
473
- }
474
-
475
- countGroups(){
476
- return this.groupList.length;
477
- }
478
-
479
- generateGroups(rows){
480
- var oldGroups = this.groups;
481
-
482
- this.groups = {};
483
- this.groupList = [];
484
-
485
- if(this.allowedValues && this.allowedValues[0]){
486
- this.allowedValues[0].forEach((value) => {
487
- this.createGroup(value, 0, oldGroups);
488
- });
489
-
490
- rows.forEach((row) => {
491
- this.assignRowToExistingGroup(row, oldGroups);
492
- });
493
- }else{
494
- rows.forEach((row) => {
495
- this.assignRowToGroup(row, oldGroups);
496
- });
497
- }
498
-
499
- Object.values(oldGroups).forEach((group) => {
500
- group.wipe(true);
501
- });
502
- }
503
-
504
-
505
- createGroup(groupID, level, oldGroups){
506
- var groupKey = level + "_" + groupID,
507
- group;
508
-
509
- oldGroups = oldGroups || [];
510
-
511
- group = new Group(this, false, level, groupID, this.groupIDLookups[0].field, this.headerGenerator[0], oldGroups[groupKey]);
512
-
513
- this.groups[groupKey] = group;
514
- this.groupList.push(group);
515
- }
516
-
517
- assignRowToExistingGroup(row, oldGroups){
518
- var groupID = this.groupIDLookups[0].func(row.getData()),
519
- groupKey = "0_" + groupID;
520
-
521
- if(this.groups[groupKey]){
522
- this.groups[groupKey].addRow(row);
523
- }
524
- }
525
-
526
- assignRowToGroup(row, oldGroups){
527
- var groupID = this.groupIDLookups[0].func(row.getData()),
528
- newGroupNeeded = !this.groups["0_" + groupID];
529
-
530
- if(newGroupNeeded){
531
- this.createGroup(groupID, 0, oldGroups);
532
- }
533
-
534
- this.groups["0_" + groupID].addRow(row);
535
-
536
- return !newGroupNeeded;
537
- }
538
-
539
- reassignRowToGroup(row){
540
- if(row.type === "row"){
541
- var oldRowGroup = row.modules.group,
542
- oldGroupPath = oldRowGroup.getPath(),
543
- newGroupPath = this.getExpectedPath(row),
544
- samePath;
545
-
546
- // figure out if new group path is the same as old group path
547
- samePath = (oldGroupPath.length == newGroupPath.length) && oldGroupPath.every((element, index) => {
548
- return element === newGroupPath[index];
549
- });
550
-
551
- // refresh if they new path and old path aren't the same (aka the row's groupings have changed)
552
- if(!samePath) {
553
- oldRowGroup.removeRow(row);
554
- this.assignRowToGroup(row, this.groups);
555
- this.refreshData(true);
556
- }
557
- }
558
- }
559
-
560
- getExpectedPath(row) {
561
- var groupPath = [], rowData = row.getData();
562
-
563
- this.groupIDLookups.forEach((groupId) => {
564
- groupPath.push(groupId.func(rowData));
565
- });
566
-
567
- return groupPath;
568
- }
569
-
570
- updateGroupRows(force){
571
- var output = [];
572
-
573
- if(!this.blockRedraw){
574
- this.groupList.forEach((group) => {
575
- output = output.concat(group.getHeadersAndRows());
576
- });
577
-
578
- if(force){
579
- this.refreshData(true);
580
- }
581
- }
582
-
583
- return output;
584
- }
585
-
586
- scrollHeaders(left){
587
- if(this.table.options.groupBy){
588
- if(this.table.options.renderHorizontal === "virtual"){
589
- left -= this.table.columnManager.renderer.vDomPadLeft;
590
- }
591
-
592
- left = left + "px";
593
-
594
- this.groupList.forEach((group) => {
595
- group.scrollHeader(left);
596
- });
597
- }
598
- }
599
-
600
- removeGroup(group){
601
- var groupKey = group.level + "_" + group.key,
602
- index;
603
-
604
- if(this.groups[groupKey]){
605
- delete this.groups[groupKey];
606
-
607
- index = this.groupList.indexOf(group);
608
-
609
- if(index > -1){
610
- this.groupList.splice(index, 1);
611
- }
612
- }
613
- }
614
-
615
- checkBasicModeGroupHeaderWidth(){
616
- var element = this.table.rowManager.tableElement,
617
- onlyGroupHeaders = true;
618
-
619
- this.table.rowManager.getDisplayRows().forEach((row, index) =>{
620
- this.table.rowManager.styleRow(row, index);
621
- element.appendChild(row.getElement());
622
- row.initialize(true);
623
-
624
- if(row.type !== "group"){
625
- onlyGroupHeaders = false;
626
- }
627
- });
628
-
629
- if(onlyGroupHeaders){
630
- element.style.minWidth = this.table.columnManager.getWidth() + "px";
631
- }else{
632
- element.style.minWidth = "";
633
- }
634
- }
635
-
636
- }
637
-
638
- GroupRows.moduleName = "groupRows";
639
-
1
+ import Module from '../../core/Module.js';
2
+
3
+ import Group from './Group.js';
4
+
5
+ class GroupRows extends Module{
6
+
7
+ constructor(table){
8
+ super(table);
9
+
10
+ this.groupIDLookups = false; //enable table grouping and set field to group by
11
+ this.startOpen = [function(){return false;}]; //starting state of group
12
+ this.headerGenerator = [function(){return "";}];
13
+ this.groupList = []; //ordered list of groups
14
+ this.allowedValues = false;
15
+ this.groups = {}; //hold row groups
16
+
17
+ this.displayHandler = this.getRows.bind(this);
18
+
19
+ this.blockRedraw = false;
20
+
21
+ //register table options
22
+ this.registerTableOption("groupBy", false); //enable table grouping and set field to group by
23
+ this.registerTableOption("groupStartOpen", true); //starting state of group
24
+ this.registerTableOption("groupValues", false);
25
+ this.registerTableOption("groupUpdateOnCellEdit", false);
26
+ this.registerTableOption("groupHeader", false); //header generation function
27
+ this.registerTableOption("groupHeaderPrint", null);
28
+ this.registerTableOption("groupHeaderClipboard", null);
29
+ this.registerTableOption("groupHeaderHtmlOutput", null);
30
+ this.registerTableOption("groupHeaderDownload", null);
31
+ this.registerTableOption("groupToggleElement", "arrow");
32
+ this.registerTableOption("groupClosedShowCalcs", false);
33
+
34
+ //register table functions
35
+ this.registerTableFunction("setGroupBy", this.setGroupBy.bind(this));
36
+ this.registerTableFunction("setGroupValues", this.setGroupValues.bind(this));
37
+ this.registerTableFunction("setGroupStartOpen", this.setGroupStartOpen.bind(this));
38
+ this.registerTableFunction("setGroupHeader", this.setGroupHeader.bind(this));
39
+ this.registerTableFunction("getGroups", this.userGetGroups.bind(this));
40
+ this.registerTableFunction("getGroupedData", this.userGetGroupedData.bind(this));
41
+
42
+ //register component functions
43
+ this.registerComponentFunction("row", "getGroup", this.rowGetGroup.bind(this));
44
+ }
45
+
46
+ //initialize group configuration
47
+ initialize(){
48
+ this.subscribe("table-destroy", this._blockRedrawing.bind(this));
49
+ this.subscribe("rows-wipe", this._blockRedrawing.bind(this));
50
+ this.subscribe("rows-wiped", this._restore_redrawing.bind(this));
51
+
52
+ if(this.table.options.groupBy){
53
+ if(this.table.options.groupUpdateOnCellEdit){
54
+ this.subscribe("cell-value-updated", this.cellUpdated.bind(this));
55
+ this.subscribe("row-data-changed", this.reassignRowToGroup.bind(this), 0);
56
+ }
57
+
58
+ this.subscribe("table-built", this.configureGroupSetup.bind(this));
59
+
60
+ this.subscribe("row-deleting", this.rowDeleting.bind(this));
61
+ this.subscribe("row-deleted", this.rowsUpdated.bind(this));
62
+ this.subscribe("scroll-horizontal", this.scrollHeaders.bind(this));
63
+ this.subscribe("rows-wipe", this.wipe.bind(this));
64
+ this.subscribe("rows-added", this.rowsUpdated.bind(this));
65
+ this.subscribe("row-moving", this.rowMoving.bind(this));
66
+ this.subscribe("row-adding-index", this.rowAddingIndex.bind(this));
67
+
68
+ this.subscribe("rows-sample", this.rowSample.bind(this));
69
+
70
+ this.subscribe("render-virtual-fill", this.virtualRenderFill.bind(this));
71
+
72
+ this.registerDisplayHandler(this.displayHandler, 20);
73
+
74
+ this.initialized = true;
75
+ }
76
+ }
77
+
78
+ _blockRedrawing(){
79
+ this.blockRedraw = true;
80
+ }
81
+
82
+ _restore_redrawing(){
83
+ this.blockRedraw = false;
84
+ }
85
+
86
+ configureGroupSetup(){
87
+ if(this.table.options.groupBy){
88
+ var groupBy = this.table.options.groupBy,
89
+ startOpen = this.table.options.groupStartOpen,
90
+ groupHeader = this.table.options.groupHeader;
91
+
92
+ this.allowedValues = this.table.options.groupValues;
93
+
94
+ if(Array.isArray(groupBy) && Array.isArray(groupHeader) && groupBy.length > groupHeader.length){
95
+ console.warn("Error creating group headers, groupHeader array is shorter than groupBy array");
96
+ }
97
+
98
+ this.headerGenerator = [function(){return "";}];
99
+ this.startOpen = [function(){return false;}]; //starting state of group
100
+
101
+ this.langBind("groups|item", (langValue, lang) => {
102
+ this.headerGenerator[0] = (value, count, data) => { //header layout function
103
+ return (typeof value === "undefined" ? "" : value) + "<span>(" + count + " " + ((count === 1) ? langValue : lang.groups.items) + ")</span>";
104
+ };
105
+ });
106
+
107
+ this.groupIDLookups = [];
108
+
109
+ if(groupBy){
110
+ if(this.table.modExists("columnCalcs") && this.table.options.columnCalcs != "table" && this.table.options.columnCalcs != "both"){
111
+ this.table.modules.columnCalcs.removeCalcs();
112
+ }
113
+ }else{
114
+ if(this.table.modExists("columnCalcs") && this.table.options.columnCalcs != "group"){
115
+
116
+ var cols = this.table.columnManager.getRealColumns();
117
+
118
+ cols.forEach((col) => {
119
+ if(col.definition.topCalc){
120
+ this.table.modules.columnCalcs.initializeTopRow();
121
+ }
122
+
123
+ if(col.definition.bottomCalc){
124
+ this.table.modules.columnCalcs.initializeBottomRow();
125
+ }
126
+ });
127
+ }
128
+ }
129
+
130
+ if(!Array.isArray(groupBy)){
131
+ groupBy = [groupBy];
132
+ }
133
+
134
+ groupBy.forEach((group, i) => {
135
+ var lookupFunc, column;
136
+
137
+ if(typeof group == "function"){
138
+ lookupFunc = group;
139
+ }else{
140
+ column = this.table.columnManager.getColumnByField(group);
141
+
142
+ if(column){
143
+ lookupFunc = function(data){
144
+ return column.getFieldValue(data);
145
+ };
146
+ }else{
147
+ lookupFunc = function(data){
148
+ return data[group];
149
+ };
150
+ }
151
+ }
152
+
153
+ this.groupIDLookups.push({
154
+ field: typeof group === "function" ? false : group,
155
+ func:lookupFunc,
156
+ values:this.allowedValues ? this.allowedValues[i] : false,
157
+ });
158
+ });
159
+
160
+ if(startOpen){
161
+ if(!Array.isArray(startOpen)){
162
+ startOpen = [startOpen];
163
+ }
164
+
165
+ startOpen.forEach((level) => {
166
+ level = typeof level == "function" ? level : function(){return true;};
167
+ });
168
+
169
+ this.startOpen = startOpen;
170
+ }
171
+
172
+ if(groupHeader){
173
+ this.headerGenerator = Array.isArray(groupHeader) ? groupHeader : [groupHeader];
174
+ }
175
+ }else{
176
+ this.groupList = [];
177
+ this.groups = {};
178
+ }
179
+ }
180
+
181
+ rowSample(rows, prevValue){
182
+ if(this.table.options.groupBy){
183
+ var group = this.getGroups(false)[0];
184
+
185
+ prevValue.push(group.getRows(false)[0]);
186
+ }
187
+
188
+ return prevValue;
189
+ }
190
+
191
+ virtualRenderFill(){
192
+ var el = this.table.rowManager.tableElement;
193
+ var rows = this.table.rowManager.getVisibleRows();
194
+
195
+ if(this.table.options.groupBy){
196
+ rows = rows.filter((row) => {
197
+ return row.type !== "group";
198
+ });
199
+
200
+ el.style.minWidth = !rows.length ? this.table.columnManager.getWidth() + "px" : "";
201
+ }else{
202
+ return rows;
203
+ }
204
+ }
205
+
206
+ rowAddingIndex(row, index, top){
207
+ if(this.table.options.groupBy){
208
+ this.assignRowToGroup(row);
209
+
210
+ var groupRows = row.modules.group.rows;
211
+
212
+ if(groupRows.length > 1){
213
+ if(!index || (index && groupRows.indexOf(index) == -1)){
214
+ if(top){
215
+ if(groupRows[0] !== row){
216
+ index = groupRows[0];
217
+ this.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);
218
+ }
219
+ }else{
220
+ if(groupRows[groupRows.length -1] !== row){
221
+ index = groupRows[groupRows.length -1];
222
+ this.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);
223
+ }
224
+ }
225
+ }else{
226
+ this.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);
227
+ }
228
+ }
229
+
230
+ return index;
231
+ }
232
+ }
233
+
234
+ trackChanges(){
235
+ this.dispatch("group-changed");
236
+ }
237
+
238
+ ///////////////////////////////////
239
+ ///////// Table Functions /////////
240
+ ///////////////////////////////////
241
+
242
+ setGroupBy(groups){
243
+ this.table.options.groupBy = groups;
244
+
245
+ if(!this.initialized){
246
+ this.initialize();
247
+ }
248
+
249
+ this.configureGroupSetup();
250
+
251
+ if(!groups && this.table.modExists("columnCalcs") && this.table.options.columnCalcs === true){
252
+ this.table.modules.columnCalcs.reinitializeCalcs();
253
+ }
254
+
255
+ this.refreshData();
256
+
257
+ this.trackChanges();
258
+ }
259
+
260
+ setGroupValues(groupValues){
261
+ this.table.options.groupValues = groupValues;
262
+ this.configureGroupSetup();
263
+ this.refreshData();
264
+
265
+ this.trackChanges();
266
+ }
267
+
268
+ setGroupStartOpen(values){
269
+ this.table.options.groupStartOpen = values;
270
+ this.configureGroupSetup();
271
+
272
+ if(this.table.options.groupBy){
273
+ this.refreshData();
274
+
275
+ this.trackChanges();
276
+ }else{
277
+ console.warn("Grouping Update - cant refresh view, no groups have been set");
278
+ }
279
+ }
280
+
281
+ setGroupHeader(values){
282
+ this.table.options.groupHeader = values;
283
+ this.configureGroupSetup();
284
+
285
+ if(this.table.options.groupBy){
286
+ this.refreshData();
287
+
288
+ this.trackChanges();
289
+ }else{
290
+ console.warn("Grouping Update - cant refresh view, no groups have been set");
291
+ }
292
+ }
293
+
294
+ userGetGroups(values){
295
+ return this.getGroups(true);
296
+ }
297
+
298
+ // get grouped table data in the same format as getData()
299
+ userGetGroupedData(){
300
+ return this.table.options.groupBy ? this.getGroupedData() : this.getData();
301
+ }
302
+
303
+
304
+ ///////////////////////////////////////
305
+ ///////// Component Functions /////////
306
+ ///////////////////////////////////////
307
+
308
+ rowGetGroup(row){
309
+ return row.modules.group ? row.modules.group.getComponent() : false;
310
+ }
311
+
312
+ ///////////////////////////////////
313
+ ///////// Internal Logic //////////
314
+ ///////////////////////////////////
315
+
316
+ rowMoving(from, to, after){
317
+ if(this.table.options.groupBy){
318
+ if(!after && to instanceof Group){
319
+ to = this.table.rowManager.prevDisplayRow(from) || to;
320
+ }
321
+
322
+ var toGroup = to instanceof Group ? to : to.modules.group;
323
+ var fromGroup = from instanceof Group ? from : from.modules.group;
324
+
325
+ if(toGroup === fromGroup){
326
+ this.table.rowManager.moveRowInArray(toGroup.rows, from, to, after);
327
+ }else{
328
+ if(fromGroup){
329
+ fromGroup.removeRow(from);
330
+ }
331
+
332
+ toGroup.insertRow(from, to, after);
333
+ }
334
+ }
335
+ }
336
+
337
+
338
+ rowDeleting(row){
339
+ //remove from group
340
+ if(this.table.options.groupBy && row.modules.group){
341
+ row.modules.group.removeRow(row);
342
+ }
343
+ }
344
+
345
+ rowsUpdated(row){
346
+ if(this.table.options.groupBy){
347
+ this.updateGroupRows(true);
348
+ }
349
+ }
350
+
351
+ cellUpdated(cell){
352
+ if(this.table.options.groupBy){
353
+ this.reassignRowToGroup(cell.row);
354
+ }
355
+ }
356
+
357
+ //return appropriate rows with group headers
358
+ getRows(rows){
359
+ if(this.table.options.groupBy && this.groupIDLookups.length){
360
+
361
+ this.dispatchExternal("dataGrouping");
362
+
363
+ this.generateGroups(rows);
364
+
365
+ if(this.subscribedExternal("dataGrouped")){
366
+ this.dispatchExternal("dataGrouped", this.getGroups(true));
367
+ }
368
+
369
+ return this.updateGroupRows();
370
+
371
+ }else{
372
+ return rows.slice(0);
373
+ }
374
+ }
375
+
376
+ getGroups(component){
377
+ var groupComponents = [];
378
+
379
+ this.groupList.forEach(function(group){
380
+ groupComponents.push(component ? group.getComponent() : group);
381
+ });
382
+
383
+ return groupComponents;
384
+ }
385
+
386
+ getChildGroups(group){
387
+ var groupComponents = [];
388
+
389
+ if(!group){
390
+ group = this;
391
+ }
392
+
393
+ group.groupList.forEach((child) => {
394
+ if(child.groupList.length){
395
+ groupComponents = groupComponents.concat(this.getChildGroups(child));
396
+ }else{
397
+ groupComponents.push(child);
398
+ }
399
+ });
400
+
401
+ return groupComponents;
402
+ }
403
+
404
+ wipe(){
405
+ if(this.table.options.groupBy){
406
+ this.groupList.forEach(function(group){
407
+ group.wipe();
408
+ });
409
+
410
+ this.groupList = [];
411
+ this.groups = {};
412
+ }
413
+ }
414
+
415
+ pullGroupListData(groupList) {
416
+ var groupListData = [];
417
+
418
+ groupList.forEach((group) => {
419
+ var groupHeader = {};
420
+ groupHeader.level = 0;
421
+ groupHeader.rowCount = 0;
422
+ groupHeader.headerContent = "";
423
+ var childData = [];
424
+
425
+ if (group.hasSubGroups) {
426
+ childData = this.pullGroupListData(group.groupList);
427
+
428
+ groupHeader.level = group.level;
429
+ groupHeader.rowCount = childData.length - group.groupList.length; // data length minus number of sub-headers
430
+ groupHeader.headerContent = group.generator(group.key, groupHeader.rowCount, group.rows, group);
431
+
432
+ groupListData.push(groupHeader);
433
+ groupListData = groupListData.concat(childData);
434
+ }
435
+
436
+ else {
437
+ groupHeader.level = group.level;
438
+ groupHeader.headerContent = group.generator(group.key, group.rows.length, group.rows, group);
439
+ groupHeader.rowCount = group.getRows().length;
440
+
441
+ groupListData.push(groupHeader);
442
+
443
+ group.getRows().forEach((row) => {
444
+ groupListData.push(row.getData("data"));
445
+ });
446
+ }
447
+ });
448
+
449
+ return groupListData;
450
+ }
451
+
452
+ getGroupedData(){
453
+
454
+ return this.pullGroupListData(this.groupList);
455
+ }
456
+
457
+ getRowGroup(row){
458
+ var match = false;
459
+
460
+ if(this.options("dataTree")){
461
+ row = this.table.modules.dataTree.getTreeParentRoot(row);
462
+ }
463
+
464
+ this.groupList.forEach((group) => {
465
+ var result = group.getRowGroup(row);
466
+
467
+ if(result){
468
+ match = result;
469
+ }
470
+ });
471
+
472
+ return match;
473
+ }
474
+
475
+ countGroups(){
476
+ return this.groupList.length;
477
+ }
478
+
479
+ generateGroups(rows){
480
+ var oldGroups = this.groups;
481
+
482
+ this.groups = {};
483
+ this.groupList = [];
484
+
485
+ if(this.allowedValues && this.allowedValues[0]){
486
+ this.allowedValues[0].forEach((value) => {
487
+ this.createGroup(value, 0, oldGroups);
488
+ });
489
+
490
+ rows.forEach((row) => {
491
+ this.assignRowToExistingGroup(row, oldGroups);
492
+ });
493
+ }else{
494
+ rows.forEach((row) => {
495
+ this.assignRowToGroup(row, oldGroups);
496
+ });
497
+ }
498
+
499
+ Object.values(oldGroups).forEach((group) => {
500
+ group.wipe(true);
501
+ });
502
+ }
503
+
504
+
505
+ createGroup(groupID, level, oldGroups){
506
+ var groupKey = level + "_" + groupID,
507
+ group;
508
+
509
+ oldGroups = oldGroups || [];
510
+
511
+ group = new Group(this, false, level, groupID, this.groupIDLookups[0].field, this.headerGenerator[0], oldGroups[groupKey]);
512
+
513
+ this.groups[groupKey] = group;
514
+ this.groupList.push(group);
515
+ }
516
+
517
+ assignRowToExistingGroup(row, oldGroups){
518
+ var groupID = this.groupIDLookups[0].func(row.getData()),
519
+ groupKey = "0_" + groupID;
520
+
521
+ if(this.groups[groupKey]){
522
+ this.groups[groupKey].addRow(row);
523
+ }
524
+ }
525
+
526
+ assignRowToGroup(row, oldGroups){
527
+ var groupID = this.groupIDLookups[0].func(row.getData()),
528
+ newGroupNeeded = !this.groups["0_" + groupID];
529
+
530
+ if(newGroupNeeded){
531
+ this.createGroup(groupID, 0, oldGroups);
532
+ }
533
+
534
+ this.groups["0_" + groupID].addRow(row);
535
+
536
+ return !newGroupNeeded;
537
+ }
538
+
539
+ reassignRowToGroup(row){
540
+ if(row.type === "row"){
541
+ var oldRowGroup = row.modules.group,
542
+ oldGroupPath = oldRowGroup.getPath(),
543
+ newGroupPath = this.getExpectedPath(row),
544
+ samePath;
545
+
546
+ // figure out if new group path is the same as old group path
547
+ samePath = (oldGroupPath.length == newGroupPath.length) && oldGroupPath.every((element, index) => {
548
+ return element === newGroupPath[index];
549
+ });
550
+
551
+ // refresh if they new path and old path aren't the same (aka the row's groupings have changed)
552
+ if(!samePath) {
553
+ oldRowGroup.removeRow(row);
554
+ this.assignRowToGroup(row, this.groups);
555
+ this.refreshData(true);
556
+ }
557
+ }
558
+ }
559
+
560
+ getExpectedPath(row) {
561
+ var groupPath = [], rowData = row.getData();
562
+
563
+ this.groupIDLookups.forEach((groupId) => {
564
+ groupPath.push(groupId.func(rowData));
565
+ });
566
+
567
+ return groupPath;
568
+ }
569
+
570
+ updateGroupRows(force){
571
+ var output = [];
572
+
573
+ if(!this.blockRedraw){
574
+ this.groupList.forEach((group) => {
575
+ output = output.concat(group.getHeadersAndRows());
576
+ });
577
+
578
+ if(force){
579
+ this.refreshData(true);
580
+ }
581
+ }
582
+
583
+ return output;
584
+ }
585
+
586
+ scrollHeaders(left){
587
+ if(this.table.options.groupBy){
588
+ if(this.table.options.renderHorizontal === "virtual"){
589
+ left -= this.table.columnManager.renderer.vDomPadLeft;
590
+ }
591
+
592
+ left = left + "px";
593
+
594
+ this.groupList.forEach((group) => {
595
+ group.scrollHeader(left);
596
+ });
597
+ }
598
+ }
599
+
600
+ removeGroup(group){
601
+ var groupKey = group.level + "_" + group.key,
602
+ index;
603
+
604
+ if(this.groups[groupKey]){
605
+ delete this.groups[groupKey];
606
+
607
+ index = this.groupList.indexOf(group);
608
+
609
+ if(index > -1){
610
+ this.groupList.splice(index, 1);
611
+ }
612
+ }
613
+ }
614
+
615
+ checkBasicModeGroupHeaderWidth(){
616
+ var element = this.table.rowManager.tableElement,
617
+ onlyGroupHeaders = true;
618
+
619
+ this.table.rowManager.getDisplayRows().forEach((row, index) =>{
620
+ this.table.rowManager.styleRow(row, index);
621
+ element.appendChild(row.getElement());
622
+ row.initialize(true);
623
+
624
+ if(row.type !== "group"){
625
+ onlyGroupHeaders = false;
626
+ }
627
+ });
628
+
629
+ if(onlyGroupHeaders){
630
+ element.style.minWidth = this.table.columnManager.getWidth() + "px";
631
+ }else{
632
+ element.style.minWidth = "";
633
+ }
634
+ }
635
+
636
+ }
637
+
638
+ GroupRows.moduleName = "groupRows";
639
+
640
640
  export default GroupRows;