@refinitiv-ui/efx-grid 6.0.52 → 6.0.54

Sign up to get free protection for your applications and to get access to all the features.
@@ -8,6 +8,8 @@ declare namespace FieldDefinition {
8
8
 
9
9
  function get(field: string): any;
10
10
 
11
+ function getFieldInfo(field: string): any;
12
+
11
13
  function hasFieldInfo(field: string): boolean;
12
14
 
13
15
  function getTimeSeriesChildren(field: string): any;
@@ -18,8 +20,6 @@ declare namespace FieldDefinition {
18
20
 
19
21
  function setSynapseConfig(config: Grid.SynapseConfig|null): void;
20
22
 
21
- function setFieldCaching(caching: boolean): void;
22
-
23
23
  function disableTimeSeriesExpansion(disabled: boolean): void;
24
24
 
25
25
  function isFormula(field: string): boolean;
@@ -10,9 +10,9 @@ import { Deferred } from "../../tr-grid-util/es6/Deferred.js";
10
10
  * @const
11
11
  */
12
12
  var SYNAPSE_URL =
13
- '/synapse/service/suggestions/suggest/?'
14
- + 'hits=1' // search only 1 result
15
- + '&profile=' + encodeURIComponent('Field Selector');
13
+ "/synapse/service/suggestions/suggest/?"
14
+ + "hits=1" // search only 1 result
15
+ + "&profile=" + encodeURIComponent("Field Selector");
16
16
 
17
17
  /* @namespace */
18
18
  var FieldDefinition = {};
@@ -129,18 +129,13 @@ FieldDefinition._timeSeriesChildren = {};
129
129
  * @private
130
130
  * @const
131
131
  */
132
- FieldDefinition._synapse = '';
132
+ FieldDefinition._synapse = "";
133
133
  /**
134
134
  * @type {string}
135
135
  * @private
136
136
  * @const
137
137
  */
138
- FieldDefinition._lang = 'en';
139
- /**
140
- * @type {boolean}
141
- * @private
142
- */
143
- FieldDefinition._caching = false;
138
+ FieldDefinition._lang = "en";
144
139
  /**
145
140
  * @type {boolean}
146
141
  * @private
@@ -167,17 +162,22 @@ FieldDefinition.set = function(field, def) {
167
162
  }
168
163
  }
169
164
  };
170
- /** @public
165
+ /** Get field definition object
166
+ * @public
171
167
  * @function
172
168
  * @param {string} field
173
169
  * @return {Object}
174
170
  */
175
171
  FieldDefinition.get = function(field) {
176
- if(this._caching) {
177
- return FieldDefinition._defs[field];
178
- }
179
- return null;
172
+ return FieldDefinition._defs[field] || null;
180
173
  };
174
+ /** Get field definition object
175
+ * @public
176
+ * @function
177
+ * @param {string} field
178
+ * @return {Object}
179
+ */
180
+ FieldDefinition.getFieldInfo = FieldDefinition.get;
181
181
 
182
182
  /** @public
183
183
  * @function
@@ -186,7 +186,7 @@ FieldDefinition.get = function(field) {
186
186
  */
187
187
  FieldDefinition.hasFieldInfo = function(field) {
188
188
  var val = FieldDefinition.get(field);
189
- return val && val.field; // Already preventing an error caused by accessing a property on a null value
189
+ return (val && val.field) ? true : false; // Already preventing an error caused by accessing a property on a null value
190
190
  };
191
191
 
192
192
  /** @public
@@ -222,15 +222,6 @@ FieldDefinition.remove = function(field) {
222
222
  */
223
223
  FieldDefinition.setSynapseConfig = function (config) {
224
224
  FieldDefinition._synapse = config;
225
-
226
- };
227
-
228
- /** @public
229
- * @function
230
- * @param {boolean} caching
231
- */
232
- FieldDefinition.setFieldCaching = function (caching) {
233
- FieldDefinition._caching = caching;
234
225
  };
235
226
 
236
227
  /** @public
@@ -355,7 +346,7 @@ FieldDefinition.getFieldProperty = function(field, propertyName) {
355
346
  return null;
356
347
  };
357
348
 
358
- /** to get more info about field via synapse service
349
+ /** To get more info about field via synapse service
359
350
  * @private
360
351
  * @param {string} field
361
352
  * @returns {Promise}
@@ -387,12 +378,12 @@ FieldDefinition.loadFieldInfo = function (field) {
387
378
  // everything fine, call synapse service
388
379
  else {
389
380
  var queryUrl = SYNAPSE_URL
390
- + '&api-key=' + encodeURIComponent(synapse.apiKey)
391
- + '&contextApp=' + encodeURIComponent(synapse.contextApp)
392
- + '&language=' + encodeURIComponent(FieldDefinition._lang)
393
- + '&query=' + encodeURIComponent(field);
381
+ + "&api-key=" + encodeURIComponent(synapse.apiKey)
382
+ + "&contextApp=" + encodeURIComponent(synapse.contextApp)
383
+ + "&language=" + encodeURIComponent(FieldDefinition._lang)
384
+ + "&query=" + encodeURIComponent(field);
394
385
  if (synapse.auth) {
395
- queryUrl += '&auth=' + encodeURIComponent(synapse.auth);
386
+ queryUrl += "&auth=" + encodeURIComponent(synapse.auth);
396
387
  }
397
388
  // TODO: handle client timeout
398
389
  var xmr = new XMLHttpRequest();
@@ -401,9 +392,9 @@ FieldDefinition.loadFieldInfo = function (field) {
401
392
  FieldDefinition._loadingField[field] = defer;
402
393
 
403
394
  // for now we care only successful case
404
- xmr.addEventListener('loadend', onLoadEnd);
405
- xmr.addEventListener('timeout', onError);
406
- xmr.addEventListener('error', onError);
395
+ xmr.addEventListener("loadend", onLoadEnd);
396
+ xmr.addEventListener("timeout", onError);
397
+ xmr.addEventListener("error", onError);
407
398
  xmr.open("GET", queryUrl, true); // true for asynchronous
408
399
  xmr.send();
409
400
  }
@@ -431,7 +422,7 @@ FieldDefinition._mockOnLoadEndData = function (field, defer) {
431
422
  var fieldUpperCase = field.toUpperCase();
432
423
  var fieldLowerCase = fieldUpperCase.toLowerCase();
433
424
  var label;
434
- if (fieldLowerCase.indexOf('_') === 2) { // transform XX_ABCD -> Abcd
425
+ if (fieldLowerCase.indexOf("_") === 2) { // transform XX_ABCD -> Abcd
435
426
  label = fieldUpperCase[3] + fieldLowerCase.substring(4);
436
427
  } else {
437
428
  label = fieldUpperCase[0] + fieldLowerCase.substring(1);
@@ -493,49 +484,49 @@ FieldDefinition._mockOnLoadEndData = function (field, defer) {
493
484
  function onLoadEnd(e) {
494
485
  var xmr = e.currentTarget;
495
486
  var defer = xmr._defer;
496
- var resolve = defer.resolve;
497
- var reject = defer.reject;
487
+ var field = xmr._field;
498
488
 
499
- delete FieldDefinition._loadingField[xmr._field];
489
+ delete FieldDefinition._loadingField[field];
500
490
 
501
491
  if (xmr.status === 200) { // case success
502
- var returnObj = {
503
- field: xmr._field,
504
- fieldDefinition: null
505
- };
506
492
  var res = JSON.parse(xmr.responseText);
493
+ var fieldDef = null;
507
494
 
508
495
  var result = res.result && res.result[0];
509
496
  if (result) {
510
497
  var item = result.hits && result.hits[0];
511
498
  if (item && item.p) {
512
499
  var profile = item.p;
513
- if (profile.fn.toUpperCase() === xmr._field.toUpperCase()) {
514
- var fieldDef = FieldDefinition.get(xmr._field) || {};
500
+ if (profile.fn.toUpperCase() === field.toUpperCase()) {
501
+ fieldDef = FieldDefinition.get(field) || {};
515
502
 
516
503
  fieldDef.field = profile.fn; // name
504
+ fieldDef.name = profile.fl; // label
517
505
  fieldDef.rank = profile.Rank;
518
506
  fieldDef.fieldDataType = profile.fdt; // data type
507
+ fieldDef.id = profile.fid;
519
508
  fieldDef.IsMonitorOnlyField = profile.fimo;
520
509
  fieldDef.IsRealtimePortfolioField = profile.firp;
521
510
  fieldDef.IsRealtimeField = profile.firt;
522
- fieldDef.name = profile.fl; // label
523
511
  fieldDef.source = profile.fsrc;
524
512
  fieldDef.sourceRank = profile.fsrnk;
525
513
  fieldDef.description = item.title;
526
514
 
527
- FieldDefinition.set(xmr._field, fieldDef);
528
- returnObj.fieldDefinition = fieldDef;
515
+ FieldDefinition.set(field, fieldDef);
529
516
  }
530
517
  }
531
518
  }
532
- resolve(returnObj);
519
+ if(fieldDef) {
520
+ defer.resolve(fieldDef);
521
+ } else {
522
+ defer.reject("No definition for " + field);
523
+ }
533
524
  } else if (xmr._error) { // case error && time out
534
- xmr._error.field = xmr._field;
535
- reject(xmr._error);
525
+ xmr._error.field = field;
526
+ defer.reject(xmr._error);
536
527
  } else { // case status not 200
537
- reject({
538
- field: xmr._field,
528
+ defer.reject({
529
+ field: field,
539
530
  status: xmr.status,
540
531
  statusText: xmr.statusText,
541
532
  request: xmr
@@ -133,9 +133,13 @@ declare class Grid extends EventDispatcher {
133
133
 
134
134
  public replaceColumn(columnOption: ColumnDefinition.Options|string|null, colRef: Grid.ColumnReference|null): void;
135
135
 
136
+ public getFieldInfo(field: string): any;
137
+
138
+ public loadFieldInfo(field: string): Promise<any>|null;
139
+
136
140
  public setColumns(columns: (any)[]|null): void;
137
141
 
138
- public restoreColumns(columns: (any)[]|null): void;
142
+ public restoreColumns(columns: (any)[]|null, byId?: boolean|null): void;
139
143
 
140
144
  public setFields(ary: (string)[]|null): void;
141
145
 
@@ -291,6 +291,19 @@ var _hasFieldOrId = function(colDef, str) {
291
291
  return (colDef.getField() === str) || (colDef.getId() === str);
292
292
  };
293
293
 
294
+ /** Compare the difference in the 'id' property.
295
+ * @private
296
+ * @param {Object} obj1
297
+ * @param {Object} obj2
298
+ * @returns {boolean} If the id property of two objects is equal, the return will be true, otherwise it will be false.
299
+ */
300
+ var _hasMatchingId = function(obj1, obj2) {
301
+ if(!obj1 || !obj2 || !obj1.id || !obj2.id) { // Handle nullable, if the object or id have null, it's means difference value
302
+ return false;
303
+ }
304
+ return obj1.id === obj2.id;
305
+ };
306
+
294
307
  /** @constructor
295
308
  * @extends {EventDispatcher}
296
309
  * @param {(Element|null)=} placeholder
@@ -840,7 +853,6 @@ Grid.prototype.initialize = function(gridOption) {
840
853
 
841
854
  if (gridOption["fieldCaching"]) {
842
855
  t._fieldCaching = gridOption["fieldCaching"];
843
- FieldDefinition.setFieldCaching(t._fieldCaching);
844
856
  }
845
857
 
846
858
  if(gridOption["timeSeriesExpansion"] != null) {
@@ -1590,8 +1602,8 @@ Grid.prototype.replaceColumn = function (columnOption, colRef) {
1590
1602
  * @param {Object} response
1591
1603
  */
1592
1604
  Grid.prototype._onFieldLoadedSuccess = function (field, colDef, response) {
1593
- if (response && response.fieldDefinition) {
1594
- var fieldDef = response.fieldDefinition;
1605
+ if (response && response.id) {
1606
+ var fieldDef = response;
1595
1607
  if (colDef && colDef.getField() === field) {
1596
1608
  if (colDef.isDefaultName() && fieldDef.name) {
1597
1609
  colDef.setName(fieldDef.name);
@@ -1639,6 +1651,34 @@ Grid.prototype._setScrollbarParent = function (host) {
1639
1651
  this._grid.getHScrollbar().attachToExternalElement(host);
1640
1652
  };
1641
1653
 
1654
+ /** Get stored field information. If field information has not been requested or no data has been received yet, null value is returned.
1655
+ * @public
1656
+ * @function
1657
+ * @param {string} field
1658
+ * @return {Object}
1659
+ */
1660
+ Grid.prototype.getFieldInfo = function(field) {
1661
+ return FieldDefinition.getFieldInfo(field);
1662
+ };
1663
+ /** Request field information from Synapse service. If field information already exists, a resolved promise is returned. Synapse config must be supplied before the request can be made.
1664
+ * @public
1665
+ * @function
1666
+ * @param {string} field
1667
+ * @return {Promise}
1668
+ * @example
1669
+ * var gridConfig = {
1670
+ * synapse: { // define synapse configuration
1671
+ * apiKey: "xxx",
1672
+ * contextApp: "xxx",
1673
+ * auth: "xxx" (optional)
1674
+ * }
1675
+ * };
1676
+ * var promise = grid.loadFieldInfo("CF_LAST");
1677
+ */
1678
+ Grid.prototype.loadFieldInfo = function(field) {
1679
+ return FieldDefinition.loadFieldInfo(field);
1680
+ };
1681
+
1642
1682
  /**
1643
1683
  * @private
1644
1684
  * @param {string} field
@@ -1697,8 +1737,9 @@ Grid.prototype.setColumns = function(columns) {
1697
1737
  /** Remove, add and keep column based on the given column data
1698
1738
  * @public
1699
1739
  * @param {Array.<Object>} columns Array of column options
1740
+ * @param {boolean=} byId=false, if enable it, this method will only check for differences in the 'id' property
1700
1741
  */
1701
- Grid.prototype.restoreColumns = function(columns) {
1742
+ Grid.prototype.restoreColumns = function(columns, byId) {
1702
1743
  var grid = this._grid;
1703
1744
  grid.startBatch("reset");
1704
1745
  var configObj = this.getConfigObject();
@@ -1707,6 +1748,7 @@ Grid.prototype.restoreColumns = function(columns) {
1707
1748
  var preColLen = previousColumns.length;
1708
1749
  var newColLen = columns.length;
1709
1750
 
1751
+ var compareLogic = byId ? _hasMatchingId : deepEqual;
1710
1752
  var removingFields = [];
1711
1753
  var keepingColumns = [];
1712
1754
  var columnOrdering = [];
@@ -1716,7 +1758,7 @@ Grid.prototype.restoreColumns = function(columns) {
1716
1758
  for (i = 0; i < preColLen; i++) {
1717
1759
  found = false;
1718
1760
  for (j = 0; j < newColLen; j++) {
1719
- if (deepEqual(previousColumns[i], columns[j])) {
1761
+ if(compareLogic(previousColumns[i], columns[j])) {
1720
1762
  keepingColumns.push(previousColumns[i]);
1721
1763
  found = true;
1722
1764
  break;
@@ -1737,7 +1779,7 @@ Grid.prototype.restoreColumns = function(columns) {
1737
1779
  for (i = 0; i < newColLen; i++) {
1738
1780
  found = false;
1739
1781
  for (j = 0; j < keepingLen; j++) { // loop only keeping column
1740
- if (deepEqual(columns[i], keepingColumns[j])) {
1782
+ if(compareLogic(columns[i], keepingColumns[j])) {
1741
1783
  found = true;
1742
1784
  var colIndex = this.getColumnIndex(columns[i].field); // We cannot use 'i' (colIndex) in this case, as it will sort the columns. Instead, we need to obtain a new column index from the field.
1743
1785
  columnOrdering.push(this.getColumnId(colIndex));
@@ -4,22 +4,22 @@ import { GridPlugin } from "../../tr-grid-util/es6/GridPlugin.js";
4
4
  declare namespace AutoTooltipPlugin {
5
5
 
6
6
  type Options = {
7
- header?: boolean,
8
- title?: boolean,
9
- footer?: boolean,
10
- content?: boolean,
11
- quickMode?: boolean
7
+ header?: boolean|null,
8
+ title?: boolean|null,
9
+ footer?: boolean|null,
10
+ content?: boolean|null,
11
+ quickMode?: boolean|null
12
12
  };
13
13
 
14
14
  type ColumnOptions = {
15
- autoTooltip?: boolean
15
+ autoTooltip?: boolean|null
16
16
  };
17
17
 
18
18
  }
19
19
 
20
20
  declare class AutoTooltipPlugin extends GridPlugin {
21
21
 
22
- constructor(options?: AutoTooltipPlugin.Options);
22
+ constructor(options?: AutoTooltipPlugin.Options|null);
23
23
 
24
24
  public getName(): string;
25
25
 
@@ -31,9 +31,9 @@ declare class AutoTooltipPlugin extends GridPlugin {
31
31
 
32
32
  public getConfigObject(gridOptions?: any): any;
33
33
 
34
- public applyTooltip(colIndex: number, fromR?: number, toR?: number): void;
34
+ public applyTooltip(colIndex: number, fromR?: number|null, toR?: number|null): void;
35
35
 
36
- public applyTooltipToColumns(colIndices?: (number)[]): void;
36
+ public applyTooltipToColumns(colIndices?: (number)[]|null): void;
37
37
 
38
38
  public applyTooltipToAllColumns(): void;
39
39
 
@@ -279,12 +279,14 @@ AutoTooltipPlugin.prototype.applyTooltipToAllColumns = function () {
279
279
  AutoTooltipPlugin.prototype._applyTooltipToSection = function (section, colIndex, fromR, toR) {
280
280
  if (!section) { return false; }
281
281
 
282
- if (!fromR) {
282
+ if (fromR == null) {
283
+ fromR = section.getFirstIndexInView();
284
+ } else if(!fromR) {
283
285
  fromR = 0;
284
286
  }
285
287
 
286
288
  if (toR == null) {
287
- toR = section.getRowCount();
289
+ toR = section.getLastIndexInView() + 1;
288
290
  }
289
291
 
290
292
  if (fromR >= toR) {
@@ -296,6 +298,10 @@ AutoTooltipPlugin.prototype._applyTooltipToSection = function (section, colIndex
296
298
  return false;
297
299
  }
298
300
 
301
+ if(columnObj.getVisibility && !columnObj.getVisibility()) {
302
+ return false;
303
+ }
304
+
299
305
  var colElem = columnObj.getElement();
300
306
  if (!colElem) {
301
307
  return false;
@@ -93,6 +93,8 @@ declare class ColumnGroupingPlugin extends GridPlugin {
93
93
 
94
94
  public unpinGroup(groupId: string, dest?: (number|string)|null): void;
95
95
 
96
+ public selectGroupHeaders(colIndices: (number)[]|null): void;
97
+
96
98
  public static getObjectIndex(column: any): number;
97
99
 
98
100
  public static getObjectId(column: any): string;
@@ -71,6 +71,10 @@ ColumnGroupingPlugin.prototype._rerenderTimerId = 0;
71
71
  /** @type {number}
72
72
  * @private
73
73
  */
74
+ ColumnGroupingPlugin.prototype._groupHeaderTimerId = 0;
75
+ /** @type {number}
76
+ * @private
77
+ */
74
78
  ColumnGroupingPlugin.prototype._addingTimerId = 0;
75
79
  /** @type {Array}
76
80
  * @private
@@ -84,6 +88,11 @@ ColumnGroupingPlugin.prototype._legacyColumnGroups = null;
84
88
  * @private
85
89
  */
86
90
  ColumnGroupingPlugin.prototype._inPinning = false;
91
+ /** @type {!Object.<string, boolean}
92
+ * @description A map of selected groups
93
+ * @private
94
+ */
95
+ ColumnGroupingPlugin.prototype._selectedColMap;
87
96
 
88
97
  /** @private
89
98
  * @param {number} a
@@ -298,6 +307,10 @@ ColumnGroupingPlugin.prototype.unload = function (host) {
298
307
  clearTimeout(this._rerenderTimerId);
299
308
  this._rerenderTimerId = 0;
300
309
  }
310
+ if (this._groupHeaderTimerId) {
311
+ clearTimeout(this._groupHeaderTimerId);
312
+ this._groupHeaderTimerId = 0;
313
+ }
301
314
  if (this._addingTimerId) {
302
315
  clearTimeout(this._addingTimerId);
303
316
  this._addingTimerId = 0;
@@ -485,6 +498,7 @@ ColumnGroupingPlugin.prototype._applyGrouping = function () {
485
498
  if (cell) {
486
499
  // TODO: The style and class from the user will not be reset, for example, the color or background
487
500
  cell.removeClass("no-sort");
501
+ cell.removeClass("selected-group");
488
502
  cell.removeAttribute("group-id");
489
503
  }
490
504
  }
@@ -655,6 +669,14 @@ ColumnGroupingPlugin.prototype._requestApplyGrouping = function () {
655
669
  this._rerenderTimerId = setTimeout(this._applyGrouping.bind(this), 10);
656
670
  }
657
671
  };
672
+ /** Set a timer to call renderGroups only once to avoid performance issue
673
+ * @private
674
+ */
675
+ ColumnGroupingPlugin.prototype._requestGroupRendering = function () {
676
+ if (!this._groupHeaderTimerId) {
677
+ this._groupHeaderTimerId = setTimeout(this.renderGroups.bind(this), 10);
678
+ }
679
+ };
658
680
  /** Apply nearest grouping to column.
659
681
  * @private
660
682
  * @param {number} colIndex
@@ -753,11 +775,16 @@ ColumnGroupingPlugin.prototype._spanGroupHorizontally = function (titleSection)
753
775
  spanIndices = [];
754
776
  groupDef = visibleGroupMap[id];
755
777
  colIds = GroupDefinitions.getLeafDescendants(visibleGroupMap, id);
778
+ var isAllSelected = this._selectedColMap ? true : false;
756
779
  for (i = 0; i < colIds.length; i++) {
757
- index = this._getColumnIndexById(colIds[i]);
780
+ var colId = colIds[i];
781
+ index = this._getColumnIndexById(colId);
758
782
  if (index > -1) {
759
783
  spanIndices.push(index);
760
784
  }
785
+ if (isAllSelected && this._selectedColMap) {
786
+ isAllSelected &= this._selectedColMap[colId];
787
+ }
761
788
  }
762
789
  spanIndices.sort(ColumnGroupingPlugin._ascSortLogic);
763
790
  len = spanIndices.length;
@@ -767,6 +794,10 @@ ColumnGroupingPlugin.prototype._spanGroupHorizontally = function (titleSection)
767
794
  var end = spanIndices[len - 1];
768
795
  section.setCellColSpan(start, groupDef["onRow"], end - start + 1);
769
796
  groupDef["colIndex"] = start;
797
+ if (isAllSelected) {
798
+ var cell = section.getCell(start, groupDef["onRow"]);
799
+ cell.addClass("selected-group");
800
+ }
770
801
  }
771
802
  }
772
803
  };
@@ -774,6 +805,7 @@ ColumnGroupingPlugin.prototype._spanGroupHorizontally = function (titleSection)
774
805
  * @public
775
806
  */
776
807
  ColumnGroupingPlugin.prototype.renderGroups = function () {
808
+ this._groupHeaderTimerId = 0;
777
809
  var hostCount = this._hosts.length;
778
810
  var groupMap = this._visibleGroupMap;
779
811
  for (var i = 0; i < hostCount; ++i) {
@@ -798,6 +830,17 @@ ColumnGroupingPlugin.prototype._renderGroup = function (groupDef, section) {
798
830
  }
799
831
  var rowIndex = groupDef["onRow"];
800
832
  var cell = section.getCell(colIndex, rowIndex);
833
+ var colIds = GroupDefinitions.getLeafDescendants(this._visibleGroupMap, groupDef["id"]);
834
+ var isAllSelected = false;
835
+ if (this._selectedColMap) {
836
+ isAllSelected = true;
837
+ for (var i = 0; i < colIds.length; i++) {
838
+ if (!this._selectedColMap[colIds[i]]) {
839
+ isAllSelected = false;
840
+ break;
841
+ }
842
+ }
843
+ }
801
844
  if (cell) {
802
845
  // Overide the defaults
803
846
  cell.setStyle("text-align", groupDef["alignment"] || "");
@@ -807,6 +850,11 @@ ColumnGroupingPlugin.prototype._renderGroup = function (groupDef, section) {
807
850
  // Additional cell settings must be removed in the _applyGrouping() method
808
851
  cell.addClass("no-sort");
809
852
  cell.setAttribute("group-id", groupDef["id"]);
853
+ if (isAllSelected) {
854
+ cell.addClass("selected-group");
855
+ } else {
856
+ cell.removeClass("selected-group");
857
+ }
810
858
  if (groupDef["legacyRender"]) {
811
859
  // Built-in version if render receive colIndex, cell, groupDefinition as arguments
812
860
  groupDef["legacyRender"](colIndex, cell, groupDef);
@@ -1710,6 +1758,26 @@ ColumnGroupingPlugin.prototype.unpinGroup = function (groupId, dest) {
1710
1758
  this.moveGroup(groupId, destId);
1711
1759
  }
1712
1760
  };
1761
+ /** @public
1762
+ * @param {Array<number>} colIndices
1763
+ */
1764
+ ColumnGroupingPlugin.prototype.selectGroupHeaders = function (colIndices) {
1765
+ var host = this._hosts[0];
1766
+ var count = colIndices.length;
1767
+ if (host && count) {
1768
+ var colIds = [];
1769
+ for (var i = 0; i < count; i++) {
1770
+ colIds.push(host.getColumnId(colIndices[i]));
1771
+ }
1772
+ var colMap = host.createColumnMap(colIds);
1773
+ if (colMap) {
1774
+ this._selectedColMap = colMap;
1775
+ }
1776
+ } else {
1777
+ this._selectedColMap = null;
1778
+ }
1779
+ this._requestGroupRendering();
1780
+ };
1713
1781
 
1714
1782
  /** Get column index from column object
1715
1783
  * @public
@@ -685,6 +685,8 @@ ColumnSelectionPlugin.prototype.clearAllSelections = function () {
685
685
 
686
686
  this._clearMenuIcon();
687
687
  }
688
+
689
+ this._updateGroupSelection();
688
690
  };
689
691
  /** Alias to clearAllSelections() method
690
692
  * @public
@@ -821,37 +823,14 @@ ColumnSelectionPlugin.prototype._isSelectedColumns = function (colIndices) {
821
823
 
822
824
  return isAllSelected;
823
825
  };
824
- /**
826
+ /** Update group selection according to current selected columns
825
827
  * @private
826
- * @param {Array<number>} colIndices
827
828
  */
828
829
 
829
830
 
830
831
  ColumnSelectionPlugin.prototype._updateGroupSelection = function () {
831
- var cgp = this._cgp;
832
- var grid = this._activeGrid;
833
-
834
- if (!cgp || !grid) {
835
- return;
836
- }
837
-
838
- var section = grid.getSection("title");
839
- var groupDefs = cgp.getGroupDefinitions();
840
- var count = groupDefs.length;
841
-
842
- for (var i = 0; i < count; i++) {
843
- var groupDef = groupDefs[i];
844
- var groupId = groupDef["id"];
845
- var childIndices = cgp.getChildColumnIndices(groupId);
846
- var rowIndex = cgp.getGroupLevel(groupId);
847
- var colIndex = childIndices[0];
848
- var cell = section.getCell(colIndex, rowIndex);
849
-
850
- if (this._isSelectedColumns(childIndices)) {
851
- cell.addClass("selected-group");
852
- } else {
853
- cell.removeClass("selected-group");
854
- }
832
+ if (this._cgp && this._cgp.selectGroupHeaders) {
833
+ this._cgp.selectGroupHeaders(this.getSelectedColumns());
855
834
  }
856
835
  };
857
836
  /** Left click on title causes selection change. <br>
@@ -1506,12 +1506,12 @@ ColumnStackPlugin.prototype._addRefToStack = function (stackOption, colIndex) {
1506
1506
  /** Remove unique ref of the specified index from the stack
1507
1507
  * @private
1508
1508
  * @param {Object} stackOption
1509
- * @param {string} colRef For removing state
1509
+ * @param {string} colId For removing state
1510
1510
  * @param {number} colIndex For updating UI
1511
1511
  * @return {boolean}
1512
1512
  */
1513
- ColumnStackPlugin.prototype._removeRefFromStack = function (stackOption, colRef, colIndex) {
1514
- if(!this._groupDefs.removeGroupChild(stackOption.id, colRef)) {
1513
+ ColumnStackPlugin.prototype._removeRefFromStack = function (stackOption, colId, colIndex) {
1514
+ if(!this._groupDefs.removeGroupChild(stackOption.id, colId)) {
1515
1515
  return false;
1516
1516
  }
1517
1517
 
@@ -1787,7 +1787,7 @@ ColumnStackPlugin.prototype.removeColumnFromStack = function(colRef) {
1787
1787
  }
1788
1788
 
1789
1789
  var colIndices = this.getColumnIndices(children);
1790
- this._removeRefFromStack(stack, colRef, colIndex);
1790
+ this._removeRefFromStack(stack, colId, colIndex);
1791
1791
 
1792
1792
  this.moveColumnById(colIndex, colIndices[memberCount - 1] + 1); // This assumes that the column order is already in correct position
1793
1793
 
@@ -1890,7 +1890,7 @@ ColumnStackPlugin.prototype.addStackChild = function(stackId, colRef) {
1890
1890
  */
1891
1891
  ColumnStackPlugin.prototype.removeStackChild = function(stackId, colRef) {
1892
1892
  if(stackId === this.getStackId(colRef)) {
1893
- this.removeColumnFromStack(colIndex);
1893
+ this.removeColumnFromStack(colRef);
1894
1894
  }
1895
1895
  };
1896
1896
  /** @public
@@ -24,6 +24,8 @@ declare class GroupDefinitions {
24
24
 
25
25
  public cloneGroupMap(): { [key: string]: any };
26
26
 
27
+ public rebuildMap(): void;
28
+
27
29
  public getGroupChildren(groupId: string): (string)[]|null;
28
30
 
29
31
  public getLeafDescendants(groupId: string): (string)[]|null;
@@ -46,10 +48,12 @@ declare class GroupDefinitions {
46
48
 
47
49
  public removeGroup(groupId: string): boolean;
48
50
 
49
- public setGroup(groupId: string, groupDef?: (string)[]|any|null): string;
51
+ public setGroup(groupId: string, groupDef?: ((string)[]|any)|null): string;
50
52
 
51
53
  public hasGroupChild(parentId: string, childId: string): boolean;
52
54
 
55
+ public contains(groupId: string, childId: string): boolean;
56
+
53
57
  public addGroupChild(parentId: string, childId: string, position?: number|null): boolean;
54
58
 
55
59
  public removeGroupChild(parentId: string, childId?: string|null): boolean;