@refinitiv-ui/efx-grid 6.0.16 → 6.0.18

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 (31) hide show
  1. package/lib/grid/index.js +1 -1
  2. package/lib/rt-grid/dist/rt-grid.js +177 -64
  3. package/lib/rt-grid/dist/rt-grid.min.js +1 -1
  4. package/lib/rt-grid/es6/ColumnDefinition.js +2 -1
  5. package/lib/rt-grid/es6/Grid.d.ts +12 -2
  6. package/lib/rt-grid/es6/Grid.js +152 -54
  7. package/lib/rt-grid/es6/RowDefinition.js +4 -0
  8. package/lib/tr-grid-column-grouping/es6/ColumnGrouping.d.ts +4 -4
  9. package/lib/tr-grid-column-grouping/es6/ColumnGrouping.js +344 -185
  10. package/lib/tr-grid-column-stack/es6/ColumnStack.d.ts +7 -1
  11. package/lib/tr-grid-column-stack/es6/ColumnStack.js +164 -147
  12. package/lib/tr-grid-filter-input/es6/FilterInput.d.ts +1 -0
  13. package/lib/tr-grid-filter-input/es6/FilterInput.js +27 -0
  14. package/lib/tr-grid-in-cell-editing/es6/InCellEditing.d.ts +44 -43
  15. package/lib/tr-grid-in-cell-editing/es6/InCellEditing.js +202 -497
  16. package/lib/tr-grid-row-grouping/es6/RowGrouping.d.ts +40 -40
  17. package/lib/types/es6/ColumnGrouping.d.ts +4 -4
  18. package/lib/types/es6/ColumnStack.d.ts +7 -1
  19. package/lib/types/es6/Core/data/Segment.d.ts +3 -3
  20. package/lib/types/es6/Core/data/SegmentCollection.d.ts +1 -1
  21. package/lib/types/es6/InCellEditing.d.ts +44 -43
  22. package/lib/types/es6/RealtimeGrid/ColumnDefinition.d.ts +10 -0
  23. package/lib/types/es6/RealtimeGrid/FieldDefinition.d.ts +6 -0
  24. package/lib/types/es6/RealtimeGrid/Grid.d.ts +13 -1
  25. package/lib/types/es6/RealtimeGrid/RowDefinition.d.ts +4 -0
  26. package/lib/types/es6/RealtimeGrid/SnapshotFiller.d.ts +1 -0
  27. package/lib/types/es6/RowColoring.d.ts +17 -15
  28. package/lib/types/es6/RowFiltering.d.ts +30 -29
  29. package/lib/types/es6/RowGrouping.d.ts +40 -40
  30. package/lib/versions.json +5 -5
  31. package/package.json +1 -1
@@ -31,6 +31,7 @@ var ColumnGroupingPlugin = function ColumnGroupingPlugin(options) {
31
31
  t._onColumnChanged = t._onColumnChanged.bind(t);
32
32
  t._onColumnAdded = t._onColumnAdded.bind(t);
33
33
  t._onColumnMoved = t._onColumnMoved.bind(t);
34
+ t._onColumnRemoved = t._onColumnRemoved.bind(t);
34
35
  t._requestApplyAddChildGroup = t._requestApplyAddChildGroup.bind(this);
35
36
  t._onPostSectionRender = t._onPostSectionRender.bind(t);
36
37
  t._onBeforeColumnBoundUpdate = t._onBeforeColumnBoundUpdate.bind(t);
@@ -60,6 +61,11 @@ ColumnGroupingPlugin.prototype._groupMap;
60
61
  * @private
61
62
  */
62
63
  ColumnGroupingPlugin.prototype._childToParent;
64
+ /** @type {!Object.<string, ColumnGroupingPlugin~GroupDefinition>}
65
+ * @description A map of visible group id to group defintion
66
+ * @private
67
+ */
68
+ ColumnGroupingPlugin.prototype._visibleGroupMap;
63
69
  /** @type {number}
64
70
  * @private
65
71
  */
@@ -99,20 +105,6 @@ ColumnGroupingPlugin._getTooltip = function (groupingOptions) {
99
105
  }
100
106
  return title;
101
107
  };
102
- /** Prevent built-in config
103
- * @public
104
- * @param {string} optionName
105
- * @param {Object} optionValue
106
- * @return {*}
107
- */
108
- ColumnGroupingPlugin.prototype.beforeProcessOption = function (optionName, optionValue) {
109
- if (optionName === "columnGroups") {
110
- this._legacyColumnGroups = optionValue;
111
- return false; // eslint-disable-line
112
- }
113
-
114
- return; // eslint-disable-line
115
- };
116
108
  /** @public
117
109
  * @return {string}
118
110
  */
@@ -142,7 +134,7 @@ ColumnGroupingPlugin.prototype.initialize = function (host, options) {
142
134
  if (this._hosts.length === 1) {
143
135
  host.listen("columnAdded", this._onColumnAdded);
144
136
  host.listen("columnMoved", this._onColumnMoved);
145
- host.listen("columnRemoved", this._onColumnChanged);
137
+ host.listen("columnRemoved", this._onColumnRemoved);
146
138
  host.listen("columnVisibilityChanged", this._onColumnChanged);
147
139
  host.listen("postSectionRender", this._onPostSectionRender);
148
140
  host.listen("beforeColumnBoundUpdate", this._onBeforeColumnBoundUpdate);
@@ -162,6 +154,20 @@ ColumnGroupingPlugin.prototype.initialize = function (host, options) {
162
154
  }
163
155
  // TODO: wrong render group in hide/show column
164
156
  };
157
+ /** Prevent built-in config
158
+ * @public
159
+ * @param {string} optionName
160
+ * @param {Object} optionValue
161
+ * @return {*}
162
+ */
163
+ ColumnGroupingPlugin.prototype.beforeProcessOption = function (optionName, optionValue) {
164
+ if (optionName === "columnGroups") {
165
+ this._legacyColumnGroups = optionValue;
166
+ return false; // eslint-disable-line
167
+ }
168
+
169
+ return; // eslint-disable-line
170
+ };
165
171
  /**
166
172
  * @protected
167
173
  * @ignore
@@ -180,7 +186,7 @@ ColumnGroupingPlugin.prototype.unload = function (host) {
180
186
  this._hosts.splice(at, 1);
181
187
  host.unlisten("columnAdded", this._onColumnChanged);
182
188
  host.unlisten("columnMoved", this._onColumnMoved);
183
- host.unlisten("columnRemoved", this._onColumnChanged);
189
+ host.unlisten("columnRemoved", this._onColumnRemoved);
184
190
  host.unlisten("postSectionRender", this._onPostSectionRender);
185
191
  host.unlisten("beforeColumnBoundUpdate", this._onBeforeColumnBoundUpdate);
186
192
  if (!this._hosts.length) {
@@ -205,8 +211,20 @@ ColumnGroupingPlugin.prototype.config = function (options) {
205
211
  }
206
212
  var extOptions = options["columnGrouping"];
207
213
  if (Array.isArray(extOptions)) {
208
- this._groupDefs = extOptions.filter(ColumnGroupingPlugin._isValidGroup).map(ColumnGroupingPlugin._cloneObject);
214
+ var groupDefs = extOptions.map(ColumnGroupingPlugin._cloneObject);
215
+ this._groupDefs = groupDefs.filter(ColumnGroupingPlugin._isValidGroup);
209
216
  }
217
+ var columns = options["columns"];
218
+ if (!columns) {
219
+ return;
220
+ }
221
+ var len = columns.length;
222
+ for (var i = 0; i < len; ++i) {
223
+ this._setColumnGrouping(i, {
224
+ id: columns[i].id
225
+ }); // used for columnRemoved event
226
+ }
227
+
210
228
  this._migrateLegacyStructure(options["columns"]);
211
229
  };
212
230
  /** @public
@@ -218,13 +236,26 @@ ColumnGroupingPlugin.prototype.getConfigObject = function (gridOptions) {
218
236
 
219
237
  // TODO: Handle legacyRender method that has been migrated
220
238
  var columnGroupingDefs = this.getGroupDefinitions();
221
- for (var i = 0; i < columnGroupingDefs.length; i++) {
222
- columnGroupingDefs[i] = this._groupMap[columnGroupingDefs[i].id];
223
- }
224
239
  obj.columnGrouping = columnGroupingDefs;
225
240
  return obj;
226
241
  };
227
242
 
243
+ /** @private
244
+ * @param {number} colIndex
245
+ * @param {Object} data
246
+ */
247
+ ColumnGroupingPlugin.prototype._setColumnGrouping = function (colIndex, data) {
248
+ var colData = this._newColumnData(colIndex);
249
+ colData["columnGrouping"] = data;
250
+ };
251
+ /** @private
252
+ * @param {number} colIndex
253
+ * @return {Object}
254
+ */
255
+ ColumnGroupingPlugin.prototype._getColumnGrouping = function (colIndex) {
256
+ return this._getColumnOption(colIndex, "columnGrouping");
257
+ };
258
+
228
259
  /** Legacy group structure from composite grid will be converted to the new structure
229
260
  * @private
230
261
  * @param {Object.<string, Array>} objMap
@@ -274,7 +305,7 @@ ColumnGroupingPlugin.prototype._migrateLegacyStructure = function (colModels) {
274
305
 
275
306
  // Add new definitions and structure to the given legacy objects
276
307
  for (i = 0; i < groupCount; ++i) {
277
- groupDef = legacyColumnGroups[i];
308
+ groupDef = ColumnGroupingPlugin._cloneObject(legacyColumnGroups[i]);
278
309
  if (groupDef && groupDef.id) {
279
310
  // WARNING: Modify user's object
280
311
  var childAry = groupMap[groupDef.id];
@@ -286,6 +317,7 @@ ColumnGroupingPlugin.prototype._migrateLegacyStructure = function (colModels) {
286
317
  this._groupDefs.push(groupDef);
287
318
  }
288
319
  }
320
+ this._groupDefs = this._groupDefs.filter(ColumnGroupingPlugin._isValidGroup);
289
321
  };
290
322
 
291
323
  /** Consolidate and process configuration. Force rerendering on column adding, removing, moving, initializaing, and run-time API execution.
@@ -313,6 +345,7 @@ ColumnGroupingPlugin.prototype._applyGrouping = function () {
313
345
  for (r = 0; r < rowCount; r++) {
314
346
  cell = section.getCell(c, r, false);
315
347
  if (cell) {
348
+ cell.reset();
316
349
  cell.removeClass("no-sort");
317
350
  cell.removeAttribute("group-id");
318
351
  }
@@ -333,6 +366,173 @@ ColumnGroupingPlugin.prototype._applyGrouping = function () {
333
366
  }
334
367
  }
335
368
  };
369
+ /** @private
370
+ */
371
+ ColumnGroupingPlugin.prototype._evaluateGroupStructure = function () {
372
+ // Clear existing group structure
373
+ var groupMap = this._groupMap = {};
374
+ var childToParent = this._childToParent = {};
375
+ var visibleGroupMap = this._visibleGroupMap = {};
376
+ this._maxDepth = -1;
377
+
378
+ // Flatten tree structure to simple dictionary
379
+ var groupDefs = this._groupDefs;
380
+ var len = groupDefs.length;
381
+ var i;
382
+ for (i = 0; i < len; i++) {
383
+ this._flattenGroupDefs(groupDefs[i], groupDefs);
384
+ }
385
+
386
+ // Create group map
387
+ var groupDef;
388
+ len = groupDefs.length; // length can be changed after flattening
389
+ for (i = 0; i < len; i++) {
390
+ groupDef = groupDefs[i];
391
+ groupMap[groupDef.id] = groupDef;
392
+
393
+ // Clone group definitions for rendering
394
+ visibleGroupMap[groupDef.id] = ColumnGroupingPlugin._cloneObject(groupDef);
395
+ visibleGroupMap[groupDef.id].children = groupDef.children.slice();
396
+ }
397
+
398
+ // Create child to parent map
399
+ var gid, children, member;
400
+ for (gid in groupMap) {
401
+ groupDef = groupMap[gid];
402
+ children = groupDef.children;
403
+ for (i = 0; i < children.length; i++) {
404
+ member = children[i];
405
+ childToParent[member] = gid;
406
+ }
407
+ }
408
+
409
+ // Apply a parent id to group definition to make it easier to find depth
410
+ var parentId;
411
+ for (gid in visibleGroupMap) {
412
+ parentId = childToParent[gid];
413
+ if (parentId) {
414
+ visibleGroupMap[gid].parent = parentId;
415
+ groupMap[gid].parent = parentId;
416
+ }
417
+ }
418
+
419
+ // Filter invisible groups out
420
+ var rootGroup = [];
421
+ for (gid in visibleGroupMap) {
422
+ groupDef = visibleGroupMap[gid];
423
+ if (this._findGroupTreeDepth(groupDef, 1) === 1) {
424
+ rootGroup.push(groupDef);
425
+ }
426
+ }
427
+ len = rootGroup.length;
428
+ for (i = 0; i < len; i++) {
429
+ this._verifySingleChild(rootGroup[i]);
430
+ }
431
+
432
+ // Determine the depth of each group
433
+ var depth;
434
+ for (gid in visibleGroupMap) {
435
+ groupDef = visibleGroupMap[gid];
436
+ depth = this._findGroupTreeDepth(groupDef, 1);
437
+ groupDef["onRow"] = depth - 1;
438
+ }
439
+
440
+ // Calculate the maximum depth
441
+ var maxDepth = -1;
442
+ for (gid in visibleGroupMap) {
443
+ groupDef = visibleGroupMap[gid];
444
+ depth = groupDef["onRow"];
445
+ if (depth > maxDepth) {
446
+ maxDepth = depth;
447
+ }
448
+ }
449
+ this._maxDepth = maxDepth + 1; // Column header depth = maximum group depth + 1
450
+ };
451
+
452
+ /** Flatten group definition structure by using group ID instead of nested group definitions.
453
+ * @private
454
+ * @param {Object} groupDef
455
+ * @param {Array} groupDefs
456
+ */
457
+ ColumnGroupingPlugin.prototype._flattenGroupDefs = function (groupDef, groupDefs) {
458
+ if (groupDef && groupDef.children) {
459
+ var children = groupDef.children;
460
+ var member, groupId;
461
+ for (var i = 0; i < children.length; i++) {
462
+ member = children[i];
463
+ if (typeof member !== "string") {
464
+ // member is nested group definition
465
+ groupId = member.id;
466
+ if (groupId) {
467
+ children[i] = groupId; // Use group ID instead of nested group definition
468
+ if (groupDefs.indexOf(member) < 0) {
469
+ groupDefs.push(member);
470
+ }
471
+ this._flattenGroupDefs(member, groupDefs);
472
+ }
473
+ }
474
+ }
475
+ }
476
+ };
477
+
478
+ /** @private
479
+ * @param {Object} groupDef
480
+ * @param {number} currentDepth
481
+ * @return {number}
482
+ */
483
+ ColumnGroupingPlugin.prototype._findGroupTreeDepth = function (groupDef, currentDepth) {
484
+ var parentId = groupDef["parent"];
485
+ var parentNode = this._visibleGroupMap[parentId];
486
+ if (parentNode) {
487
+ return this._findGroupTreeDepth(parentNode, currentDepth + 1);
488
+ } else {
489
+ return currentDepth;
490
+ }
491
+ };
492
+
493
+ /** @private
494
+ * @param {Object} groupDef
495
+ * @return {boolean}
496
+ */
497
+ ColumnGroupingPlugin.prototype._verifySingleChild = function (groupDef) {
498
+ var children = groupDef.children;
499
+ var visibleChildCount = 0;
500
+ var visibleChildGroupCount = 0;
501
+ var invisibleMembers = [];
502
+ var i, member;
503
+ for (i = 0; i < children.length; i++) {
504
+ member = children[i];
505
+ if (this._visibleGroupMap[member]) {
506
+ if (this._verifySingleChild(this._visibleGroupMap[member])) {
507
+ ++visibleChildCount;
508
+ ++visibleChildGroupCount;
509
+ } else {
510
+ invisibleMembers.push(member);
511
+ }
512
+ } else {
513
+ if (this._getColumnIndexById(member) > -1) {
514
+ ++visibleChildCount;
515
+ } else {
516
+ invisibleMembers.push(member);
517
+ }
518
+ }
519
+ }
520
+
521
+ // Remove invisible members, keep only visible members
522
+ if (invisibleMembers.length) {
523
+ for (i = 0; i < invisibleMembers.length; i++) {
524
+ member = invisibleMembers[i];
525
+ groupDef.children.splice(children.indexOf(member), 1);
526
+ }
527
+ }
528
+ if (visibleChildCount > 1 || visibleChildGroupCount > 1) {
529
+ return true;
530
+ } else {
531
+ delete this._visibleGroupMap[groupDef.id];
532
+ return false;
533
+ }
534
+ };
535
+
336
536
  /** Set a timer to call applyGrouping only once to avoid performance issue
337
537
  * @private
338
538
  */
@@ -354,7 +554,14 @@ ColumnGroupingPlugin.prototype._applyNearestGrouping = function (colIndex) {
354
554
  var groupLeftIds = this.getGroupIds(colIndexLeft);
355
555
  var groupRightIds = this.getGroupIds(colIndexRight);
356
556
  if (groupLeftIds && groupRightIds) {
357
- var i, j, groupLeftId, groupRightId, field;
557
+ var colId = this.getColumnId(colIndex);
558
+ var groupId = this._childToParent[colId];
559
+ if (groupId) {
560
+ if (groupLeftIds.indexOf(groupId) > -1 || groupRightIds.indexOf(groupId) > -1) {
561
+ return;
562
+ }
563
+ }
564
+ var i, j, groupLeftId, groupRightId;
358
565
  var found = false;
359
566
  for (i = 0; i < groupLeftIds.length; i++) {
360
567
  groupLeftId = groupLeftIds[i];
@@ -362,12 +569,15 @@ ColumnGroupingPlugin.prototype._applyNearestGrouping = function (colIndex) {
362
569
  groupRightId = groupRightIds[j];
363
570
  if (groupLeftId === groupRightId) {
364
571
  // found same Id between group
365
- field = this.getColumnId(colIndex);
366
- this._addGroupChild(field, groupRightId);
572
+
573
+ // This method modifies the group definition and outdates the group structure.
574
+ // It is necessary to recalculate group structure manually.
575
+ this._addGroupChild(colId, groupRightId);
367
576
  found = true;
368
577
  }
369
578
  }
370
579
  if (found) {
580
+ this._evaluateGroupStructure();
371
581
  break;
372
582
  }
373
583
  }
@@ -404,7 +614,7 @@ ColumnGroupingPlugin.prototype._spanGroupVertically = function (titleSection) {
404
614
  */
405
615
  ColumnGroupingPlugin.prototype._spanGroupHorizontally = function (titleSection) {
406
616
  var section = titleSection;
407
- var groupTable = this._groupMap;
617
+ var groupTable = this._visibleGroupMap;
408
618
 
409
619
  // Span column of column group
410
620
  for (var id in groupTable) {
@@ -427,7 +637,7 @@ ColumnGroupingPlugin.prototype._spanGroupHorizontally = function (titleSection)
427
637
  */
428
638
  ColumnGroupingPlugin.prototype._renderGroups = function () {
429
639
  var hostCount = this._hosts.length;
430
- var groupMap = this._groupMap;
640
+ var groupMap = this._visibleGroupMap;
431
641
  for (var i = 0; i < hostCount; ++i) {
432
642
  var section = this._hosts[i].getSection("title");
433
643
  if (!section) {
@@ -515,12 +725,20 @@ ColumnGroupingPlugin.prototype._applyTimeSeries = function (e) {
515
725
  var parentName = tsParentDef.getName();
516
726
  var parentId = tsParentDef.getId();
517
727
  var groupId = "timeSerieGroup_" + parentId;
518
- var getGroupDefintion = this.getGroupDefinition(groupId);
519
- if (getGroupDefintion) {
728
+ var groupDef = this._groupMap[groupId];
729
+ if (groupDef) {
520
730
  // add children time series field to parent
731
+ var dirty = false;
732
+ var child;
521
733
  for (i = 0; i < children.length; i++) {
522
- var child = children[i];
523
- this._addGroupChild(child, groupId);
734
+ child = children[i];
735
+
736
+ // This method modifies the group definition and outdates the group structure.
737
+ // It is necessary to recalculate group structure manually.
738
+ dirty |= this._addGroupChild(child, groupId);
739
+ }
740
+ if (dirty) {
741
+ this._evaluateGroupStructure();
524
742
  }
525
743
  } else {
526
744
  // create new group
@@ -558,29 +776,52 @@ ColumnGroupingPlugin.prototype._onColumnMoved = function (e) {
558
776
  var toColIndex = e.toColIndex;
559
777
  var colId = this.getColumnId(toColIndex);
560
778
  var groupId = this._childToParent[colId];
561
- var colIndexLeft = toColIndex - 1;
562
- var colIndexRight = toColIndex + 1;
563
- var colIdLeft = this.getColumnId(colIndexLeft);
564
- var colIdRight = this.getColumnId(colIndexRight);
565
- var groupIdLeft = this._childToParent[colIdLeft];
566
- var groupIdRight = this._childToParent[colIdRight];
567
- if (groupId != groupIdLeft && groupId != groupIdRight) {
568
- // remove column from previous group
569
- if (groupId) {
570
- var groupChild = this.getGroupChildren(groupId);
571
- var removeIndex = groupChild.indexOf(colId);
779
+ if (groupId) {
780
+ var colIdLeft = this.getColumnId(toColIndex - 1);
781
+ var colIdRight = this.getColumnId(toColIndex + 1);
782
+ var groupIdLeft = this._childToParent[colIdLeft];
783
+ var groupIdRight = this._childToParent[colIdRight];
784
+ if (groupId != groupIdLeft && groupId != groupIdRight) {
785
+ // Remove column from previous group
786
+ var children = this.getGroupChildren(groupId);
787
+ var removeIndex = children.indexOf(colId);
572
788
  if (removeIndex > -1) {
573
- groupChild.splice(removeIndex, 1);
789
+ children.splice(removeIndex, 1);
574
790
  }
575
- this.setGroupChildren(groupId, groupChild);
791
+ this.setGroupChildren(groupId, children);
576
792
  }
577
- this._applyNearestGrouping(toColIndex);
578
793
  }
794
+ this._applyNearestGrouping(toColIndex);
579
795
  this._requestApplyGrouping();
580
796
  };
581
797
  /** @private
582
798
  * @param {Object} e
583
799
  */
800
+ ColumnGroupingPlugin.prototype._onColumnRemoved = function (e) {
801
+ var colData = e.columnData;
802
+ if (colData && colData.columnGrouping) {
803
+ var colId = colData.columnGrouping.id;
804
+ var groupId = this._childToParent[colId];
805
+ if (groupId) {
806
+ var groupDef = this._groupMap[groupId];
807
+ if (groupDef) {
808
+ var children = groupDef.children;
809
+ var index = children.indexOf(colId);
810
+ if (index > -1) {
811
+ if (children.length < 3) {
812
+ this._groupDefs.splice(this._groupDefs.indexOf(groupDef), 1);
813
+ } else {
814
+ children.splice(index, 1);
815
+ }
816
+ this._requestApplyGrouping();
817
+ }
818
+ }
819
+ }
820
+ }
821
+ };
822
+ /** @private
823
+ * @param {Object} e
824
+ */
584
825
  ColumnGroupingPlugin.prototype._onBeforeColumnBoundUpdate = function (e) {
585
826
  var selectedColumns = e.selectedColumns;
586
827
  var parentMap = this._childToParent;
@@ -668,7 +909,13 @@ ColumnGroupingPlugin.prototype._onBeforeColumnBoundUpdate = function (e) {
668
909
  ColumnGroupingPlugin.prototype.addColumnToGroup = function (column, groupId, colIndex) {
669
910
  if (!column || !groupId) return;
670
911
  var columnIndex = colIndex || this.getColumnCount();
671
- this._addGroupChild(column.id, groupId);
912
+
913
+ // This method modifies the group definition and outdates the group structure.
914
+ // It is necessary to recalculate group structure manually.
915
+ if (this._addGroupChild(column.id, groupId)) {
916
+ this._evaluateGroupStructure(); // To prevent event handler from using outdated group structure
917
+ }
918
+
672
919
  if (this._realTimeGrid) {
673
920
  this._realTimeGrid.insertColumn(column, columnIndex);
674
921
  } else if (this._compositeGrid) {
@@ -685,7 +932,7 @@ ColumnGroupingPlugin.prototype.addGroup = function (groupDef) {
685
932
  if (groupDef && groupDef.id) {
686
933
  var curDef = this.getGroupDefinition(groupDef.id);
687
934
  if (!curDef) {
688
- var newGroupDef = cloneObject(groupDef);
935
+ var newGroupDef = ColumnGroupingPlugin._cloneObject(groupDef);
689
936
  this._groupDefs.push(newGroupDef);
690
937
  this._applyGrouping();
691
938
  return true;
@@ -721,6 +968,7 @@ ColumnGroupingPlugin.prototype.removeGroup = function (groupId) {
721
968
  */
722
969
  ColumnGroupingPlugin.prototype.setGroupDefinitions = function (groupDefs) {
723
970
  if (Array.isArray(groupDefs)) {
971
+ groupDefs = groupDefs.map(ColumnGroupingPlugin._cloneObject);
724
972
  groupDefs = groupDefs.filter(ColumnGroupingPlugin._isValidGroup);
725
973
  if (!groupDefs.length) {
726
974
  groupDefs = null;
@@ -744,10 +992,6 @@ ColumnGroupingPlugin.prototype.setGroupDefinitions = function (groupDefs) {
744
992
  ColumnGroupingPlugin._isValidGroup = function (groupDef) {
745
993
  if (groupDef) {
746
994
  if (groupDef.id) {
747
- if (!groupDef.children) {
748
- groupDef.children = []; // WARNING: Modify user's object
749
- }
750
-
751
995
  return true;
752
996
  }
753
997
  }
@@ -759,7 +1003,13 @@ ColumnGroupingPlugin._isValidGroup = function (groupDef) {
759
1003
  * @return {boolean}
760
1004
  */
761
1005
  ColumnGroupingPlugin._cloneObject = function (obj) {
762
- return cloneObject(obj);
1006
+ var newObj = cloneObject(obj);
1007
+ if (Array.isArray(newObj.children)) {
1008
+ newObj.children = newObj.children;
1009
+ } else {
1010
+ newObj.children = [];
1011
+ }
1012
+ return newObj;
763
1013
  };
764
1014
  /** Get a shallow copy of all existing group definitions
765
1015
  * @public
@@ -777,6 +1027,7 @@ ColumnGroupingPlugin.prototype.setGroupDefinition = function (groupId, newDef) {
777
1027
  var curDef = this.getGroupDefinition(groupId);
778
1028
  if (curDef) {
779
1029
  var at = this._groupDefs.indexOf(curDef);
1030
+ newDef = ColumnGroupingPlugin._cloneObject(newDef);
780
1031
  newDef.id = groupId;
781
1032
  this._groupDefs[at] = newDef;
782
1033
  this._applyGrouping();
@@ -801,6 +1052,7 @@ ColumnGroupingPlugin.prototype.setGroupChildren = function (groupId, newChildLis
801
1052
  var groupDef = this.getGroupDefinition(groupId);
802
1053
  if (groupDef) {
803
1054
  if (Array.isArray(newChildList)) {
1055
+ groupDef.aaa = 0; // TODO: for testing, need to be removed
804
1056
  groupDef.children = newChildList.slice();
805
1057
  this._applyGrouping();
806
1058
  } else if (!newChildList && groupDef.children.length) {
@@ -816,9 +1068,8 @@ ColumnGroupingPlugin.prototype.setGroupChildren = function (groupId, newChildLis
816
1068
  ColumnGroupingPlugin.prototype.getGroupChildren = function (groupId) {
817
1069
  var groupDef = this.getGroupDefinition(groupId);
818
1070
  if (groupDef) {
819
- return groupDef.children.slice(); // Shallow copy
1071
+ return groupDef.children;
820
1072
  }
821
-
822
1073
  return null;
823
1074
  };
824
1075
 
@@ -832,11 +1083,11 @@ ColumnGroupingPlugin.prototype.getChildColumnIndices = function (groupId) {
832
1083
  if (group) {
833
1084
  var colIds = this._getGroupMembers(group);
834
1085
  var colIndices = [];
835
- var id;
1086
+ var index;
836
1087
  for (var i = 0; i < colIds.length; i++) {
837
- id = this._getColumnIndexById(colIds[i]);
838
- if (id > -1) {
839
- colIndices.push(id);
1088
+ index = this.getColumnIndex(colIds[i]);
1089
+ if (index > -1) {
1090
+ colIndices.push(index);
840
1091
  }
841
1092
  }
842
1093
  return colIndices.sort();
@@ -860,7 +1111,7 @@ ColumnGroupingPlugin.prototype.getGroupIds = function (colRef) {
860
1111
  var groupIds = [groupId];
861
1112
  var group = this._groupMap[groupId];
862
1113
  while (group && group.parent) {
863
- group = this.getGroupDefinition(group.parent);
1114
+ group = this._groupMap[group.parent];
864
1115
  if (group) {
865
1116
  groupIds.push(group.id);
866
1117
  }
@@ -886,7 +1137,7 @@ ColumnGroupingPlugin.prototype.getMaxGroupLevel = function () {
886
1137
  * @return {number}
887
1138
  */
888
1139
  ColumnGroupingPlugin.prototype.getGroupLevel = function (groupId) {
889
- var group = this._groupMap[groupId];
1140
+ var group = this._visibleGroupMap[groupId];
890
1141
  if (group) {
891
1142
  return group.onRow;
892
1143
  }
@@ -927,106 +1178,11 @@ ColumnGroupingPlugin.prototype._getRootGroup = function (groupId) {
927
1178
  }
928
1179
  var group = this._groupMap[groupId];
929
1180
  while (group.parent) {
930
- group = this.getGroupDefinition(group.parent);
1181
+ group = this._groupMap[group.parent];
931
1182
  }
932
1183
  return group;
933
1184
  };
934
1185
 
935
- /** @private
936
- */
937
- ColumnGroupingPlugin.prototype._evaluateGroupStructure = function () {
938
- // Clear existing group structure
939
- this._groupMap = {};
940
- this._childToParent = {};
941
- this._maxDepth = -1;
942
-
943
- // Flatten tree to dictionary
944
- var columnGroups = this._groupDefs;
945
- var inUsedGroup = {};
946
- var node;
947
- for (var cg = 0; cg < columnGroups.length; cg++) {
948
- // node can be a root or child
949
- node = columnGroups[cg];
950
- // skip tree that don't have a child
951
- if (node.children && node.children.length) {
952
- this._flattenTree(node, inUsedGroup);
953
- }
954
- }
955
- var id;
956
- // Apply parent id to columnGroup for easy to find depth
957
- for (id in this._groupMap) {
958
- node = this._groupMap[id];
959
- if (this._childToParent[node.id]) {
960
- var parentId = this._childToParent[node.id];
961
- node["parent"] = parentId;
962
- }
963
- }
964
-
965
- // find depth of each group
966
- for (id in this._groupMap) {
967
- node = this._groupMap[id];
968
- var depth = this._findGroupTreeDepth(node, 1);
969
- node["onRow"] = depth - 1; // Modify user's object
970
- }
971
-
972
- // Calculate max depth
973
- var maxDepth = 0;
974
- for (id in this._groupMap) {
975
- node = this._groupMap[id];
976
- depth = node["onRow"] + 1;
977
- if (depth > maxDepth) {
978
- maxDepth = depth;
979
- }
980
- }
981
- this._maxDepth = maxDepth;
982
- };
983
- /** @private
984
- * @param {Object} node
985
- * @param {boolean} inUsedGroup
986
- */
987
- ColumnGroupingPlugin.prototype._flattenTree = function (node, inUsedGroup) {
988
- var childrens = node.children;
989
- if (childrens && childrens.length > 0) {
990
- var childId;
991
- for (var c = 0; c < childrens.length; c++) {
992
- var child = childrens[c];
993
- if (child.id) {
994
- // child is group object
995
- childId = child.id;
996
- this._flattenTree(child, inUsedGroup);
997
- } else {
998
- // child can be column id or group id
999
- childId = child;
1000
- if (inUsedGroup[childId] || this._getColumnIndexById(childId) !== -1) {
1001
- inUsedGroup[node.id] = true;
1002
- }
1003
- }
1004
- if (!this._childToParent[childId] && childId != node.id) {
1005
- this._childToParent[childId] = node.id;
1006
- }
1007
- }
1008
-
1009
- // Create Tree node for only in-used group
1010
- if (!this._groupMap[node.id] && inUsedGroup[node.id]) {
1011
- this._groupMap[node.id] = cloneObject(node); // clone node
1012
- }
1013
- }
1014
- };
1015
- /** @private
1016
- * @param {Object} node
1017
- * @param {number} currentDepth
1018
- * @return {number}
1019
- */
1020
- ColumnGroupingPlugin.prototype._findGroupTreeDepth = function (node, currentDepth) {
1021
- var parentId = node["parent"];
1022
- var parentNode = this._groupMap[parentId];
1023
- if (parentNode) {
1024
- return this._findGroupTreeDepth(parentNode, currentDepth + 1);
1025
- } else {
1026
- return currentDepth;
1027
- }
1028
- };
1029
-
1030
1186
  /** This version exclude invisible column unlike the one in GridPlugin
1031
1187
  * @private
1032
1188
  * @param {string} id
@@ -1056,20 +1212,20 @@ ColumnGroupingPlugin.prototype._findColumnIndexArr = function (node, cluster) {
1056
1212
  for (var i = 0; i < childrens.length; i++) {
1057
1213
  var child = childrens[i];
1058
1214
  if (!child.id) {
1059
- if (!this._groupMap[child]) {
1215
+ if (!this._visibleGroupMap[child]) {
1060
1216
  var colIndex = this._getColumnIndexById(child);
1061
1217
  if (colIndex !== -1) {
1062
1218
  cluster.push(colIndex);
1063
1219
  }
1064
1220
  } else {
1065
- this._findColumnIndexArr(this._groupMap[child], cluster);
1221
+ this._findColumnIndexArr(this._visibleGroupMap[child], cluster);
1066
1222
  }
1067
1223
  } else {
1068
1224
  // skip children that has same id as parent
1069
1225
  if (child.id === node.id) {
1070
1226
  return;
1071
1227
  }
1072
- this._findColumnIndexArr(this._groupMap[child.id], cluster);
1228
+ this._findColumnIndexArr(this._visibleGroupMap[child.id], cluster);
1073
1229
  }
1074
1230
  }
1075
1231
  }
@@ -1118,26 +1274,29 @@ ColumnGroupingPlugin._groupConsecutiveArr = function (arr) {
1118
1274
  }
1119
1275
  return result;
1120
1276
  };
1121
- /** @private
1277
+ /** This method modifies the group definition and outdates the group structure. It is necessary to recalculate group structure manually.
1278
+ * @private
1122
1279
  * @param {string} childId
1123
1280
  * @param {string} groupId
1281
+ * @return {boolean}
1124
1282
  */
1125
1283
  ColumnGroupingPlugin.prototype._addGroupChild = function (childId, groupId) {
1126
- var groupDef = this.getGroupDefinition(groupId);
1284
+ var groupDef = this._groupMap[groupId];
1127
1285
  if (childId && groupDef) {
1128
1286
  var chdr = groupDef.children;
1129
1287
  if (chdr && chdr.indexOf(childId) < 0) {
1130
- this._childToParent[childId] = groupId;
1131
1288
  chdr.push(childId);
1289
+ return true;
1132
1290
  }
1133
1291
  }
1292
+ return false;
1134
1293
  };
1135
1294
  /** @private
1136
1295
  * @param {string} childId
1137
1296
  * @return {ColumnGroupingPlugin~GroupDefinition}
1138
1297
  */
1139
1298
  ColumnGroupingPlugin.prototype._getParentGroup = function (childId) {
1140
- return this.getGroupDefinition(this._childToParent[childId]);
1299
+ return this._visibleGroupMap[this._childToParent[childId]];
1141
1300
  };
1142
1301
  /** @private
1143
1302
  * @param {string} colId
@@ -1195,16 +1354,16 @@ ColumnGroupingPlugin.prototype.getCellInfo = function (e) {
1195
1354
  return cellInfo;
1196
1355
  };
1197
1356
  /** @public
1198
- * @param {number|string} from //Column index or id that should be moved
1357
+ * @param {number|string} colRef //Column index or id that should be moved
1199
1358
  * @param {number} to
1200
1359
  * @param {string} groupId
1201
1360
  */
1202
- ColumnGroupingPlugin.prototype.moveColumnIntoGroup = function (from, to, groupId) {
1361
+ ColumnGroupingPlugin.prototype.moveColumnIntoGroup = function (colRef, to, groupId) {
1203
1362
  var fromIndex = -1;
1204
- if (typeof from == "string") {
1205
- fromIndex = this._getColumnIndexById(from);
1363
+ if (typeof colRef == "string") {
1364
+ fromIndex = this._getColumnIndexById(colRef);
1206
1365
  } else {
1207
- fromIndex = from;
1366
+ fromIndex = colRef;
1208
1367
  }
1209
1368
  if (fromIndex == -1) {
1210
1369
  return;
@@ -1255,42 +1414,42 @@ ColumnGroupingPlugin.prototype.moveColumnIntoGroup = function (from, to, groupId
1255
1414
  }
1256
1415
  }
1257
1416
  }
1417
+
1418
+ // Get column id before start moving
1419
+ var colId = this.getColumnId(fromIndex);
1258
1420
  for (var gridIndex = this._hosts.length; --gridIndex >= 0;) {
1259
1421
  var host = this._hosts[gridIndex];
1260
1422
  host.moveColumn(fromIndex, to);
1261
1423
  }
1424
+ if (colId) {
1425
+ // Remove from current group
1426
+ var previousGroup = this._childToParent[colId];
1427
+ if (previousGroup) {
1428
+ var previousGroupChild = this.getGroupChildren(previousGroup);
1429
+ previousGroupChild.splice(previousGroupChild.indexOf(colId), 1);
1430
+ this.setGroupChildren(previousGroup, previousGroupChild);
1431
+ }
1262
1432
 
1263
- //remove previous group apply to column
1264
- var colId = this.getColumnId(to);
1265
- var previousGroup = this._childToParent[colId];
1266
- if (previousGroup) {
1267
- var previousGroupChild = this.getGroupChildren(previousGroup);
1268
- previousGroupChild.splice(previousGroupChild.indexOf(colId), 1);
1269
- this.setGroupChildren(previousGroup, previousGroupChild);
1270
- }
1271
-
1272
- //apply new group
1273
- var children = this.getGroupChildren(groupId);
1274
- if (children.indexOf(colId) == -1) {
1275
- if (colId) {
1433
+ // Add to new group
1434
+ var children = this.getGroupChildren(groupId);
1435
+ if (children.indexOf(colId) < 0) {
1276
1436
  children.push(colId);
1437
+ this.setGroupChildren(groupId, children);
1277
1438
  }
1278
1439
  }
1279
- this.setGroupChildren(groupId, children);
1280
- this._requestApplyGrouping();
1281
1440
  };
1282
1441
  /** @public
1283
- * @param {number|string} columnIndex //Column index or id that should be moved
1442
+ * @param {number|string} colRef //Column index or id that should be moved
1284
1443
  * @param {string} groupId
1285
1444
  */
1286
- ColumnGroupingPlugin.prototype.setColumnParent = function (columnIndex, groupId) {
1445
+ ColumnGroupingPlugin.prototype.setColumnParent = function (colRef, groupId) {
1287
1446
  var api = this.getGridApi();
1288
1447
  if (!api) {
1289
1448
  return;
1290
1449
  }
1291
1450
  var grid = this._hosts[0];
1292
1451
  var colCount = grid.getColumnCount();
1293
- this.moveColumnIntoGroup(columnIndex, colCount, groupId);
1452
+ this.moveColumnIntoGroup(colRef, colCount, groupId);
1294
1453
  };
1295
1454
  export default ColumnGroupingPlugin;
1296
1455
  export { ColumnGroupingPlugin, ColumnGroupingPlugin as ColumnGrouping, ColumnGroupingPlugin as ColumnGroupingExtension };