canvas-datagrid 0.3.25 → 0.4.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.
@@ -1275,7 +1275,256 @@ function _typeof(obj) { "@babel/helpers - typeof"; if (typeof Symbol === "functi
1275
1275
  self.controlInput.focus();
1276
1276
  }
1277
1277
  });
1278
+ } //#region group/ungroup columns
1279
+
1280
+
1281
+ var groupAreaHeight = self.getColumnGroupAreaHeight();
1282
+ var groupAreaWidth = self.getRowGroupAreaWidth();
1283
+
1284
+ var setCollapseStateForAllGroups = function setCollapseStateForAllGroups(allGroups, collapsed) {
1285
+ if (allGroups.length === 0) return;
1286
+
1287
+ for (var i = 0; i < allGroups.length; i++) {
1288
+ var groups = allGroups[i];
1289
+
1290
+ for (var j = 0; j < groups.length; j++) {
1291
+ var group = groups[j];
1292
+ group.collapsed = collapsed;
1293
+ }
1294
+ }
1295
+
1296
+ self.refresh();
1297
+ };
1298
+
1299
+ if (e.pos && e.pos.y < groupAreaHeight) {
1300
+ e.items.push({
1301
+ title: self.attributes.showRemoveAllGroupColumns,
1302
+ click: function click(ev) {
1303
+ ev.preventDefault();
1304
+ self.groupedColumns = [];
1305
+ self.refresh();
1306
+ }
1307
+ });
1308
+ e.items.push({
1309
+ title: self.attributes.showExpandAllGroupColumns,
1310
+ click: function click(ev) {
1311
+ ev.preventDefault();
1312
+ setCollapseStateForAllGroups(self.groupedColumns, false);
1313
+ }
1314
+ });
1315
+ e.items.push({
1316
+ title: self.attributes.showCollapseAllGroupColumns,
1317
+ click: function click(ev) {
1318
+ ev.preventDefault();
1319
+ setCollapseStateForAllGroups(self.groupedColumns, true);
1320
+ }
1321
+ });
1322
+ }
1323
+
1324
+ if (e.pos && e.pos.x < groupAreaWidth) {
1325
+ e.items.push({
1326
+ title: self.attributes.showRemoveAllGroupRows,
1327
+ click: function click(ev) {
1328
+ ev.preventDefault();
1329
+ self.groupedRows = [];
1330
+ self.refresh();
1331
+ }
1332
+ });
1333
+ e.items.push({
1334
+ title: self.attributes.showExpandAllGroupRows,
1335
+ click: function click(ev) {
1336
+ ev.preventDefault();
1337
+ setCollapseStateForAllGroups(self.groupedRows, false);
1338
+ }
1339
+ });
1340
+ e.items.push({
1341
+ title: self.attributes.showCollapseAllGroupRows,
1342
+ click: function click(ev) {
1343
+ ev.preventDefault();
1344
+ setCollapseStateForAllGroups(self.groupedRows, true);
1345
+ }
1346
+ });
1347
+ }
1348
+
1349
+ var canGroupByColumns = self.attributes.allowGroupingColumns && e.cell.isColumnHeader && e.cell.header && e.cell.header.index > 0;
1350
+ var canUngroupColumns = self.attributes.allowGroupingColumns && e.cell.isColumnHeader;
1351
+ var canGroupByRows = self.attributes.allowGroupingRows && e.cell.isRowHeader && e.cell.header;
1352
+ var canUngroupRows = self.attributes.allowGroupingRows && e.cell.isRowHeader;
1353
+ /**
1354
+ * The value for storing the return value from `self.getSchema()`
1355
+ * @type {any[]}
1356
+ */
1357
+
1358
+ var schema;
1359
+ /**
1360
+ * A map between columnIndex and column data
1361
+ * @type {Map<string,any>}
1362
+ */
1363
+
1364
+ var columns;
1365
+
1366
+ var getColumnsMap = function getColumnsMap() {
1367
+ if (!columns) {
1368
+ if (!schema) schema = self.getSchema();
1369
+ columns = new Map(schema.map(function (_col) {
1370
+ return [_col.columnIndex, _col];
1371
+ }));
1372
+ }
1373
+
1374
+ return columns;
1375
+ };
1376
+
1377
+ if (canGroupByColumns) {
1378
+ /** @type {number[]} */
1379
+ var groupIndexes = [];
1380
+ /** @type {number} */
1381
+
1382
+ var headerIndex = e.cell.header.index;
1383
+ var col = headerIndex;
1384
+
1385
+ for (; col >= 0; col--) {
1386
+ if (!self.isColumnSelected(col)) break;
1387
+ groupIndexes[0] = col;
1388
+ }
1389
+
1390
+ for (col = headerIndex;; col++) {
1391
+ if (!self.isColumnSelected(col)) break;
1392
+ groupIndexes[1] = col;
1393
+ }
1394
+
1395
+ if (col !== headerIndex && groupIndexes.length === 2 && groupIndexes[1] > groupIndexes[0] && self.isNewGroupRangeValid(self.groupedColumns, groupIndexes[0], groupIndexes[1])) {
1396
+ var _columns = getColumnsMap();
1397
+
1398
+ var groupTitles = [];
1399
+ var groupNames = [];
1400
+
1401
+ for (var i = 0; i < groupIndexes.length; i++) {
1402
+ var columnIndex = groupIndexes[i];
1403
+
1404
+ var column = _columns.get(columnIndex);
1405
+
1406
+ if (column) {
1407
+ groupNames.push(column.name);
1408
+ groupTitles.push(column.title || column.name || column.index);
1409
+ }
1410
+ }
1411
+
1412
+ if (groupNames[0] && groupNames[1]) {
1413
+ // show group options
1414
+ e.items.push({
1415
+ title: self.attributes.showGroupColumns.replace('%s', groupTitles[0] + '-' + groupTitles[1]),
1416
+ click: function click(ev) {
1417
+ ev.preventDefault();
1418
+ self.groupColumns(groupNames[0], groupNames[1]);
1419
+ self.controlInput.focus();
1420
+ }
1421
+ });
1422
+ }
1423
+ }
1424
+ }
1425
+
1426
+ if (canUngroupColumns) {
1427
+ var _columnIndex = e.cell.columnIndex;
1428
+ var groups = self.getGroupsColumnBelongsTo(_columnIndex);
1429
+
1430
+ var _columns2 = getColumnsMap();
1431
+
1432
+ var _loop = function _loop(_i) {
1433
+ var _groups$_i = groups[_i],
1434
+ from = _groups$_i.from,
1435
+ to = _groups$_i.to;
1436
+
1437
+ var cell0 = _columns2.get(from);
1438
+
1439
+ var cell1 = _columns2.get(to);
1440
+
1441
+ if (cell0 && cell1) {
1442
+ var formatArgs = (cell0.title || cell0.name || cell0.index) + '-' + (cell1.title || cell1.name || cell1.index);
1443
+ e.items.push({
1444
+ title: self.attributes.showRemoveGroupColumns.replace('%s', formatArgs),
1445
+ click: function click(ev) {
1446
+ ev.preventDefault();
1447
+ self.removeGroupColumns(cell0.name, cell1.name);
1448
+ self.controlInput.focus();
1449
+ }
1450
+ });
1451
+ } else {
1452
+ console.warn("Cannot find column ".concat(from, " or column ").concat(to));
1453
+ }
1454
+ };
1455
+
1456
+ for (var _i = 0; _i < groups.length; _i++) {
1457
+ _loop(_i);
1458
+ }
1459
+ }
1460
+
1461
+ if (canGroupByRows) {
1462
+ var range = [];
1463
+ var prev = -2;
1464
+ var ok = true;
1465
+ self.selections.forEach(function (row, index) {
1466
+ if (!ok) return;
1467
+
1468
+ if (prev < -1) {
1469
+ prev = index;
1470
+ range[0] = index;
1471
+ return;
1472
+ }
1473
+
1474
+ if (index !== prev + 1 || !row || row.length === 0) {
1475
+ ok = false;
1476
+ return;
1477
+ }
1478
+
1479
+ prev = index;
1480
+ range[1] = index;
1481
+ });
1482
+ var rangeTitle = range.map(function (rowIndex) {
1483
+ var index = self.getBoundRowIndexFromViewRowIndex(rowIndex);
1484
+ if (typeof index === 'number') return index + 1;
1485
+ return rowIndex + 1;
1486
+ }).join('-');
1487
+
1488
+ if (ok && range.length === 2 && self.isNewGroupRangeValid(self.groupedRows, range[0], range[1])) {
1489
+ e.items.push({
1490
+ title: self.attributes.showGroupRows.replace('%s', rangeTitle),
1491
+ click: function click(ev) {
1492
+ ev.preventDefault();
1493
+ self.groupRows(range[0], range[1]);
1494
+ }
1495
+ });
1496
+ }
1278
1497
  }
1498
+
1499
+ if (canUngroupRows) {
1500
+ var rowIndex = e.cell.rowIndex;
1501
+
1502
+ var _groups = self.getGroupsRowBelongsTo(rowIndex);
1503
+
1504
+ var _loop2 = function _loop2(_i2) {
1505
+ var _groups$_i2 = _groups[_i2],
1506
+ from = _groups$_i2.from,
1507
+ to = _groups$_i2.to;
1508
+ var rangeTitle = [from, to].map(function (rowIndex) {
1509
+ var index = self.getBoundRowIndexFromViewRowIndex(rowIndex);
1510
+ if (typeof index === 'number') return index + 1;
1511
+ return rowIndex + 1;
1512
+ }).join('-');
1513
+ e.items.push({
1514
+ title: self.attributes.showRemoveGroupRows.replace('%s', rangeTitle),
1515
+ click: function click(ev) {
1516
+ ev.preventDefault();
1517
+ self.removeGroupRows(from, to);
1518
+ self.controlInput.focus();
1519
+ }
1520
+ });
1521
+ };
1522
+
1523
+ for (var _i2 = 0; _i2 < _groups.length; _i2++) {
1524
+ _loop2(_i2);
1525
+ }
1526
+ } //#endregion group/ungroup columns
1527
+
1279
1528
  }
1280
1529
 
1281
1530
  self.disposeAutocomplete = function () {
@@ -1306,6 +1555,59 @@ function _typeof(obj) { "@babel/helpers - typeof"; if (typeof Symbol === "functi
1306
1555
  self.contextmenuEvent = function (e, overridePos) {
1307
1556
  if (!self.hasFocus && e.target !== self.canvas) {
1308
1557
  return;
1558
+ } // don't create context menu for parents if current position is located in child grid
1559
+
1560
+
1561
+ var children = Object.keys(self.childGrids);
1562
+
1563
+ for (var i = 0; i < children.length; i++) {
1564
+ var childGrid = self.childGrids[children[i]];
1565
+ var parentNode = childGrid && childGrid.parentNode;
1566
+ if (!parentNode) continue;
1567
+ var offsetLeft = parentNode.offsetLeft,
1568
+ offsetWidth = parentNode.offsetWidth,
1569
+ offsetTop = parentNode.offsetTop,
1570
+ offsetHeight = parentNode.offsetHeight;
1571
+ if ((e.x >= offsetLeft && e.x <= offsetLeft + offsetWidth) === false) continue;
1572
+ if ((e.y >= offsetTop && e.y <= offsetTop + offsetHeight) === false) continue;
1573
+ return; // in child grid
1574
+ } // don't create context menu for child if current position is located in parent grid
1575
+
1576
+
1577
+ if (self.isChildGrid && self.parentNode) {
1578
+ //#region check is current child grid closed
1579
+ var childGridsOfParent = self.parentGrid && self.parentGrid.childGrids;
1580
+ if (!childGridsOfParent || !Array.isArray(childGridsOfParent)) return;
1581
+ var matchedMe = childGridsOfParent.find(function (grid) {
1582
+ var nodeA = grid.parentNode;
1583
+ var nodeB = self.parentNode;
1584
+ return nodeA.offsetTop == nodeB.offsetTop && nodeA.offsetLeft === nodeB.offsetLeft;
1585
+ });
1586
+ if (!matchedMe) return; //#endregion
1587
+
1588
+ var x0 = self.parentNode.offsetLeft;
1589
+ var x1 = self.parentNode.offsetLeft + self.parentNode.offsetWidth;
1590
+ var y0 = self.parentNode.offsetTop;
1591
+ var y1 = self.parentNode.offsetTop + self.parentNode.offsetHeight;
1592
+ var node = self.parentNode.parentNode;
1593
+
1594
+ while (node) {
1595
+ var _node = node,
1596
+ _offsetLeft = _node.offsetLeft,
1597
+ _offsetWidth = _node.offsetWidth,
1598
+ _offsetTop = _node.offsetTop,
1599
+ _offsetHeight = _node.offsetHeight;
1600
+ if (_offsetLeft > x0) x0 = _offsetLeft;
1601
+ if (_offsetTop > y0) y0 = _offsetTop;
1602
+ var newX1 = _offsetLeft + _offsetWidth;
1603
+ var newY1 = _offsetTop + _offsetHeight;
1604
+ if (newX1 < x1) x1 = newX1;
1605
+ if (newY1 < y1) y1 = newY1;
1606
+ if (node.nodeType !== 'canvas-datagrid-tree') break;
1607
+ node = node.parentNode;
1608
+ }
1609
+
1610
+ if ((e.x >= x0 && e.x <= x1 && e.y >= y0 && e.y <= y1) === false) return;
1309
1611
  }
1310
1612
 
1311
1613
  function createDisposeEvent() {
@@ -1321,6 +1623,7 @@ function _typeof(obj) { "@babel/helpers - typeof"; if (typeof Symbol === "functi
1321
1623
  ev = {
1322
1624
  NativeEvent: e,
1323
1625
  cell: self.getCellAt(pos.x, pos.y),
1626
+ pos: pos,
1324
1627
  items: items
1325
1628
  };
1326
1629
 
@@ -1394,8 +1697,10 @@ __webpack_require__.r(__webpack_exports__);
1394
1697
 
1395
1698
  /* harmony default export */ function __WEBPACK_DEFAULT_EXPORT__(self) {
1396
1699
  self.defaults = {
1397
- attributes: [['allowColumnReordering', true], ['allowColumnResize', true], ['allowColumnResizeFromCell', false], ['allowFreezingRows', false], ['allowFreezingColumns', false], ['allowMovingSelection', true], ['allowRowHeaderResize', true], ['allowRowReordering', false], ['allowRowResize', true], ['allowRowResizeFromCell', false], ['allowSorting', true], ['animationDurationShowContextMenu', 50], ['animationDurationHideContextMenu', 50], ['autoGenerateSchema', false], ['autoResizeColumns', false], ['autoResizeRows', false], ['autoScrollOnMousemove', false], ['autoScrollMargin', 5], ['blanksText', '(Blanks)'], ['borderDragBehavior', 'none'], ['borderResizeZone', 10], ['clearSettingsOptionText', 'Clear saved settings'], ['columnHeaderClickBehavior', 'sort'], ['columnSelectorHiddenText', '&nbsp;&nbsp;&nbsp;'], ['columnSelectorText', 'Add/Remove columns'], ['columnSelectorVisibleText', "\u2713"], ['contextHoverScrollAmount', 2], ['contextHoverScrollRateMs', 5], ['copyHeadersOnSelectAll', true], ['copyText', 'Copy'], ['debug', false], ['editable', true], ['ellipsisText', '...'], ['filterOptionText', 'Filter %s'], ['filterTextPrefix', '(filtered) '], ['filterFrozenRows', true], ['globalRowResize', false], ['hideColumnText', 'Hide %s'], ['hoverMode', 'cell'], ['keepFocusOnMouseOut', false], ['maxAutoCompleteItems', 200], ['multiLine', false], ['name', ''], ['pageUpDownOverlap', 1], ['pasteText', 'Paste'], ['persistantSelectionMode', false], ['removeFilterOptionText', 'Remove filter on %s'], ['reorderDeadZone', 3], ['resizeScrollZone', 20], ['rowGrabZoneSize', 5], ['saveAppearance', true], ['scrollAnimationPPSThreshold', 0.75], ['scrollPointerLock', false], ['scrollRepeatRate', 75], ['selectionFollowsActiveCell', false], ['selectionHandleBehavior', 'none'], ['selectionMode', 'cell'], ['selectionScrollIncrement', 20], ['selectionScrollZone', 20], ['showClearSettingsOption', true], ['showColumnHeaders', true], ['showColumnSelector', true], ['showCopy', false], ['showFilter', true], ['showFilterInCell', false], ['showNewRow', false], ['showOrderByOption', true], ['showOrderByOptionTextAsc', 'Order by %s ascending'], ['showOrderByOptionTextDesc', 'Order by %s descending'], ['showPaste', false], ['showPerformance', false], ['showRowHeaders', true], ['showRowNumbers', true], ['showRowNumberGaps', true], ['singleSelectionMode', false], ['snapToRow', false], ['sortFrozenRows', true], ['touchContextMenuTimeMs', 800], ['touchDeadZone', 3], ['touchEasingMethod', 'easeOutQuad'], ['touchReleaseAcceleration', 1000], ['touchReleaseAnimationDurationMs', 2000], ['touchScrollZone', 20], ['touchSelectHandleZone', 20], ['touchZoomSensitivity', 0.005], ['touchZoomMin', 0.5], ['touchZoomMax', 1.75], ['maxPixelRatio', 2], ['tree', false], ['treeHorizontalScroll', false]],
1398
- styles: [['activeCellBackgroundColor', 'rgba(255, 255, 255, 1)'], ['activeCellBorderColor', 'rgba(110, 168, 255, 1)'], ['activeCellBorderWidth', 1], ['activeCellColor', 'rgba(0, 0, 0, 1)'], ['activeCellFont', '16px sans-serif'], ['activeCellHoverBackgroundColor', 'rgba(255, 255, 255, 1)'], ['activeCellHorizontalAlignment', 'left'], ['activeCellHoverColor', 'rgba(0, 0, 0, 1)'], ['activeCellOverlayBorderColor', 'rgba(66, 133, 244, 1)'], ['activeCellOverlayBorderWidth', 1], ['activeCellPaddingBottom', 5], ['activeCellPaddingLeft', 5], ['activeCellPaddingRight', 5], ['activeCellPaddingTop', 5], ['activeCellSelectedBackgroundColor', 'rgba(236, 243, 255, 1)'], ['activeCellSelectedColor', 'rgba(0, 0, 0, 1)'], ['activeCellVerticalAlignment', 'center'], ['activeColumnHeaderCellBackgroundColor', 'rgba(225, 225, 225, 1)'], ['activeColumnHeaderCellColor', 'rgba(0, 0, 0, 1)'], ['activeRowHeaderCellBackgroundColor', 'rgba(225, 225, 225, 1)'], ['activeRowHeaderCellColor', 'rgba(0, 0, 0, 1)'], ['autocompleteBottomMargin', 60], ['autosizeHeaderCellPadding', 8], ['autosizePadding', 5], ['buttonActiveBackgroundColor', 'rgba(255, 255, 255, 1)'], ['buttonActiveBorderColor', 'rgba(110, 168, 255, 1)'], ['buttonArrowColor', 'rgba(50, 50, 50, 1)'], ['buttonArrowDownHTML', '&#x25BC;'], ['buttonZIndex', 10000], ['buttonBackgroundColor', 'rgba(255, 255, 255, 1)'], ['buttonBorderColor', 'rgba(172, 172, 172, 1)'], ['buttonHoverBackgroundColor', 'rgba(240, 240, 240, 1)'], ['buttonMenuWindowMargin', 30], ['buttonPadding', '3px'], ['cellAutoResizePadding', 13], ['cellBackgroundColor', 'rgba(255, 255, 255, 1)'], ['cellBorderColor', 'rgba(195, 199, 202, 1)'], ['cellBorderWidth', 1], ['cellColor', 'rgba(0, 0, 0, 1)'], ['cellFont', '16px sans-serif'], ['cellGridHeight', 250], ['cellHeight', 24], ['cellHeightWithChildGrid', 150], ['cellHorizontalAlignment', 'left'], ['cellHoverBackgroundColor', 'rgba(255, 255, 255, 1)'], ['cellHoverColor', 'rgba(0, 0, 0, 1)'], ['cellPaddingBottom', 5], ['cellPaddingLeft', 5], ['cellPaddingRight', 5], ['cellPaddingTop', 5], ['cellSelectedBackgroundColor', 'rgba(236, 243, 255, 1)'], ['cellSelectedColor', 'rgba(0, 0, 0, 1)'], ['cellVerticalAlignment', 'center'], ['cellWidth', 250], ['cellWidthWithChildGrid', 250], ['cellWhiteSpace', 'nowrap'], ['cellLineHeight', 1], ['cellLineSpacing', 3], ['childContextMenuArrowColor', 'rgba(43, 48, 43, 1)'], ['childContextMenuArrowHTML', '&#x25BA;'], ['childContextMenuMarginLeft', -11], ['childContextMenuMarginTop', -6], ['columnHeaderCellBackgroundColor', 'rgba(240, 240, 240, 1)'], ['columnHeaderCellBorderColor', 'rgba(172, 172, 172, 1)'], ['columnHeaderCellBorderWidth', 1], ['columnHeaderCellCapBackgroundColor', 'rgba(240, 240, 240, 1)'], ['columnHeaderCellCapBorderColor', 'rgba(172, 172, 172, 1)'], ['columnHeaderCellCapBorderWidth', 1], ['columnHeaderCellColor', 'rgba(50, 50, 50, 1)'], ['columnHeaderCellFont', '16px sans-serif'], ['columnHeaderCellHeight', 25], ['columnHeaderCellHorizontalAlignment', 'left'], ['columnHeaderCellHoverBackgroundColor', 'rgba(235, 235, 235, 1)'], ['columnHeaderCellHoverColor', 'rgba(0, 0, 0, 1)'], ['columnHeaderCellPaddingBottom', 5], ['columnHeaderCellPaddingLeft', 5], ['columnHeaderCellPaddingRight', 5], ['columnHeaderCellPaddingTop', 5], ['columnHeaderCellVerticalAlignment', 'center'], ['columnHeaderOrderByArrowBorderColor', 'rgba(195, 199, 202, 1)'], ['columnHeaderOrderByArrowBorderWidth', 1], ['columnHeaderOrderByArrowColor', 'rgba(155, 155, 155, 1)'], ['columnHeaderOrderByArrowHeight', 8], ['columnHeaderOrderByArrowMarginLeft', 0], ['columnHeaderOrderByArrowMarginRight', 5], ['columnHeaderOrderByArrowMarginTop', 6], ['columnHeaderOrderByArrowWidth', 13], ['contextFilterButtonBorder', 'solid 1px rgba(158, 163, 169, 1)'], ['contextFilterButtonBorderRadius', '3px'], ['contextFilterButtonHTML', '&#x25BC;'], ['contextFilterInputBackground', 'rgba(255,255,255,1)'], ['contextFilterInputBorder', 'solid 1px rgba(158, 163, 169, 1)'], ['contextFilterInputBorderRadius', '0'], ['contextFilterInputColor', 'rgba(0,0,0,1)'], ['contextFilterInputFontFamily', 'sans-serif'], ['contextFilterInputFontSize', '14px'], ['contextFilterInvalidRegExpBackground', 'rgba(180, 6, 1, 1)'], ['contextFilterInvalidRegExpColor', 'rgba(255, 255, 255, 1)'], ['contextMenuArrowColor', 'rgba(43, 48, 43, 1)'], ['contextMenuArrowDownHTML', '&#x25BC;'], ['contextMenuArrowUpHTML', '&#x25B2;'], ['contextMenuBackground', 'rgba(240, 240, 240, 1)'], ['contextMenuBorder', 'solid 1px rgba(158, 163, 169, 1)'], ['contextMenuBorderRadius', '3px'], ['contextMenuChildArrowFontSize', '12px'], ['contextMenuColor', 'rgba(43, 48, 43, 1)'], ['contextMenuCursor', 'default'], ['contextMenuFilterButtonFontFamily', 'sans-serif'], ['contextMenuFilterButtonFontSize', '10px'], ['contextMenuFilterInvalidExpresion', 'rgba(237, 155, 156, 1)'], ['contextMenuFontFamily', 'sans-serif'], ['contextMenuFontSize', '16px'], ['contextMenuHoverBackground', 'rgba(182, 205, 250, 1)'], ['contextMenuHoverColor', 'rgba(43, 48, 153, 1)'], ['contextMenuItemBorderRadius', '3px'], ['contextMenuItemMargin', '2px'], ['contextMenuLabelDisplay', 'inline-block'], ['contextMenuLabelMargin', '0 3px 0 0'], ['contextMenuLabelMaxWidth', '700px'], ['contextMenuLabelMinWidth', '75px'], ['contextMenuMarginLeft', 3], ['contextMenuMarginTop', -3], ['contextMenuOpacity', '0.98'], ['contextMenuPadding', '2px'], ['contextMenuWindowMargin', 30], ['contextMenuZIndex', 10000], ['cornerCellBackgroundColor', 'rgba(240, 240, 240, 1)'], ['cornerCellBorderColor', 'rgba(202, 202, 202, 1)'], ['debugBackgroundColor', 'rgba(0, 0, 0, .0)'], ['debugColor', 'rgba(255, 15, 24, 1)'], ['debugEntitiesColor', 'rgba(76, 231, 239, 1.00)'], ['debugFont', '11px sans-serif'], ['debugPerfChartBackground', 'rgba(29, 25, 26, 1.00)'], ['debugPerfChartTextColor', 'rgba(255, 255, 255, 0.8)'], ['debugPerformanceColor', 'rgba(252, 255, 37, 1.00)'], ['debugScrollHeightColor', 'rgba(248, 33, 103, 1.00)'], ['debugScrollWidthColor', 'rgba(66, 255, 27, 1.00)'], ['debugTouchPPSXColor', 'rgba(246, 102, 24, 1.00)'], ['debugTouchPPSYColor', 'rgba(186, 0, 255, 1.00)'], ['display', 'inline-block'], ['editCellBackgroundColor', 'white'], ['editCellBorder', 'solid 1px rgba(110, 168, 255, 1)'], ['editCellBoxShadow', '0 2px 5px rgba(0,0,0,0.4)'], ['editCellColor', 'black'], ['editCellFontFamily', 'sans-serif'], ['editCellFontSize', '16px'], ['editCellPaddingLeft', 4], ['editCellZIndex', 10000], ['filterButtonActiveBackgroundColor', 'rgba(225, 225, 225, 1)'], ['filterButtonArrowBorderColor', 'rgba(195, 199, 202, 1)'], ['filterButtonArrowBorderWidth', 1], ['filterButtonArrowClickRadius', 5], ['filterButtonArrowColor', 'rgba(50, 50, 50, 1)'], ['filterButtonArrowHeight', 5], ['filterButtonArrowWidth', 8], ['filterButtonBackgroundColor', 'rgba(240, 240, 240, 1)'], ['filterButtonBorderColor', 'rgba(172, 172, 172, 1)'], ['filterButtonBorderRadius', 3], ['filterButtonHeight', 20], ['filterButtonHoverBackgroundColor', 'rgba(235, 235, 235, 1)'], ['filterButtonMenuOffsetTop', 10], ['filterButtonWidth', 20], ['frozenMarkerHoverColor', 'rgba(236, 243, 255, 1)'], ['frozenMarkerHoverBorderColor', 'rgba(110, 168, 255, 1)'], ['frozenMarkerActiveColor', 'rgba(236, 243, 255, 1)'], ['frozenMarkerActiveBorderColor', 'rgba(110, 168, 255, 1)'], ['frozenMarkerColor', 'rgba(222, 222, 222, 1)'], ['frozenMarkerBorderColor', 'rgba(168, 168, 168, 1)'], ['frozenMarkerBorderWidth', 1], ['frozenMarkerWidth', 2], ['gridBackgroundColor', 'rgba(240, 240, 240, 1)'], ['gridBorderCollapse', 'collapse'], ['gridBorderColor', 'rgba(202, 202, 202, 1)'], ['gridBorderWidth', 1], ['height', 'auto'], ['maxHeight', 'inherit'], ['maxWidth', 'inherit'], ['minColumnWidth', 45], ['minHeight', 'inherit'], ['minRowHeight', 24], ['minWidth', 'inherit'], ['mobileContextMenuMargin', 10], ['mobileEditInputHeight', 30], ['mobileEditFontFamily', 'sans-serif'], ['mobileEditFontSize', '16px'], ['moveOverlayBorderWidth', 1], ['moveOverlayBorderColor', 'rgba(66, 133, 244, 1)'], ['moveOverlayBorderSegments', '12, 7'], ['name', 'default'], ['overflowY', 'auto'], ['overflowX', 'auto'], ['reorderMarkerBackgroundColor', 'rgba(0, 0, 0, 0.1)'], ['reorderMarkerBorderColor', 'rgba(0, 0, 0, 0.2)'], ['reorderMarkerBorderWidth', 1.25], ['reorderMarkerIndexBorderColor', 'rgba(66, 133, 244, 1)'], ['reorderMarkerIndexBorderWidth', 2.75], ['rowHeaderCellBackgroundColor', 'rgba(240, 240, 240, 1)'], ['rowHeaderCellBorderColor', 'rgba(200, 200, 200, 1)'], ['rowHeaderCellBorderWidth', 1], ['rowHeaderCellColor', 'rgba(50, 50, 50, 1)'], ['rowHeaderCellFont', '16px sans-serif'], ['rowHeaderCellHeight', 25], ['rowHeaderCellHorizontalAlignment', 'left'], ['rowHeaderCellHoverBackgroundColor', 'rgba(235, 235, 235, 1)'], ['rowHeaderCellHoverColor', 'rgba(0, 0, 0, 1)'], ['rowHeaderCellPaddingBottom', 5], ['rowHeaderCellPaddingLeft', 5], ['rowHeaderCellPaddingRight', 5], ['rowHeaderCellPaddingTop', 5], ['rowHeaderCellRowNumberGapHeight', 5], ['rowHeaderCellRowNumberGapColor', 'rgba(50, 50, 50, 1)'], ['rowHeaderCellSelectedBackgroundColor', 'rgba(217, 217, 217, 1)'], ['rowHeaderCellSelectedColor', 'rgba(50, 50, 50, 1)'], ['rowHeaderCellVerticalAlignment', 'center'], ['rowHeaderCellWidth', 57], ['scrollBarActiveColor', 'rgba(125, 125, 125, 1)'], ['scrollBarBackgroundColor', 'rgba(240, 240, 240, 1)'], ['scrollBarBorderColor', 'rgba(202, 202, 202, 1)'], ['scrollBarBorderWidth', 0.5], ['scrollBarBoxBorderRadius', 4.125], ['scrollBarBoxColor', 'rgba(192, 192, 192, 1)'], ['scrollBarBoxMargin', 2], ['scrollBarBoxMinSize', 15], ['scrollBarBoxWidth', 8], ['scrollBarCornerBackgroundColor', 'rgba(240, 240, 240, 1)'], ['scrollBarCornerBorderColor', 'rgba(202, 202, 202, 1)'], ['scrollBarWidth', 11], ['selectionHandleBorderColor', 'rgba(255, 255, 255, 1)'], ['selectionHandleBorderWidth', 1.5], ['selectionHandleColor', 'rgba(66, 133, 244, 1)'], ['selectionHandleSize', 8], ['selectionHandleType', 'square'], ['selectionOverlayBorderColor', 'rgba(66, 133, 244, 1)'], ['selectionOverlayBorderWidth', 1], ['treeArrowBorderColor', 'rgba(195, 199, 202, 1)'], ['treeArrowBorderWidth', 1], ['treeArrowClickRadius', 5], ['treeArrowColor', 'rgba(155, 155, 155, 1)'], ['treeArrowHeight', 8], ['treeArrowMarginLeft', 0], ['treeArrowMarginRight', 5], ['treeArrowMarginTop', 6], ['treeArrowWidth', 13], ['treeGridHeight', 250], ['width', 'auto']]
1700
+ attributes: [['allowColumnReordering', true], ['allowColumnResize', true], ['allowColumnResizeFromCell', false], ['allowFreezingRows', false], ['allowFreezingColumns', false], ['allowMovingSelection', true], ['allowRowHeaderResize', true], ['allowRowReordering', false], ['allowRowResize', true], ['allowRowResizeFromCell', false], ['allowSorting', true], ['allowGroupingRows', true], ['allowGroupingColumns', true], ['animationDurationShowContextMenu', 50], ['animationDurationHideContextMenu', 50], ['autoGenerateSchema', false], ['autoResizeColumns', false], ['autoResizeRows', false], ['autoScrollOnMousemove', false], ['autoScrollMargin', 5], ['blanksText', '(Blanks)'], ['borderDragBehavior', 'none'], ['borderResizeZone', 10], ['clearSettingsOptionText', 'Clear saved settings'], ['columnHeaderClickBehavior', 'sort'], ['columnSelectorHiddenText', '&nbsp;&nbsp;&nbsp;'], ['columnSelectorText', 'Add/Remove columns'], ['columnSelectorVisibleText', "\u2713"], ['contextHoverScrollAmount', 2], ['contextHoverScrollRateMs', 5], ['copyHeadersOnSelectAll', true], ['copyText', 'Copy'], ['debug', false], ['editable', true], ['ellipsisText', '...'], ['filterOptionText', 'Filter %s'], ['filterTextPrefix', '(filtered) '], ['filterFrozenRows', true], ['globalRowResize', false], ['hideColumnText', 'Hide %s'], ['hoverMode', 'cell'], ['keepFocusOnMouseOut', false], ['maxAutoCompleteItems', 200], ['multiLine', false], ['name', ''], ['pageUpDownOverlap', 1], ['pasteText', 'Paste'], ['persistantSelectionMode', false], ['removeFilterOptionText', 'Remove filter on %s'], ['reorderDeadZone', 3], ['resizeScrollZone', 20], ['rowGrabZoneSize', 5], ['saveAppearance', true], ['scrollAnimationPPSThreshold', 0.75], ['scrollPointerLock', false], ['scrollRepeatRate', 75], ['selectionFollowsActiveCell', false], ['selectionHandleBehavior', 'none'], ['selectionMode', 'cell'], ['selectionScrollIncrement', 20], ['selectionScrollZone', 20], ['showClearSettingsOption', true], ['showColumnHeaders', true], ['showColumnSelector', true], ['showCopy', false], ['showFilter', true], ['showFilterInCell', false], ['showNewRow', false], ['showOrderByOption', true], ['showOrderByOptionTextAsc', 'Order by %s ascending'], ['showOrderByOptionTextDesc', 'Order by %s descending'], //#region grouping
1701
+ ['showGroupColumns', 'Group columns %s'], ['showGroupRows', 'Group rows %s'], ['showRemoveGroupColumns', 'Remove group %s'], ['showRemoveGroupRows', 'Remove group %s'], ['showRemoveAllGroupColumns', 'Remove all column groups'], ['showRemoveAllGroupRows', 'Remove all row groups'], ['showExpandAllGroupColumns', 'Expand all column groups'], ['showExpandAllGroupRows', 'Expand all row groups'], ['showCollapseAllGroupColumns', 'Collapse all column groups'], ['showCollapseAllGroupRows', 'Collapse all row groups'], ['columnGroupIndicatorPosition', 'right'], ['rowGroupIndicatorPosition', 'bottom'], //#endregion grouping
1702
+ ['showPaste', false], ['showPerformance', false], ['showRowHeaders', true], ['showRowNumbers', true], ['showRowNumberGaps', true], ['singleSelectionMode', false], ['snapToRow', false], ['sortFrozenRows', true], ['touchContextMenuTimeMs', 800], ['touchDeadZone', 3], ['touchEasingMethod', 'easeOutQuad'], ['touchReleaseAcceleration', 1000], ['touchReleaseAnimationDurationMs', 2000], ['touchScrollZone', 20], ['touchSelectHandleZone', 20], ['touchZoomSensitivity', 0.005], ['touchZoomMin', 0.5], ['touchZoomMax', 1.75], ['maxPixelRatio', 2], ['tree', false], ['treeHorizontalScroll', false], ['rowTree', []], ['rowTreeColIndex', 0], ['columnTree', []], ['columnTreeRowStartIndex', 0], ['columnTreeRowEndIndex', 0]],
1703
+ styles: [['activeCellBackgroundColor', 'rgba(255, 255, 255, 1)'], ['activeCellBorderColor', 'rgba(110, 168, 255, 1)'], ['activeCellBorderWidth', 1], ['activeCellColor', 'rgba(0, 0, 0, 1)'], ['activeCellFont', '16px sans-serif'], ['activeCellHoverBackgroundColor', 'rgba(255, 255, 255, 1)'], ['activeCellHorizontalAlignment', 'left'], ['activeCellHoverColor', 'rgba(0, 0, 0, 1)'], ['activeCellOverlayBorderColor', 'rgba(66, 133, 244, 1)'], ['activeCellOverlayBorderWidth', 1], ['activeCellPaddingBottom', 5], ['activeCellPaddingLeft', 5], ['activeCellPaddingRight', 5], ['activeCellPaddingTop', 5], ['activeCellSelectedBackgroundColor', 'rgba(236, 243, 255, 1)'], ['activeCellSelectedColor', 'rgba(0, 0, 0, 1)'], ['activeCellVerticalAlignment', 'center'], ['activeColumnHeaderCellBackgroundColor', 'rgba(225, 225, 225, 1)'], ['activeColumnHeaderCellColor', 'rgba(0, 0, 0, 1)'], ['activeRowHeaderCellBackgroundColor', 'rgba(225, 225, 225, 1)'], ['activeRowHeaderCellColor', 'rgba(0, 0, 0, 1)'], ['autocompleteBottomMargin', 60], ['autosizeHeaderCellPadding', 8], ['autosizePadding', 5], ['buttonActiveBackgroundColor', 'rgba(255, 255, 255, 1)'], ['buttonActiveBorderColor', 'rgba(110, 168, 255, 1)'], ['buttonArrowColor', 'rgba(50, 50, 50, 1)'], ['buttonArrowDownHTML', '&#x25BC;'], ['buttonZIndex', 10000], ['buttonBackgroundColor', 'rgba(255, 255, 255, 1)'], ['buttonBorderColor', 'rgba(172, 172, 172, 1)'], ['buttonHoverBackgroundColor', 'rgba(240, 240, 240, 1)'], ['buttonMenuWindowMargin', 30], ['buttonPadding', '3px'], ['cellAutoResizePadding', 13], ['cellBackgroundColor', 'rgba(255, 255, 255, 1)'], ['cellBorderColor', 'rgba(195, 199, 202, 1)'], ['cellBorderWidth', 1], ['cellColor', 'rgba(0, 0, 0, 1)'], ['cellFont', '16px sans-serif'], ['cellGridHeight', 250], ['cellHeight', 24], ['cellHeightWithChildGrid', 150], ['cellHorizontalAlignment', 'left'], ['cellHoverBackgroundColor', 'rgba(255, 255, 255, 1)'], ['cellHoverColor', 'rgba(0, 0, 0, 1)'], ['cellPaddingBottom', 5], ['cellPaddingLeft', 5], ['cellPaddingRight', 5], ['cellPaddingTop', 5], ['cellSelectedBackgroundColor', 'rgba(236, 243, 255, 1)'], ['cellSelectedColor', 'rgba(0, 0, 0, 1)'], ['cellTreeIconBorderColor', 'rgba(162, 174, 207, 1)'], ['cellTreeIconFillColor', 'rgba(240, 240, 240, 1)'], ['cellTreeIconHoverFillColor', 'rgba(198, 217, 233, 1)'], ['cellTreeIconLineColor', 'rgba(43, 53, 81, 1)'], ['cellTreeIconLineWidth', 1.5], ['cellTreeIconMarginLeft', 0], ['cellTreeIconMarginRight', 5], ['cellTreeIconMarginTop', 6], ['cellTreeIconWidth', 13], ['cellVerticalAlignment', 'center'], ['cellWidth', 250], ['cellWidthWithChildGrid', 250], ['cellWhiteSpace', 'nowrap'], ['cellLineHeight', 1], ['cellLineSpacing', 3], ['childContextMenuArrowColor', 'rgba(43, 48, 43, 1)'], ['childContextMenuArrowHTML', '&#x25BA;'], ['childContextMenuMarginLeft', -11], ['childContextMenuMarginTop', -6], ['columnGroupRowHeight', 25], ['columnHeaderCellBackgroundColor', 'rgba(240, 240, 240, 1)'], ['columnHeaderCellBorderColor', 'rgba(172, 172, 172, 1)'], ['columnHeaderCellBorderWidth', 1], ['columnHeaderCellCapBackgroundColor', 'rgba(240, 240, 240, 1)'], ['columnHeaderCellCapBorderColor', 'rgba(172, 172, 172, 1)'], ['columnHeaderCellCapBorderWidth', 1], ['columnHeaderCellColor', 'rgba(50, 50, 50, 1)'], ['columnHeaderCellFont', '16px sans-serif'], ['columnHeaderCellHeight', 25], ['columnHeaderCellHorizontalAlignment', 'left'], ['columnHeaderCellHoverBackgroundColor', 'rgba(235, 235, 235, 1)'], ['columnHeaderCellHoverColor', 'rgba(0, 0, 0, 1)'], ['columnHeaderCellPaddingBottom', 5], ['columnHeaderCellPaddingLeft', 5], ['columnHeaderCellPaddingRight', 5], ['columnHeaderCellPaddingTop', 5], ['columnHeaderCellVerticalAlignment', 'center'], ['columnHeaderOrderByArrowBorderColor', 'rgba(195, 199, 202, 1)'], ['columnHeaderOrderByArrowBorderWidth', 1], ['columnHeaderOrderByArrowColor', 'rgba(155, 155, 155, 1)'], ['columnHeaderOrderByArrowHeight', 8], ['columnHeaderOrderByArrowMarginLeft', 0], ['columnHeaderOrderByArrowMarginRight', 5], ['columnHeaderOrderByArrowMarginTop', 6], ['columnHeaderOrderByArrowWidth', 13], ['contextFilterButtonBorder', 'solid 1px rgba(158, 163, 169, 1)'], ['contextFilterButtonBorderRadius', '3px'], ['contextFilterButtonHTML', '&#x25BC;'], ['contextFilterInputBackground', 'rgba(255,255,255,1)'], ['contextFilterInputBorder', 'solid 1px rgba(158, 163, 169, 1)'], ['contextFilterInputBorderRadius', '0'], ['contextFilterInputColor', 'rgba(0,0,0,1)'], ['contextFilterInputFontFamily', 'sans-serif'], ['contextFilterInputFontSize', '14px'], ['contextFilterInvalidRegExpBackground', 'rgba(180, 6, 1, 1)'], ['contextFilterInvalidRegExpColor', 'rgba(255, 255, 255, 1)'], ['contextMenuArrowColor', 'rgba(43, 48, 43, 1)'], ['contextMenuArrowDownHTML', '&#x25BC;'], ['contextMenuArrowUpHTML', '&#x25B2;'], ['contextMenuBackground', 'rgba(240, 240, 240, 1)'], ['contextMenuBorder', 'solid 1px rgba(158, 163, 169, 1)'], ['contextMenuBorderRadius', '3px'], ['contextMenuChildArrowFontSize', '12px'], ['contextMenuColor', 'rgba(43, 48, 43, 1)'], ['contextMenuCursor', 'default'], ['contextMenuFilterButtonFontFamily', 'sans-serif'], ['contextMenuFilterButtonFontSize', '10px'], ['contextMenuFilterInvalidExpresion', 'rgba(237, 155, 156, 1)'], ['contextMenuFontFamily', 'sans-serif'], ['contextMenuFontSize', '16px'], ['contextMenuHoverBackground', 'rgba(182, 205, 250, 1)'], ['contextMenuHoverColor', 'rgba(43, 48, 153, 1)'], ['contextMenuItemBorderRadius', '3px'], ['contextMenuItemMargin', '2px'], ['contextMenuLabelDisplay', 'inline-block'], ['contextMenuLabelMargin', '0 3px 0 0'], ['contextMenuLabelMaxWidth', '700px'], ['contextMenuLabelMinWidth', '75px'], ['contextMenuMarginLeft', 3], ['contextMenuMarginTop', -3], ['contextMenuOpacity', '0.98'], ['contextMenuPadding', '2px'], ['contextMenuWindowMargin', 30], ['contextMenuZIndex', 10000], ['cornerCellBackgroundColor', 'rgba(240, 240, 240, 1)'], ['cornerCellBorderColor', 'rgba(202, 202, 202, 1)'], ['debugBackgroundColor', 'rgba(0, 0, 0, .0)'], ['debugColor', 'rgba(255, 15, 24, 1)'], ['debugEntitiesColor', 'rgba(76, 231, 239, 1.00)'], ['debugFont', '11px sans-serif'], ['debugPerfChartBackground', 'rgba(29, 25, 26, 1.00)'], ['debugPerfChartTextColor', 'rgba(255, 255, 255, 0.8)'], ['debugPerformanceColor', 'rgba(252, 255, 37, 1.00)'], ['debugScrollHeightColor', 'rgba(248, 33, 103, 1.00)'], ['debugScrollWidthColor', 'rgba(66, 255, 27, 1.00)'], ['debugTouchPPSXColor', 'rgba(246, 102, 24, 1.00)'], ['debugTouchPPSYColor', 'rgba(186, 0, 255, 1.00)'], ['display', 'inline-block'], ['editCellBackgroundColor', 'white'], ['editCellBorder', 'solid 1px rgba(110, 168, 255, 1)'], ['editCellBoxShadow', '0 2px 5px rgba(0,0,0,0.4)'], ['editCellColor', 'black'], ['editCellFontFamily', 'sans-serif'], ['editCellFontSize', '16px'], ['editCellPaddingLeft', 4], ['editCellZIndex', 10000], ['filterButtonActiveBackgroundColor', 'rgba(225, 225, 225, 1)'], ['filterButtonArrowBorderColor', 'rgba(195, 199, 202, 1)'], ['filterButtonArrowBorderWidth', 1], ['filterButtonArrowClickRadius', 5], ['filterButtonArrowColor', 'rgba(50, 50, 50, 1)'], ['filterButtonArrowHeight', 5], ['filterButtonArrowWidth', 8], ['filterButtonBackgroundColor', 'rgba(240, 240, 240, 1)'], ['filterButtonBorderColor', 'rgba(172, 172, 172, 1)'], ['filterButtonBorderRadius', 3], ['filterButtonHeight', 20], ['filterButtonHoverBackgroundColor', 'rgba(235, 235, 235, 1)'], ['filterButtonMenuOffsetTop', 10], ['filterButtonWidth', 20], ['frozenMarkerHoverColor', 'rgba(236, 243, 255, 1)'], ['frozenMarkerHoverBorderColor', 'rgba(110, 168, 255, 1)'], ['frozenMarkerActiveColor', 'rgba(236, 243, 255, 1)'], ['frozenMarkerActiveBorderColor', 'rgba(110, 168, 255, 1)'], ['frozenMarkerColor', 'rgba(222, 222, 222, 1)'], ['frozenMarkerBorderColor', 'rgba(168, 168, 168, 1)'], ['frozenMarkerBorderWidth', 1], ['frozenMarkerWidth', 2], ['groupingAreaBackgroundColor', 'rgba(240, 240, 240, 1)'], ['gridBackgroundColor', 'rgba(240, 240, 240, 1)'], ['gridBorderCollapse', 'collapse'], ['gridBorderColor', 'rgba(202, 202, 202, 1)'], ['gridBorderWidth', 1], ['groupIndicatorColor', 'rgba(155, 155, 155, 1)'], ['groupIndicatorBackgroundColor', 'rgba(255, 255, 255, 1)'], ['height', 'auto'], ['maxHeight', 'inherit'], ['maxWidth', 'inherit'], ['minColumnWidth', 45], ['minHeight', 'inherit'], ['minRowHeight', 24], ['minWidth', 'inherit'], ['mobileContextMenuMargin', 10], ['mobileEditInputHeight', 30], ['mobileEditFontFamily', 'sans-serif'], ['mobileEditFontSize', '16px'], ['moveOverlayBorderWidth', 1], ['moveOverlayBorderColor', 'rgba(66, 133, 244, 1)'], ['moveOverlayBorderSegments', '12, 7'], ['name', 'default'], ['overflowY', 'auto'], ['overflowX', 'auto'], ['reorderMarkerBackgroundColor', 'rgba(0, 0, 0, 0.1)'], ['reorderMarkerBorderColor', 'rgba(0, 0, 0, 0.2)'], ['reorderMarkerBorderWidth', 1.25], ['reorderMarkerIndexBorderColor', 'rgba(66, 133, 244, 1)'], ['reorderMarkerIndexBorderWidth', 2.75], ['rowGroupColumnWidth', 25], ['rowHeaderCellBackgroundColor', 'rgba(240, 240, 240, 1)'], ['rowHeaderCellBorderColor', 'rgba(200, 200, 200, 1)'], ['rowHeaderCellBorderWidth', 1], ['rowHeaderCellColor', 'rgba(50, 50, 50, 1)'], ['rowHeaderCellFont', '16px sans-serif'], ['rowHeaderCellHeight', 25], ['rowHeaderCellHorizontalAlignment', 'left'], ['rowHeaderCellHoverBackgroundColor', 'rgba(235, 235, 235, 1)'], ['rowHeaderCellHoverColor', 'rgba(0, 0, 0, 1)'], ['rowHeaderCellPaddingBottom', 5], ['rowHeaderCellPaddingLeft', 5], ['rowHeaderCellPaddingRight', 5], ['rowHeaderCellPaddingTop', 5], ['rowHeaderCellRowNumberGapHeight', 5], ['rowHeaderCellRowNumberGapColor', 'rgba(50, 50, 50, 1)'], ['rowHeaderCellSelectedBackgroundColor', 'rgba(217, 217, 217, 1)'], ['rowHeaderCellSelectedColor', 'rgba(50, 50, 50, 1)'], ['rowHeaderCellVerticalAlignment', 'center'], ['rowHeaderCellWidth', 57], ['scrollBarActiveColor', 'rgba(125, 125, 125, 1)'], ['scrollBarBackgroundColor', 'rgba(240, 240, 240, 1)'], ['scrollBarBorderColor', 'rgba(202, 202, 202, 1)'], ['scrollBarBorderWidth', 0.5], ['scrollBarBoxBorderRadius', 4.125], ['scrollBarBoxColor', 'rgba(192, 192, 192, 1)'], ['scrollBarBoxMargin', 2], ['scrollBarBoxMinSize', 15], ['scrollBarBoxWidth', 8], ['scrollBarCornerBackgroundColor', 'rgba(240, 240, 240, 1)'], ['scrollBarCornerBorderColor', 'rgba(202, 202, 202, 1)'], ['scrollBarWidth', 11], ['selectionHandleBorderColor', 'rgba(255, 255, 255, 1)'], ['selectionHandleBorderWidth', 1.5], ['selectionHandleColor', 'rgba(66, 133, 244, 1)'], ['selectionHandleSize', 8], ['selectionHandleType', 'square'], ['selectionOverlayBorderColor', 'rgba(66, 133, 244, 1)'], ['selectionOverlayBorderWidth', 1], ['treeArrowBorderColor', 'rgba(195, 199, 202, 1)'], ['treeArrowBorderWidth', 1], ['treeArrowClickRadius', 5], ['treeArrowColor', 'rgba(155, 155, 155, 1)'], ['treeArrowHeight', 8], ['treeArrowMarginLeft', 0], ['treeArrowMarginRight', 5], ['treeArrowMarginTop', 6], ['treeArrowWidth', 13], ['treeGridHeight', 250], ['width', 'auto']]
1399
1704
  };
1400
1705
  }
1401
1706
 
@@ -1524,8 +1829,19 @@ __webpack_require__.r(__webpack_exports__);
1524
1829
  return;
1525
1830
  }
1526
1831
 
1527
- self.input.style.left = pos.left + cell.x + self.canvasOffsetLeft - s.left + 'px';
1528
- self.input.style.top = pos.top + cell.y - self.style.cellBorderWidth + self.canvasOffsetTop - s.top + 'px';
1832
+ var groupAreaOffsetY = self.getColumnGroupAreaHeight();
1833
+ var groupAreaOffsetX = self.getRowGroupAreaWidth();
1834
+
1835
+ if (self.parentNode) {
1836
+ var _self$parentNode = self.parentNode,
1837
+ columnGroupsAreaHeight = _self$parentNode.columnGroupsAreaHeight,
1838
+ rowGroupsAreaWidth = _self$parentNode.rowGroupsAreaWidth;
1839
+ if (columnGroupsAreaHeight) groupAreaOffsetY += columnGroupsAreaHeight;
1840
+ if (rowGroupsAreaWidth) groupAreaOffsetX += rowGroupsAreaWidth;
1841
+ }
1842
+
1843
+ self.input.style.left = pos.left + cell.x + self.canvasOffsetLeft - s.left + groupAreaOffsetX + 'px';
1844
+ self.input.style.top = pos.top + cell.y - self.style.cellBorderWidth + self.canvasOffsetTop - s.top + groupAreaOffsetY + 'px';
1529
1845
  self.input.style.height = cell.height - borderWidth + 'px';
1530
1846
  self.input.style.width = cell.width - self.style.cellPaddingLeft + 'px';
1531
1847
  self.clipElement(self.input);
@@ -1583,6 +1899,8 @@ __webpack_require__.r(__webpack_exports__);
1583
1899
  if (self.isChildGrid) {
1584
1900
  pos.x -= self.canvasOffsetLeft;
1585
1901
  pos.y -= self.canvasOffsetTop;
1902
+ if (self.parentNode.rowGroupsAreaWidth) pos.x -= self.parentNode.rowGroupsAreaWidth;
1903
+ if (self.parentNode.columnGroupsAreaHeight) pos.y -= self.parentNode.columnGroupsAreaHeight;
1586
1904
  }
1587
1905
 
1588
1906
  return {
@@ -2351,6 +2669,40 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2351
2669
 
2352
2670
  img.src = 'data:image/svg+xml;base64,' + btoa('<svg xmlns="http://www.w3.org/2000/svg" width="' + cell.width + '" height="' + cell.height + '">\n' + '<foreignObject class="node" x="0" y="0" width="100%" height="100%">\n' + '<body xmlns="http://www.w3.org/1999/xhtml" style="margin:0;padding:0;">\n' + v + '\n' + '</body>' + '</foreignObject>\n' + '</svg>\n');
2353
2671
  }
2672
+ /**
2673
+ * @param {number[]} coords [x0,y0, x1,y1, x2,y2, ...]
2674
+ */
2675
+
2676
+
2677
+ function strokeLines(coords) {
2678
+ if (coords.length < 4) return;
2679
+ self.ctx.beginPath();
2680
+ self.ctx.moveTo(coords[0] + self.canvasOffsetLeft, coords[1] + self.canvasOffsetTop);
2681
+
2682
+ for (var i = 2; i < coords.length; i += 2) {
2683
+ var x = coords[i] + self.canvasOffsetLeft;
2684
+ var y = coords[i + 1] + self.canvasOffsetTop;
2685
+ self.ctx.lineTo(x, y);
2686
+ }
2687
+
2688
+ self.ctx.stroke();
2689
+ }
2690
+ /**
2691
+ * @param {number} x based-X (left-top)
2692
+ * @param {number} y based-Y (left-top)
2693
+ * @param {number} width
2694
+ * @param {boolean} collapsed true: '+'; false: '-'
2695
+ */
2696
+
2697
+
2698
+ function drawGroupHandle(x, y, width, collapsed) {
2699
+ fillRect(x, y, width, width);
2700
+ strokeRect(x, y, width, width);
2701
+ var cx = x + width * 0.5;
2702
+ var cy = y + width * 0.5;
2703
+ strokeLines([x + width * 0.2, cy, x + width * 0.78, cy]);
2704
+ if (collapsed) strokeLines([cx, y + width * 0.22, cx, y + width * 0.8]);
2705
+ }
2354
2706
 
2355
2707
  function drawOrderByArrow(x, y) {
2356
2708
  var mt = self.style.columnHeaderOrderByArrowMarginTop * self.scale,
@@ -2414,6 +2766,52 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2414
2766
  return ml + aw + mr;
2415
2767
  }
2416
2768
 
2769
+ function drawCellTreeIcon(cell, tree, rowTree) {
2770
+ var parentCount = rowTree ? tree.parentCount : 0;
2771
+ var iconSize = self.style.cellTreeIconWidth * self.scale,
2772
+ marginTop = self.style.cellTreeIconMarginTop * self.scale,
2773
+ marginRight = self.style.cellTreeIconMarginRight * self.scale,
2774
+ marginLeft = self.style.cellTreeIconMarginLeft * self.scale + parentCount * (iconSize + cell.paddingLeft);
2775
+ var x = cell.x + cell.paddingLeft + self.canvasOffsetLeft + marginLeft,
2776
+ y = cell.y + self.canvasOffsetTop + marginTop;
2777
+
2778
+ if (tree.icon) {
2779
+ self.ctx.beginPath();
2780
+ var oldFillStyle = self.ctx.fillStyle;
2781
+ var oldStrokeStyle = self.ctx.strokeStyle;
2782
+
2783
+ if (cell.hovered && self.hovers.onCellTreeIcon) {
2784
+ self.ctx.fillStyle = self.style.cellTreeIconHoverFillColor;
2785
+ } else {
2786
+ self.ctx.fillStyle = self.style.cellTreeIconFillColor;
2787
+ }
2788
+
2789
+ self.ctx.fillRect(x, y, iconSize, iconSize);
2790
+ self.ctx.strokeStyle = self.style.cellTreeIconBorderColor;
2791
+ self.ctx.rect(x, y, iconSize, iconSize);
2792
+ self.ctx.stroke();
2793
+ self.ctx.beginPath();
2794
+
2795
+ if (tree.expand) {
2796
+ self.ctx.moveTo(x + 3, y + iconSize * 0.5);
2797
+ self.ctx.lineTo(x + iconSize - 3, y + iconSize * 0.5);
2798
+ } else {
2799
+ self.ctx.moveTo(x + 2, y + iconSize * 0.5);
2800
+ self.ctx.lineTo(x + iconSize - 2, y + iconSize * 0.5);
2801
+ self.ctx.moveTo(x + iconSize * 0.5, y + 2);
2802
+ self.ctx.lineTo(x + iconSize * 0.5, y + iconSize - 2);
2803
+ }
2804
+
2805
+ self.ctx.lineWidth = self.style.cellTreeIconLineWidth;
2806
+ self.ctx.strokeStyle = self.style.cellTreeIconLineColor;
2807
+ self.ctx.stroke();
2808
+ self.ctx.strokeStyle = oldStrokeStyle;
2809
+ self.ctx.fillStyle = oldFillStyle;
2810
+ }
2811
+
2812
+ return marginLeft + iconSize + marginRight;
2813
+ }
2814
+
2417
2815
  function drawFilterButtonArrow(x, y) {
2418
2816
  var mt = (self.style.filterButtonHeight - self.style.filterButtonArrowHeight) / 2 * self.scale,
2419
2817
  ml = (self.style.filterButtonWidth - self.style.filterButtonArrowWidth) / 2 * self.scale,
@@ -2719,6 +3117,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2719
3117
  }
2720
3118
 
2721
3119
  function drawText(cell) {
3120
+ var treeCellPadding = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
2722
3121
  var ll = cell.text.lines.length,
2723
3122
  h = cell.fontHeight * cell.lineHeight,
2724
3123
  x,
@@ -2729,12 +3128,12 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2729
3128
  for (x = 0; x < cell.text.lines.length; x += 1) {
2730
3129
  line = cell.text.lines[x];
2731
3130
  var vPos = Math.max((cell.height - (wrap ? cell.text.height : cell.calculatedLineHeight)) * 0.5, 0) + h,
2732
- hPos = cell.paddingLeft + cell.treeArrowWidth + cell.orderByArrowWidth;
3131
+ hPos = cell.paddingLeft + treeCellPadding + cell.treeArrowWidth + cell.orderByArrowWidth;
2733
3132
 
2734
3133
  if (cell.horizontalAlignment === 'right') {
2735
- hPos = cell.paddingLeft + cell.paddedWidth - line.width;
3134
+ hPos = cell.paddingLeft + treeCellPadding + cell.paddedWidth - line.width;
2736
3135
  } else if (cell.horizontalAlignment === 'center') {
2737
- hPos = cell.paddingLeft + (cell.paddedWidth + cell.paddingRight) / 2 - line.width / 2;
3136
+ hPos = cell.paddingLeft + treeCellPadding + (cell.paddedWidth + cell.paddingRight) / 2 - line.width / 2;
2738
3137
  }
2739
3138
 
2740
3139
  if (cell.verticalAlignment === 'top') {
@@ -2780,6 +3179,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2780
3179
  s = self.getSchema(),
2781
3180
  x = 0,
2782
3181
  n = Math.min(self.frozenColumn, s.length),
3182
+ collapsedGroups = self.getCollapsedColumnGroups(),
2783
3183
  column;
2784
3184
  hiddenFrozenColumnCount = 0;
2785
3185
 
@@ -2789,7 +3189,15 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2789
3189
  if (column.hidden) {
2790
3190
  hiddenFrozenColumnCount += 1;
2791
3191
  } else {
2792
- w += self.getColumnWidth(x);
3192
+ var isCollapsed = collapsedGroups.findIndex(function (group) {
3193
+ return x >= group.from && x <= group.to;
3194
+ }) >= 0;
3195
+
3196
+ if (isCollapsed) {
3197
+ hiddenFrozenColumnCount += 1;
3198
+ } else {
3199
+ w += self.getColumnWidth(x);
3200
+ }
2793
3201
  }
2794
3202
 
2795
3203
  x += 1;
@@ -2867,6 +3275,19 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2867
3275
  u = self.currentCell || {},
2868
3276
  columnHeaderCellHeight = self.getColumnHeaderCellHeight(),
2869
3277
  rowHeaderCellWidth = self.getRowHeaderCellWidth(),
3278
+ rowGroupsAreaWidth = self.getRowGroupAreaWidth(),
3279
+ columnGroupsAreaHeight = self.getColumnGroupAreaHeight(),
3280
+
3281
+ /** key: boundRowIndex, value: `{y,h}` */
3282
+ rowGroupsRectInfo = {},
3283
+
3284
+ /** value: `{y,h}` */
3285
+ rowGroupsFrozenInfo = {},
3286
+
3287
+ /** key: columnIndex, value: `{x,w}` */
3288
+ columnGroupsRectInfo = {},
3289
+ collapsedColumnGroups = self.getCollapsedColumnGroups(),
3290
+ collapsedRowGroups = self.getCollapsedRowGroups(),
2870
3291
  cellHeight = self.style.cellHeight;
2871
3292
  drawCount += 1;
2872
3293
  p = performance.now();
@@ -2876,6 +3297,36 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
2876
3297
  self.createRowOrders();
2877
3298
  }
2878
3299
 
3300
+ function saveRowGroupsRectInfo(cell) {
3301
+ var index = cell.boundRowIndex;
3302
+ if (index >= -1 === false) if (cell.rowIndex === -1) index = -1;else return;
3303
+ if (rowGroupsRectInfo[index]) return;
3304
+ rowGroupsRectInfo[index] = {
3305
+ y: cell.y,
3306
+ h: cell.height
3307
+ };
3308
+ }
3309
+
3310
+ function saveColumnGroupsRectInfo(cell) {
3311
+ var index = cell.columnIndex;
3312
+ if (columnGroupsRectInfo[index]) return;
3313
+ columnGroupsRectInfo[index] = {
3314
+ x: cell.x,
3315
+ w: cell.width
3316
+ };
3317
+ }
3318
+ /**
3319
+ * @param {number} columnIndex
3320
+ * @returns {boolean}
3321
+ */
3322
+
3323
+
3324
+ function isColumnCollapsedByGroup(columnIndex) {
3325
+ return collapsedColumnGroups.findIndex(function (group) {
3326
+ return columnIndex >= group.from && columnIndex <= group.to;
3327
+ }) >= 0;
3328
+ }
3329
+
2879
3330
  function drawScrollBars() {
2880
3331
  var drawCorner,
2881
3332
  en = self.scrollBox.entities,
@@ -3126,7 +3577,9 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3126
3577
  parentGrid: self.intf,
3127
3578
  innerHTML: '',
3128
3579
  activeHeader: activeHeader,
3129
- value: isHeader && !isRowHeader ? header.title || header.name : rawValue
3580
+ value: isHeader && !isRowHeader ? header.title || header.name : rawValue,
3581
+ isRowTree: rowOrderIndex >= 0 && columnOrderIndex == self.cellTree.rowTreeColIndex && self.cellTree.rows.length > 0 && self.cellTree.rows[rowOrderIndex].icon,
3582
+ isColumnTree: columnOrderIndex >= 0 && self.cellTree.columns[rowOrderIndex] && self.cellTree.columns[rowOrderIndex][columnOrderIndex].icon
3130
3583
  };
3131
3584
  cell.calculatedLineHeight = cell.fontHeight * cell.lineHeight + cell.lineSpacing;
3132
3585
  cell.paddedWidth = cell.width - cell.paddingRight - cell.paddingLeft;
@@ -3135,6 +3588,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3135
3588
  cell.userHeight = cell.isHeader ? self.sizes.rows[-1] : rowHeight;
3136
3589
  cell.userWidth = cell.isHeader ? self.sizes.columns.cornerCell : self.sizes.columns[headerIndex];
3137
3590
  self.visibleCells.unshift(cell);
3591
+ saveRowGroupsRectInfo(cell);
3592
+ saveColumnGroupsRectInfo(cell);
3138
3593
 
3139
3594
  if (self.dispatchEvent('beforerendercell', ev)) {
3140
3595
  return;
@@ -3277,7 +3732,27 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3277
3732
  if (cell.innerHTML || header.type === 'html') {
3278
3733
  drawHtml(cell);
3279
3734
  } else {
3280
- drawText(cell);
3735
+ var treeCellPadding = 0,
3736
+ isDrawText = true;
3737
+ if (cell.columnIndex == self.cellTree.rowTreeColIndex && !cell.isColumnHeader && self.cellTree.rows.length > 0 && Object.keys(self.cellTree.rows[cell.rowIndex]).length > 1) treeCellPadding = drawCellTreeIcon(cell, self.cellTree.rows[cell.rowIndex], true);
3738
+
3739
+ if (!cell.isRowHeader && cell.rowIndex > 0 && self.cellTree.columns[cell.rowIndex - 1] && self.cellTree.columns[cell.rowIndex - 1][cell.columnIndex].icon) {
3740
+ for (var r = cell.rowIndex - 1; r >= 0; r--) {
3741
+ if (!self.cellTree.columns[r]) break;
3742
+ if (!self.cellTree.columns[r][cell.columnIndex].icon) break;
3743
+
3744
+ if (!self.cellTree.columns[r][cell.columnIndex].expand) {
3745
+ isDrawText = false;
3746
+ break;
3747
+ }
3748
+ }
3749
+ }
3750
+
3751
+ if (isDrawText && !cell.isRowHeader && self.cellTree.columns[cell.rowIndex] && self.cellTree.columns[cell.rowIndex][cell.columnIndex].icon) {
3752
+ if (self.viewData.length > 0 && self.viewData[cell.rowIndex][cell.columnIndex].length > 0) treeCellPadding = drawCellTreeIcon(cell, self.cellTree.columns[cell.rowIndex][cell.columnIndex], false);
3753
+ }
3754
+
3755
+ if (isDrawText) drawText(cell, treeCellPadding);
3281
3756
  }
3282
3757
 
3283
3758
  if (wrap && cell.text && cell.text.height > rowHeight) {
@@ -3317,6 +3792,12 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3317
3792
  var previousRowNumber = self.getBoundRowIndexFromViewRowIndex(rowOrderIndex - 1);
3318
3793
  var hasRowGap = previousRowNumber !== undefined && cell.boundRowIndex > 0 && cell.boundRowIndex - previousRowNumber > 1;
3319
3794
 
3795
+ if (hasRowGap && collapsedRowGroups.length > 0) {
3796
+ hasRowGap = collapsedRowGroups.find(function (group) {
3797
+ return group.from === previousRowNumber && group.to === cell.boundRowIndex;
3798
+ }) >= 0;
3799
+ }
3800
+
3320
3801
  if (hasRowGap) {
3321
3802
  var barHeight = self.style.rowHeaderCellRowNumberGapHeight;
3322
3803
  var barColor = self.style.rowHeaderCellRowNumberGapColor;
@@ -3367,7 +3848,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3367
3848
  // added to the end, and we want to render that new row's number
3368
3849
 
3369
3850
  var filteredRowNumber = self.viewData && rowIndex < self.viewData.length ? self.getBoundRowIndexFromViewRowIndex(rowIndex) + 1 : self.originalData ? self.originalData.length + 1 : rowOrderIndex + 1;
3370
- var rowHeaderValue = self.hasActiveFilters() ? filteredRowNumber : rowIndex + 1;
3851
+ var rowHeaderValue = self.hasActiveFilters() || self.hasCollapsedRowGroup() ? filteredRowNumber : rowIndex + 1;
3371
3852
  var _rowHeaderCell = {
3372
3853
  rowHeaderCell: rowHeaderValue
3373
3854
  };
@@ -3400,7 +3881,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3400
3881
  i = self.orders.columns[o];
3401
3882
  header = schema[i];
3402
3883
 
3403
- if (!header.hidden) {
3884
+ if (!header.hidden && !isColumnCollapsedByGroup(o)) {
3404
3885
  d = {
3405
3886
  title: header.title,
3406
3887
  name: header.name,
@@ -3519,8 +4000,10 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3519
4000
  cellHeight = rowHeight; //draw normal columns
3520
4001
 
3521
4002
  for (columnOrderIndex = self.scrollIndexLeft; columnOrderIndex < g; columnOrderIndex += 1) {
3522
- headerIndex = self.orders.columns[columnOrderIndex];
3523
- x += drawCell(rowData, rowOrderIndex, rowIndex)(schema[headerIndex], headerIndex, columnOrderIndex);
4003
+ if (!isColumnCollapsedByGroup(columnOrderIndex)) {
4004
+ headerIndex = self.orders.columns[columnOrderIndex];
4005
+ x += drawCell(rowData, rowOrderIndex, rowIndex)(schema[headerIndex], headerIndex, columnOrderIndex);
4006
+ }
3524
4007
 
3525
4008
  if (x > self.width) {
3526
4009
  self.scrollIndexRight = columnOrderIndex;
@@ -3537,8 +4020,10 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3537
4020
  }
3538
4021
 
3539
4022
  for (columnOrderIndex = 0; columnOrderIndex < self.frozenColumn; columnOrderIndex += 1) {
3540
- headerIndex = self.orders.columns[columnOrderIndex];
3541
- x += drawCell(rowData, rowOrderIndex, rowIndex)(schema[headerIndex], headerIndex, columnOrderIndex);
4023
+ if (!isColumnCollapsedByGroup(columnOrderIndex)) {
4024
+ headerIndex = self.orders.columns[columnOrderIndex];
4025
+ x += drawCell(rowData, rowOrderIndex, rowIndex)(schema[headerIndex], headerIndex, columnOrderIndex);
4026
+ }
3542
4027
 
3543
4028
  if (x > self.width) {
3544
4029
  break;
@@ -3565,8 +4050,19 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3565
4050
  nodeType: 'canvas-datagrid-tree',
3566
4051
  scrollTop: self.scrollBox.scrollTop,
3567
4052
  scrollLeft: self.scrollBox.scrollLeft,
3568
- rowIndex: rowOrderIndex
4053
+ rowIndex: rowOrderIndex,
4054
+ columnGroupsAreaHeight: columnGroupsAreaHeight,
4055
+ rowGroupsAreaWidth: rowGroupsAreaWidth
3569
4056
  };
4057
+
4058
+ if (self.intf.parentNode) {
4059
+ var _self$intf$parentNode = self.intf.parentNode,
4060
+ _columnGroupsAreaHeight = _self$intf$parentNode.columnGroupsAreaHeight,
4061
+ _rowGroupsAreaWidth = _self$intf$parentNode.rowGroupsAreaWidth;
4062
+ treeGrid.parentNode.columnGroupsAreaHeight += _columnGroupsAreaHeight || 0;
4063
+ treeGrid.parentNode.rowGroupsAreaWidth += _rowGroupsAreaWidth || 0;
4064
+ }
4065
+
3570
4066
  self.visibleCells.unshift({
3571
4067
  rowIndex: rowOrderIndex,
3572
4068
  columnIndex: 0,
@@ -3593,6 +4089,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3593
4089
  self.visibleRows = [];
3594
4090
  schema = self.getSchema();
3595
4091
  self.visibleCells = [];
4092
+ self.visibleGroups = [];
3596
4093
  self.canvasOffsetTop = self.isChildGrid ? self.parentNode.offsetTop : 0.5;
3597
4094
  self.canvasOffsetLeft = self.isChildGrid ? self.parentNode.offsetLeft : -0.5;
3598
4095
  h = self.height;
@@ -3606,86 +4103,510 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3606
4103
  fillRect(0, 0, w, h);
3607
4104
  }
3608
4105
 
3609
- function drawFrozenRows() {
3610
- var rowOrderIndex,
3611
- ln = Math.min(viewData.length, self.frozenRow);
3612
- x = -self.scrollBox.scrollLeft + self.scrollPixelLeft + self.style.cellBorderWidth;
3613
- y = columnHeaderCellHeight;
4106
+ function initGroupArea() {
4107
+ self.ctx.translate(rowGroupsAreaWidth, columnGroupsAreaHeight);
4108
+ }
3614
4109
 
3615
- for (rowIndex = 0; rowIndex < ln; rowIndex += 1) {
3616
- rowOrderIndex = self.orders.rows[rowIndex];
4110
+ function drawGroupArea() {
4111
+ var mx = rowGroupsAreaWidth;
4112
+ var my = columnGroupsAreaHeight;
4113
+ var frozenColumnsWidth = getFrozenColumnsWidth();
4114
+ var frozenRowsHeight = rowGroupsFrozenInfo.y + rowGroupsFrozenInfo.h - columnHeaderCellHeight;
4115
+ var onTheLeft = self.attributes.columnGroupIndicatorPosition === 'left';
4116
+ var onTheTop = self.attributes.rowGroupIndicatorPosition === 'top';
4117
+ /** @type {CanvasRenderingContext2D} */
3617
4118
 
3618
- if (!drawRow(rowOrderIndex, rowIndex)) {
3619
- break;
4119
+ var ctx = self.ctx;
4120
+ ctx.save();
4121
+ ctx.fillStyle = self.style.groupingAreaBackgroundColor;
4122
+ fillRect(0, -my, w, my);
4123
+ fillRect(-mx, -my, mx, h);
4124
+ ctx.restore(); //#region Columns Grouping
4125
+
4126
+ /** it extends `self.groupedRows` */
4127
+
4128
+ var groupedColumns = [];
4129
+
4130
+ for (var row = 0; row < self.groupedColumns.length; row++) {
4131
+ var groups = self.groupedColumns[row];
4132
+
4133
+ for (var j = 0; j < groups.length; j++) {
4134
+ groupedColumns.push(Object.assign({
4135
+ row: row
4136
+ }, groups[j]));
3620
4137
  }
3621
4138
  }
3622
4139
 
3623
- if (self.attributes.allowFreezingRows) {
3624
- // HACK great, another stupid magic number.
3625
- // Background will appear as a 0.5px artifact behind the row freeze bar without this hack
3626
- y += self.style.frozenMarkerBorderWidth + self.style.frozenMarkerWidth - 0.4999999999;
3627
- }
4140
+ if (groupedColumns.length > 0) {
4141
+ (function () {
4142
+ var rowHeight = self.style.columnGroupRowHeight;
4143
+ var toggleHandleSize = rowHeight * 0.5;
4144
+ var toggleHandlePadding = (rowHeight - toggleHandleSize) * 0.5;
3628
4145
 
3629
- self.lastFrozenRowPixel = y;
3630
- }
4146
+ var _loop = function _loop(i) {
4147
+ var group = groupedColumns[i];
4148
+ var row = group.row,
4149
+ collapsed = group.collapsed;
4150
+ var topY = -my + row * rowHeight;
4151
+ var centerY = topY + rowHeight * 0.5;
4152
+ var bottomY = topY + rowHeight - toggleHandlePadding;
4153
+ var leftmostX = rowHeaderCellWidth - toggleHandleSize - toggleHandlePadding;
3631
4154
 
3632
- function drawRows() {
3633
- self.ctx.save();
4155
+ var drawGroupHandleAtX = function drawGroupHandleAtX(x) {
4156
+ return drawGroupHandle(x, topY + toggleHandlePadding, toggleHandleSize, group.collapsed);
4157
+ };
3634
4158
 
3635
- if (self.frozenRow > 0) {
3636
- radiusRect(0, self.lastFrozenRowPixel, self.width, self.height - self.lastFrozenRowPixel, 0);
3637
- self.ctx.clip();
3638
- }
4159
+ var pushToVisibleGroups = function pushToVisibleGroups(leftX, rightX) {
4160
+ return self.visibleGroups.push({
4161
+ type: 'c',
4162
+ collapsed: collapsed,
4163
+ from: group.from,
4164
+ to: group.to,
4165
+ row: row,
4166
+ x: leftX + mx,
4167
+ y: topY + my,
4168
+ x2: rightX + mx,
4169
+ y2: bottomY + my
4170
+ });
4171
+ }; //#region check the relationship between this group and frozen columns
3639
4172
 
3640
- var columnOrderIndex,
3641
- rowOrderIndex,
3642
- headerIndex,
3643
- g = schema.length;
3644
- x = -self.scrollBox.scrollLeft + self.scrollPixelLeft + self.style.cellBorderWidth;
3645
4173
 
3646
- if (!self.attributes.snapToRow) {
3647
- y += -self.scrollBox.scrollTop + self.scrollPixelTop + self.style.cellBorderWidth;
3648
- }
4174
+ var crossTheFrozen = group.from < self.frozenColumn && group.to >= self.frozenColumn;
4175
+ var notInFrozen = group.from >= self.frozenColumn; //#endregion
3649
4176
 
3650
- for (rowIndex = self.frozenRow + self.scrollIndexTop; rowIndex < l; rowIndex += 1) {
3651
- rowOrderIndex = self.orders.rows[rowIndex];
3652
- self.scrollIndexBottom = rowIndex;
3653
- self.scrollPixelBottom = y;
4177
+ if (collapsed) {
4178
+ var _leftX = leftmostX + toggleHandleSize; // This group is not sticking on the first column
3654
4179
 
3655
- if (!drawRow(rowOrderIndex, rowIndex)) {
3656
- break;
3657
- }
3658
- }
3659
4180
 
3660
- if (self.attributes.showNewRow) {
3661
- if (self.attributes.showRowHeaders) {
3662
- x += rowHeaderCellWidth;
3663
- }
4181
+ if (group.from > 0) {
4182
+ var colIndex = group.to + 1;
4183
+ var col = columnGroupsRectInfo[colIndex];
3664
4184
 
3665
- rowHeight = cellHeight = self.style.cellHeight;
3666
- rowOpen = false;
4185
+ if (!col) {
4186
+ colIndex = group.from - 1;
4187
+ col = columnGroupsRectInfo[colIndex];
4188
+ if (!col) return "continue"; // don't draw this group indicator because it is invisible
3667
4189
 
3668
- for (columnOrderIndex = self.scrollIndexLeft; columnOrderIndex < g; columnOrderIndex += 1) {
3669
- headerIndex = self.orders.columns[columnOrderIndex];
3670
- x += drawCell(self.newRow, viewData.length, viewData.length)(schema[headerIndex], headerIndex, columnOrderIndex);
4190
+ _leftX = col.x + col.w - toggleHandleSize * 0.5;
4191
+ } else {
4192
+ _leftX = col.x + toggleHandlePadding;
4193
+ }
3671
4194
 
3672
- if (x > self.width + self.scrollBox.scrollLeft) {
3673
- break;
3674
- }
3675
- }
4195
+ if (colIndex >= self.frozenColumn) {
4196
+ var compare = frozenColumnsWidth + rowHeaderCellWidth - toggleHandlePadding; // don't draw this group indicator because it is hidden by frozen columns
3676
4197
 
3677
- rowHeaders.push([self.newRow, viewData.length, viewData.length, y, rowHeight]);
3678
- }
4198
+ if (_leftX < compare) return "continue";
4199
+ }
4200
+ }
3679
4201
 
3680
- self.ctx.restore();
3681
- }
4202
+ var _rightX = _leftX + toggleHandleSize;
3682
4203
 
3683
- function drawMoveMarkers() {
3684
- if (!self.movingSelection) {
3685
- return;
3686
- }
4204
+ ctx.save();
4205
+ ctx.strokeStyle = self.style.groupIndicatorColor;
4206
+ ctx.fillStyle = self.style.groupIndicatorBackgroundColor;
4207
+ drawGroupHandleAtX(_leftX);
4208
+ ctx.restore();
4209
+ pushToVisibleGroups(_leftX, _rightX);
4210
+ } // end of collapsed group
3687
4211
 
3688
- self.ctx.lineWidth = self.style.moveOverlayBorderWidth;
4212
+ /** @type {number} pointer for loop */
4213
+
4214
+
4215
+ var ptr = void 0;
4216
+ var left = columnGroupsRectInfo[group.from];
4217
+ var right = columnGroupsRectInfo[group.to];
4218
+ var containsBegining = true;
4219
+ var containsEnd = true;
4220
+ ptr = group.from;
4221
+
4222
+ while (!left && ptr < group.to) {
4223
+ left = columnGroupsRectInfo[++ptr];
4224
+ containsBegining = false;
4225
+ }
4226
+
4227
+ ptr = group.to;
4228
+
4229
+ while (!right && ptr > group.from) {
4230
+ right = columnGroupsRectInfo[--ptr];
4231
+ containsEnd = false;
4232
+ }
4233
+
4234
+ if (!left || !right) return "continue";
4235
+ var rightX = right.x + right.w;
4236
+ var leftX = left.x;
4237
+
4238
+ if (crossTheFrozen) {
4239
+ var rightCompare = columnGroupsRectInfo[self.frozenColumn - 1];
4240
+
4241
+ if (rightCompare) {
4242
+ var compareX = rightCompare.x + rightCompare.w;
4243
+ if (!onTheLeft) compareX += toggleHandleSize;
4244
+
4245
+ if (compareX >= rightX) {
4246
+ right = rightCompare;
4247
+ rightX = right.x + right.w;
4248
+ containsEnd = false;
4249
+ }
4250
+ }
4251
+ }
4252
+
4253
+ var minLeftX = rowHeaderCellWidth + (notInFrozen ? frozenColumnsWidth : 0);
4254
+ if (rightX + (onTheLeft ? 0 : toggleHandleSize) < minLeftX) return "continue";
4255
+ rightX -= toggleHandlePadding;
4256
+ leftX += toggleHandlePadding;
4257
+ ctx.save();
4258
+ ctx.strokeStyle = self.style.groupIndicatorColor;
4259
+ ctx.fillStyle = self.style.groupIndicatorBackgroundColor;
4260
+ var lineCoords = [];
4261
+
4262
+ if (onTheLeft) {
4263
+ // avoid lines from two groups be overlapping
4264
+ minLeftX += toggleHandlePadding * 2;
4265
+ if (leftX < minLeftX) leftX = minLeftX;
4266
+ if (group.from === 0) leftX -= toggleHandlePadding * 2;
4267
+
4268
+ if (rightX >= leftX) {
4269
+ lineCoords.push(leftX, centerY, rightX, centerY);
4270
+ if (containsEnd) lineCoords.push(rightX, bottomY);
4271
+ } else {
4272
+ rightX = leftX;
4273
+ }
4274
+
4275
+ leftX -= toggleHandleSize;
4276
+ drawGroupHandleAtX(leftX); // add more clickable area into `visibleGroups`
4277
+
4278
+ rightX += toggleHandlePadding - 1;
4279
+ } else {
4280
+ // handle on the right
4281
+ if (leftX < minLeftX) leftX = minLeftX;
4282
+ if (group.from === 0) leftX -= toggleHandlePadding * 2;
4283
+
4284
+ if (containsEnd) {
4285
+ if (group.to === self.frozenColumn - 1) {
4286
+ rightX -= toggleHandleSize;
4287
+ } else {
4288
+ rightX += toggleHandlePadding * 2;
4289
+ }
4290
+
4291
+ drawGroupHandleAtX(rightX);
4292
+ }
4293
+
4294
+ if (leftX > rightX) {
4295
+ leftX = rightX;
4296
+ } else {
4297
+ if (group.from === 0) {
4298
+ containsBegining = true;
4299
+ leftX = leftmostX + toggleHandleSize;
4300
+ }
4301
+
4302
+ if (containsBegining) lineCoords.push(leftX, bottomY);
4303
+ lineCoords.push(leftX, centerY, rightX, centerY);
4304
+ } // add more clickable area into `visibleGroups`
4305
+
4306
+
4307
+ leftX -= toggleHandlePadding + 1;
4308
+ if (containsEnd) rightX += toggleHandleSize;
4309
+ }
4310
+
4311
+ strokeLines(lineCoords);
4312
+ ctx.restore();
4313
+ pushToVisibleGroups(leftX, rightX);
4314
+ };
4315
+
4316
+ for (var i = 0; i < groupedColumns.length; i++) {
4317
+ var _ret = _loop(i);
4318
+
4319
+ if (_ret === "continue") continue;
4320
+ }
4321
+ })();
4322
+ } //#endregion Columns Grouping
4323
+ //#region Rows Grouping
4324
+
4325
+ /** it extends `self.groupedRows` */
4326
+
4327
+
4328
+ var groupedRows = [];
4329
+
4330
+ for (var col = 0; col < self.groupedRows.length; col++) {
4331
+ var _groups = self.groupedRows[col];
4332
+
4333
+ for (var _j = 0; _j < _groups.length; _j++) {
4334
+ groupedRows.push(Object.assign({
4335
+ col: col
4336
+ }, _groups[_j]));
4337
+ }
4338
+ }
4339
+
4340
+ if (groupedRows.length > 0) {
4341
+ (function () {
4342
+ var colWidth = self.style.rowGroupColumnWidth;
4343
+ var toggleHandleSize = colWidth * 0.5;
4344
+ var toggleHandlePadding = (colWidth - toggleHandleSize) * 0.5;
4345
+
4346
+ var _loop2 = function _loop2(i) {
4347
+ var group = groupedRows[i];
4348
+ var col = group.col,
4349
+ collapsed = group.collapsed;
4350
+ var leftX = -mx + col * colWidth;
4351
+ var centerX = leftX + colWidth * 0.5;
4352
+ var rightX = leftX + colWidth - toggleHandlePadding;
4353
+ var topmostY = columnHeaderCellHeight - toggleHandleSize - toggleHandlePadding;
4354
+
4355
+ var drawGroupHandleAtY = function drawGroupHandleAtY(y) {
4356
+ return drawGroupHandle(leftX + toggleHandlePadding, y, toggleHandleSize, group.collapsed);
4357
+ };
4358
+
4359
+ var pushToVisibleGroups = function pushToVisibleGroups(topY, bottomY) {
4360
+ return self.visibleGroups.push({
4361
+ type: 'r',
4362
+ collapsed: collapsed,
4363
+ from: group.from,
4364
+ to: group.to,
4365
+ col: col,
4366
+ x: leftX + mx,
4367
+ y: topY + my,
4368
+ x2: rightX + mx,
4369
+ y2: bottomY + my
4370
+ });
4371
+ }; //#region check the relationship between this group and frozen columns
4372
+
4373
+
4374
+ var crossTheFrozen = group.from < self.frozenRow && group.to >= self.frozenRow;
4375
+ var notInFrozen = group.from >= self.frozenRow; //#endregion
4376
+
4377
+ if (collapsed) {
4378
+ var _topY = topmostY + toggleHandleSize; // This group is not sticking on the first column
4379
+
4380
+
4381
+ if (group.from > 0) {
4382
+ var _rowIndex = group.to + 1;
4383
+
4384
+ var _row = rowGroupsRectInfo[_rowIndex];
4385
+
4386
+ if (!_row) {
4387
+ _rowIndex = group.from - 1;
4388
+ _row = rowGroupsRectInfo[_rowIndex];
4389
+ if (!_row) return "continue"; // don't draw this group indicator because it is invisible
4390
+
4391
+ _topY = _row.y + _row.h - toggleHandleSize * 0.5;
4392
+ } else {
4393
+ _topY = _row.y;
4394
+ }
4395
+
4396
+ if (_rowIndex >= self.frozenRow) {
4397
+ var compare = frozenRowsHeight + columnHeaderCellHeight - toggleHandlePadding; // don't draw this group indicator because it is hidden by frozen columns
4398
+
4399
+ if (_topY < compare) return "continue";
4400
+ }
4401
+ }
4402
+
4403
+ var _bottomY = _topY + toggleHandleSize;
4404
+
4405
+ ctx.save();
4406
+ ctx.strokeStyle = self.style.groupIndicatorColor;
4407
+ ctx.fillStyle = self.style.groupIndicatorBackgroundColor;
4408
+ drawGroupHandleAtY(_topY);
4409
+ ctx.restore();
4410
+ pushToVisibleGroups(_topY, _bottomY);
4411
+ } // end of collapsed group
4412
+
4413
+ /** @type {number} pointer for loop */
4414
+
4415
+
4416
+ var ptr = void 0;
4417
+ var top = rowGroupsRectInfo[group.from];
4418
+ var bottom = rowGroupsRectInfo[group.to];
4419
+ var containsBegining = true;
4420
+ var containsEnd = true;
4421
+ ptr = group.from;
4422
+
4423
+ while (!top && ptr < group.to) {
4424
+ top = rowGroupsRectInfo[++ptr];
4425
+ containsBegining = false;
4426
+ }
4427
+
4428
+ ptr = group.to;
4429
+
4430
+ while (!bottom && ptr > group.from) {
4431
+ bottom = rowGroupsRectInfo[--ptr];
4432
+ containsEnd = false;
4433
+ }
4434
+
4435
+ if (!top || !bottom) return "continue";
4436
+ var bottomY = bottom.y + bottom.h;
4437
+ var topY = top.y;
4438
+
4439
+ if (crossTheFrozen) {
4440
+ var bottomCompare = rowGroupsRectInfo[self.frozenRow - 1];
4441
+
4442
+ if (bottomCompare) {
4443
+ var compareY = bottomCompare.y + bottomCompare.h;
4444
+ if (!onTheTop) compareY += toggleHandleSize;
4445
+
4446
+ if (compareY >= bottomY) {
4447
+ bottom = bottomCompare;
4448
+ bottomY = bottom.y + bottom.h;
4449
+ containsEnd = false;
4450
+ }
4451
+ }
4452
+ }
4453
+
4454
+ var minTopY = columnHeaderCellHeight + (notInFrozen ? frozenRowsHeight : 0);
4455
+ if (bottomY + (onTheTop ? 0 : toggleHandleSize) < minTopY) return "continue";
4456
+ bottomY -= toggleHandlePadding;
4457
+ topY += toggleHandlePadding;
4458
+ ctx.save();
4459
+ ctx.strokeStyle = self.style.groupIndicatorColor;
4460
+ ctx.fillStyle = self.style.groupIndicatorBackgroundColor;
4461
+ var lineCoords = [];
4462
+
4463
+ if (onTheTop) {
4464
+ // avoid lines from two groups be overlapping
4465
+ minTopY += toggleHandlePadding * 2;
4466
+ if (topY < minTopY) topY = minTopY;
4467
+ if (group.from === 0) topY -= toggleHandlePadding * 2;
4468
+
4469
+ if (bottomY >= topY) {
4470
+ lineCoords.push(centerX, topY, centerX, bottomY);
4471
+ if (containsEnd) lineCoords.push(rightX, bottomY);
4472
+ } else {
4473
+ bottomY = topY;
4474
+ }
4475
+
4476
+ topY -= toggleHandleSize;
4477
+ drawGroupHandleAtY(topY); // add more clickable area into `visibleGroups`
4478
+
4479
+ bottomY += toggleHandlePadding - 1;
4480
+ } else {
4481
+ // handle on the bottom
4482
+ if (topY < minTopY) topY = minTopY;
4483
+ if (group.from === 0) topY -= toggleHandlePadding * 2;
4484
+
4485
+ if (containsEnd) {
4486
+ if (group.to === self.frozenRow - 1) {
4487
+ bottomY -= toggleHandleSize;
4488
+ } else {// bottomY += toggleHandlePadding * 2;
4489
+ }
4490
+
4491
+ drawGroupHandleAtY(bottomY);
4492
+ }
4493
+
4494
+ if (topY > bottomY) {
4495
+ topY = bottomY;
4496
+ } else {
4497
+ if (group.from === 0) {
4498
+ containsBegining = true;
4499
+ topY = topmostY + toggleHandleSize;
4500
+ }
4501
+
4502
+ if (containsBegining) lineCoords.push(rightX, topY);
4503
+ lineCoords.push(centerX, topY, centerX, bottomY); // add more clickable area into `visibleGroups`
4504
+
4505
+ topY -= toggleHandlePadding + 1;
4506
+ } // add more clickable area into `visibleGroups`
4507
+
4508
+
4509
+ if (containsEnd) bottomY += toggleHandleSize;
4510
+ }
4511
+
4512
+ strokeLines(lineCoords);
4513
+ ctx.restore();
4514
+ pushToVisibleGroups(topY, bottomY);
4515
+ };
4516
+
4517
+ for (var i = 0; i < groupedRows.length; i++) {
4518
+ var _ret2 = _loop2(i);
4519
+
4520
+ if (_ret2 === "continue") continue;
4521
+ }
4522
+ })();
4523
+ } //#endregion Rows Grouping
4524
+
4525
+ }
4526
+
4527
+ function drawFrozenRows() {
4528
+ var rowOrderIndex,
4529
+ ln = Math.min(viewData.length, self.frozenRow);
4530
+ x = -self.scrollBox.scrollLeft + self.scrollPixelLeft + self.style.cellBorderWidth;
4531
+ y = columnHeaderCellHeight;
4532
+
4533
+ for (rowIndex = 0; rowIndex < ln; rowIndex += 1) {
4534
+ rowOrderIndex = self.orders.rows[rowIndex];
4535
+
4536
+ if (!drawRow(rowOrderIndex, rowIndex)) {
4537
+ break;
4538
+ }
4539
+ }
4540
+
4541
+ if (self.attributes.allowFreezingRows) {
4542
+ // HACK great, another stupid magic number.
4543
+ // Background will appear as a 0.5px artifact behind the row freeze bar without this hack
4544
+ y += self.style.frozenMarkerBorderWidth + self.style.frozenMarkerWidth - 0.4999999999;
4545
+ }
4546
+
4547
+ self.lastFrozenRowPixel = y;
4548
+ }
4549
+
4550
+ function drawRows() {
4551
+ self.ctx.save();
4552
+
4553
+ if (self.frozenRow > 0) {
4554
+ radiusRect(0, self.lastFrozenRowPixel, self.width, self.height - self.lastFrozenRowPixel, 0);
4555
+ self.ctx.clip();
4556
+ }
4557
+
4558
+ var columnOrderIndex,
4559
+ rowOrderIndex,
4560
+ headerIndex,
4561
+ g = schema.length;
4562
+ x = -self.scrollBox.scrollLeft + self.scrollPixelLeft + self.style.cellBorderWidth;
4563
+
4564
+ if (!self.attributes.snapToRow) {
4565
+ y += -self.scrollBox.scrollTop + self.scrollPixelTop + self.style.cellBorderWidth;
4566
+ }
4567
+
4568
+ for (rowIndex = self.frozenRow + self.scrollIndexTop; rowIndex < l; rowIndex += 1) {
4569
+ rowOrderIndex = self.orders.rows[rowIndex];
4570
+ self.scrollIndexBottom = rowIndex;
4571
+ self.scrollPixelBottom = y;
4572
+ if (self.cellTree.rows.length > 0 && Object.keys(self.cellTree.rows[rowOrderIndex]).length > 0 && self.cellTree.rows[rowOrderIndex].hide) continue;
4573
+
4574
+ if (!drawRow(rowOrderIndex, rowIndex)) {
4575
+ break;
4576
+ }
4577
+ }
4578
+
4579
+ if (self.attributes.showNewRow) {
4580
+ if (self.attributes.showRowHeaders) {
4581
+ x += rowHeaderCellWidth;
4582
+ }
4583
+
4584
+ rowHeight = cellHeight = self.style.cellHeight;
4585
+ rowOpen = false;
4586
+
4587
+ for (columnOrderIndex = self.scrollIndexLeft; columnOrderIndex < g; columnOrderIndex += 1) {
4588
+ if (!isColumnCollapsedByGroup(columnOrderIndex)) {
4589
+ headerIndex = self.orders.columns[columnOrderIndex];
4590
+ x += drawCell(self.newRow, viewData.length, viewData.length)(schema[headerIndex], headerIndex, columnOrderIndex);
4591
+ }
4592
+
4593
+ if (x > self.width + self.scrollBox.scrollLeft) {
4594
+ break;
4595
+ }
4596
+ }
4597
+
4598
+ rowHeaders.push([self.newRow, viewData.length, viewData.length, y, rowHeight]);
4599
+ }
4600
+
4601
+ self.ctx.restore();
4602
+ }
4603
+
4604
+ function drawMoveMarkers() {
4605
+ if (!self.movingSelection) {
4606
+ return;
4607
+ }
4608
+
4609
+ self.ctx.lineWidth = self.style.moveOverlayBorderWidth;
3689
4610
  self.ctx.strokeStyle = self.style.moveOverlayBorderColor;
3690
4611
  self.ctx.setLineDash(self.style.moveOverlayBorderSegments);
3691
4612
  moveBorders.forEach(function (c) {
@@ -3871,13 +4792,18 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
3871
4792
  self.ctx.strokeStyle = xHover ? self.style.frozenMarkerHoverBorderColor : self.style.frozenMarkerBorderColor;
3872
4793
  fillRect(0, my, self.width, self.style.frozenMarkerWidth);
3873
4794
  strokeRect(0, my, self.width, self.style.frozenMarkerWidth);
4795
+ var height = self.style.frozenMarkerWidth + self.style.frozenMarkerBorderWidth;
3874
4796
  self.visibleCells.unshift({
3875
4797
  x: 0,
3876
4798
  y: my,
3877
- height: self.style.frozenMarkerWidth + self.style.frozenMarkerBorderWidth,
4799
+ height: height,
3878
4800
  width: self.width,
3879
4801
  style: 'frozen-row-marker'
3880
4802
  });
4803
+ rowGroupsFrozenInfo = {
4804
+ y: my,
4805
+ h: height
4806
+ };
3881
4807
  }
3882
4808
 
3883
4809
  if (self.freezeMarkerPosition) {
@@ -4039,6 +4965,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4039
4965
  self.ctx.save();
4040
4966
  initDraw();
4041
4967
  drawBackground();
4968
+ initGroupArea();
4042
4969
  drawFrozenRows();
4043
4970
  drawRows();
4044
4971
  drawActiveCell();
@@ -4055,6 +4982,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4055
4982
  self.resize(true);
4056
4983
  }
4057
4984
 
4985
+ drawGroupArea();
4058
4986
  drawDebug();
4059
4987
  drawPerfLines();
4060
4988
 
@@ -4228,6 +5156,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4228
5156
  l = (self.viewData || []).length,
4229
5157
  columnHeaderCellHeight = self.getColumnHeaderCellHeight(),
4230
5158
  rowHeaderCellWidth = self.getRowHeaderCellWidth(),
5159
+ topGroupAreaHeight = self.getColumnGroupAreaHeight(),
5160
+ leftGroupAreaWidth = self.getRowGroupAreaWidth(),
4231
5161
  ch = self.style.cellHeight,
4232
5162
  s = self.getSchema(); // sets actual DOM canvas element
4233
5163
 
@@ -4239,8 +5169,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4239
5169
  }
4240
5170
 
4241
5171
  function setScrollBoxSize() {
4242
- self.scrollBox.width = self.width - rowHeaderCellWidth;
4243
- self.scrollBox.height = self.height - columnHeaderCellHeight;
5172
+ self.scrollBox.width = self.width - rowHeaderCellWidth - leftGroupAreaWidth;
5173
+ self.scrollBox.height = self.height - columnHeaderCellHeight - topGroupAreaHeight;
4244
5174
  }
4245
5175
 
4246
5176
  function setCanvasSize() {
@@ -4250,8 +5180,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4250
5180
 
4251
5181
  dims = {
4252
5182
  // HACK +1 ? maybe it's a magic cell border? Required to line up properly in auto height mode.
4253
- height: columnHeaderCellHeight + dataHeight + cellBorder + 1,
4254
- width: dataWidth + rowHeaderCellWidth + cellBorder
5183
+ height: columnHeaderCellHeight + topGroupAreaHeight + dataHeight + cellBorder + 1,
5184
+ width: dataWidth + rowHeaderCellWidth + cellBorder + leftGroupAreaWidth
4255
5185
  };
4256
5186
  ['width', 'height'].forEach(function (dim) {
4257
5187
  //TODO: support inherit
@@ -4280,18 +5210,32 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4280
5210
  self.scrollCache.y[x] = dataHeight;
4281
5211
  }
4282
5212
 
5213
+ var collapsedColumnGroups = self.getCollapsedColumnGroups();
5214
+
5215
+ var isColumnCollapsed = function isColumnCollapsed(columnIndex) {
5216
+ return collapsedColumnGroups.findIndex(function (group) {
5217
+ return columnIndex >= group.from && columnIndex <= group.to;
5218
+ }) >= 0;
5219
+ };
5220
+ /** @type {number} it will be used in `reduceSchema` only */
5221
+
5222
+
5223
+ var frozenWidth = 0;
4283
5224
  dataWidth = s.reduce(function reduceSchema(accumulator, column, columnIndex) {
4284
5225
  // intentional redefintion of column. This causes scrollCache to be in the correct order
4285
- column = s[self.orders.columns[columnIndex]];
5226
+ var schemaIndex = self.orders.columns[columnIndex];
5227
+ var columnWidth = self.getColumnWidth(schemaIndex);
5228
+ column = s[schemaIndex];
5229
+ if (!column.hidden && !isColumnCollapsed(columnIndex)) accumulator += columnWidth;
4286
5230
 
4287
- if (column.hidden) {
5231
+ if (columnIndex < self.frozenColumn) {
4288
5232
  self.scrollCache.x[columnIndex] = accumulator;
4289
- return accumulator;
5233
+ frozenWidth = accumulator;
5234
+ } else {
5235
+ self.scrollCache.x[columnIndex] = Math.max(frozenWidth + columnWidth, accumulator);
4290
5236
  }
4291
5237
 
4292
- var va = accumulator + self.getColumnWidth(self.orders.columns[columnIndex]);
4293
- self.scrollCache.x[columnIndex] = va;
4294
- return va;
5238
+ return accumulator;
4295
5239
  }, 0) || 0;
4296
5240
 
4297
5241
  if (self.attributes.showNewRow) {
@@ -4316,8 +5260,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4316
5260
  // non-controversial
4317
5261
 
4318
5262
 
4319
- self.scrollBox.top = columnHeaderCellHeight + columnHeaderCellBorder;
4320
- self.scrollBox.left = rowHeaderCellWidth; // width and height of scroll box
5263
+ self.scrollBox.top = columnHeaderCellHeight + topGroupAreaHeight + columnHeaderCellBorder;
5264
+ self.scrollBox.left = rowHeaderCellWidth + leftGroupAreaWidth; // width and height of scroll box
4321
5265
 
4322
5266
  setScrollBoxSize(); // is the data larger than the scroll box
4323
5267
 
@@ -4363,24 +5307,24 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4363
5307
  // the dragged mouse.
4364
5308
  // https://github.com/TonyGermaneri/canvas-datagrid/issues/97
4365
5309
 
4366
- self.scrollBox.heightBoxRatio = (self.scrollBox.height - columnHeaderCellHeight - self.scrollCache.y[self.frozenRow]) / dataHeight;
5310
+ self.scrollBox.heightBoxRatio = (self.scrollBox.height - columnHeaderCellHeight - topGroupAreaHeight - self.scrollCache.y[self.frozenRow]) / dataHeight;
4367
5311
  self.scrollBox.scrollBoxHeight = self.scrollBox.height * self.scrollBox.heightBoxRatio - self.style.scrollBarWidth - b - d;
4368
5312
  self.scrollBox.scrollBoxWidth = Math.max(self.scrollBox.scrollBoxWidth, self.style.scrollBarBoxMinSize);
4369
5313
  self.scrollBox.scrollBoxHeight = Math.max(self.scrollBox.scrollBoxHeight, self.style.scrollBarBoxMinSize); // horizontal
4370
5314
 
4371
5315
  n.x += rowHeaderCellWidth;
4372
- n.y += self.height - self.style.scrollBarWidth - d;
4373
- n.width = self.width - self.style.scrollBarWidth - rowHeaderCellWidth - d - m;
5316
+ n.y += self.height - self.style.scrollBarWidth - d - topGroupAreaHeight;
5317
+ n.width = self.width - self.style.scrollBarWidth - rowHeaderCellWidth - leftGroupAreaWidth - d - m;
4374
5318
  n.height = self.style.scrollBarWidth + self.style.scrollBarBorderWidth + d; // horizontal box
4375
5319
 
4376
5320
  nb.y = n.y + self.style.scrollBarBoxMargin;
4377
5321
  nb.width = self.scrollBox.scrollBoxWidth;
4378
5322
  nb.height = self.style.scrollBarBoxWidth; // vertical
4379
5323
 
4380
- v.x += self.width - self.style.scrollBarWidth - self.style.scrollBarBorderWidth - d;
5324
+ v.x += self.width - leftGroupAreaWidth - self.style.scrollBarWidth - self.style.scrollBarBorderWidth - d;
4381
5325
  v.y += columnHeaderCellHeight + self.scrollCache.y[self.frozenRow];
4382
5326
  v.width = self.style.scrollBarWidth + self.style.scrollBarBorderWidth + d;
4383
- v.height = self.height - columnHeaderCellHeight - self.style.scrollBarWidth - d - m; // vertical box
5327
+ v.height = self.height - columnHeaderCellHeight - topGroupAreaHeight - self.style.scrollBarWidth - d - m; // vertical box
4384
5328
 
4385
5329
  vb.x = v.x + self.style.scrollBarBoxMargin;
4386
5330
  vb.y += self.scrollCache.y[self.frozenRow];
@@ -4542,13 +5486,26 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4542
5486
  self.hovers = {
4543
5487
  rowIndex: cell.rowIndex,
4544
5488
  columnIndex: cell.columnIndex,
4545
- onFilterButton: false
5489
+ onFilterButton: false,
5490
+ onCellTreeIcon: false
4546
5491
  };
4547
5492
 
4548
5493
  if (cell.isFilterable && x > cell.x + cell.width + self.canvasOffsetLeft - self.style.filterButtonWidth && x < cell.x + cell.width + self.canvasOffsetLeft && y > cell.y + cell.height + self.canvasOffsetTop - self.style.filterButtonHeight && y < cell.y + cell.height + self.canvasOffsetTop) {
4549
5494
  self.hovers.onFilterButton = true;
4550
5495
  self.draw();
4551
5496
  }
5497
+
5498
+ if (cell.isRowTree || cell.isColumnTree) {
5499
+ var pc = cell.isRowTree ? self.cellTree.rows[cell.rowIndex].parentCount : 0;
5500
+ var rc = self.style.cellTreeIconWidth * self.scale,
5501
+ rx = cell.x + cell.paddingLeft + self.canvasOffsetLeft + self.style.cellTreeIconMarginLeft + pc * (rc + cell.paddingLeft),
5502
+ ry = cell.y + self.canvasOffsetTop + self.style.cellTreeIconMarginTop * self.scale;
5503
+
5504
+ if (x >= rx && x <= rx + rc && y >= ry && y < ry + rc) {
5505
+ self.hovers.onCellTreeIcon = true;
5506
+ self.draw();
5507
+ }
5508
+ }
4552
5509
  }
4553
5510
 
4554
5511
  if (self.selecting || self.reorderObject) {
@@ -4609,12 +5566,16 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4609
5566
 
4610
5567
  self.draw();
4611
5568
  return;
5569
+ } else if (cell.hovered && self.hovers.onCellTreeIcon && e.type == 'mousedown') {
5570
+ self.toggleCollapseTree(cell.rowIndex, cell.columnIndex);
5571
+ return;
4612
5572
  } else {
4613
5573
  self.selectedFilterButton = {
4614
5574
  columnIndex: -1,
4615
5575
  rowIndex: -1
4616
5576
  };
4617
5577
  if (self.hovers.onFilterButton) return;
5578
+ if (self.hovers.onCellTreeIcon) return;
4618
5579
 
4619
5580
  if (!self.dragAddToSelection && cell.rowIndex !== undefined) {
4620
5581
  if (self.selections[cell.rowIndex] && self.selections[cell.rowIndex].indexOf(cell.columnIndex) !== -1) {
@@ -4669,6 +5630,10 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4669
5630
  }
4670
5631
  }
4671
5632
 
5633
+ var columnGroup = self.getColumnGroupAt(self.mouse.x, self.mouse.y);
5634
+ if (columnGroup) self.cursor = 'pointer';
5635
+ var rowGroup = self.getRowGroupAt(self.mouse.x, self.mouse.y);
5636
+ if (rowGroup) self.cursor = 'pointer';
4672
5637
  self.cellBoundaryCrossed = false;
4673
5638
  self.rowBoundaryCrossed = false;
4674
5639
  self.columnBoundaryCrossed = false;
@@ -4725,10 +5690,26 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4725
5690
  return;
4726
5691
  }
4727
5692
 
5693
+ var group = self.getColumnGroupAt(pos.x, pos.y);
5694
+ if (!group) group = self.getRowGroupAt(pos.x, pos.y);
5695
+
5696
+ if (group) {
5697
+ if (self.toggleGroup(group)) {
5698
+ self.setStorageData();
5699
+ self.refresh();
5700
+ return;
5701
+ }
5702
+ }
5703
+
4728
5704
  if (!self.hasFocus) {
4729
5705
  return;
4730
5706
  }
4731
5707
 
5708
+ var leftOffset = self.getRowGroupAreaWidth();
5709
+ var topOffset = self.getColumnGroupAreaHeight();
5710
+ var xInGrid = pos.x - leftOffset;
5711
+ var yInGrid = pos.y - topOffset;
5712
+
4732
5713
  if (['rowHeaderCell', 'columnHeaderCell'].indexOf(self.currentCell.style) === -1 && !ctrl) {
4733
5714
  if (!self.hovers.onFilterButton) {
4734
5715
  self.setActiveCell(i.columnIndex, i.rowIndex);
@@ -4760,7 +5741,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4760
5741
  self.selections[i.rowIndex] = self.selections[i.rowIndex] || [];
4761
5742
 
4762
5743
  if (self.attributes.selectionMode === 'row' || self.currentCell.style === 'rowHeaderCell') {
4763
- if (self.currentCell.style === 'rowHeaderCell' && self.attributes.tree && pos.x > 0 && pos.x - self.currentCell.x < self.style.treeArrowWidth + self.style.treeArrowMarginLeft + self.style.treeArrowMarginRight + self.style.treeArrowClickRadius && pos.y - self.currentCell.y < self.style.treeArrowHeight + self.style.treeArrowMarginTop + self.style.treeArrowClickRadius && pos.y > 0) {
5744
+ if (self.currentCell.style === 'rowHeaderCell' && self.attributes.tree && xInGrid > 0 && xInGrid - self.currentCell.x < self.style.treeArrowWidth + self.style.treeArrowMarginLeft + self.style.treeArrowMarginRight + self.style.treeArrowClickRadius && yInGrid - self.currentCell.y < self.style.treeArrowHeight + self.style.treeArrowMarginTop + self.style.treeArrowClickRadius && yInGrid > 0) {
4764
5745
  self.toggleTree(i.rowIndex);
4765
5746
  return;
4766
5747
  }
@@ -4800,7 +5781,6 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
4800
5781
 
4801
5782
  if (self.scrollBox.scrollLeft > self.scrollBox.scrollWidth - self.attributes.resizeScrollZone && self.dragMode === 'ew-resize') {
4802
5783
  self.resize(true);
4803
- self.scrollBox.scrollLeft += x;
4804
5784
  }
4805
5785
 
4806
5786
  if (self.dragMode === 'ew-resize') {
@@ -5113,6 +6093,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
5113
6093
  rowHeaderCellWidth = self.getRowHeaderCellWidth();
5114
6094
  self.ignoreNextClick = true;
5115
6095
  self.freezeMarkerPosition = pos;
6096
+ pos.x -= self.getRowGroupAreaWidth();
6097
+ pos.y -= self.getColumnGroupAreaHeight();
5116
6098
 
5117
6099
  if (self.currentCell && self.currentCell.rowIndex !== undefined && self.dragMode === 'frozen-row-marker') {
5118
6100
  self.scrollBox.scrollTop = 0;
@@ -5611,8 +6593,13 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
5611
6593
  }
5612
6594
  } else if (self.currentCell.context === 'ew-resize' && self.currentCell.style === 'cornerCell') {
5613
6595
  self.autosize();
5614
- } else if (['cell', 'activeCell'].includes(self.currentCell.style) && !self.hovers.onFilterButton) {
5615
- self.beginEditAt(self.currentCell.columnIndex, self.currentCell.rowIndex);
6596
+ } else if (['cell', 'activeCell'].includes(self.currentCell.style) && !self.hovers.onFilterButton && !self.hovers.onCellTreeIcon) {
6597
+ if (self.currentCell.isRowTree || self.currentCell.isColumnTree) {
6598
+ self.cellTreeExpandCollapse(self.currentCell.rowIndex, self.currentCell.columnIndex);
6599
+ self.draw();
6600
+ } else {
6601
+ self.beginEditAt(self.currentCell.columnIndex, self.currentCell.rowIndex);
6602
+ }
5616
6603
  }
5617
6604
  };
5618
6605
 
@@ -6036,7 +7023,7 @@ var createHTMLString = function createHTMLString(selectedData, isNeat) {
6036
7023
  var htmlString = '<table>';
6037
7024
  htmlString += selectedData.map(function (row) {
6038
7025
  return '<tr>' + Object.values(row).map(function (value) {
6039
- return '<td>' + htmlSafe(value) + '</td>';
7026
+ return ['<td>', htmlSafe(value), '</td>'].join('');
6040
7027
  }).join('') + '</tr>';
6041
7028
  }).join('');
6042
7029
  htmlString += '</table>';
@@ -6068,6 +7055,14 @@ __webpack_require__.r(__webpack_exports__);
6068
7055
  /*globals HTMLElement: false, Reflect: false, define: true, MutationObserver: false, requestAnimationFrame: false, performance: false, btoa: false*/
6069
7056
 
6070
7057
 
7058
+ function _toConsumableArray(arr) { return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread(); }
7059
+
7060
+ function _nonIterableSpread() { throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
7061
+
7062
+ function _iterableToArray(iter) { if (typeof Symbol !== "undefined" && Symbol.iterator in Object(iter)) return Array.from(iter); }
7063
+
7064
+ function _arrayWithoutHoles(arr) { if (Array.isArray(arr)) return _arrayLikeToArray(arr); }
7065
+
6071
7066
  function _typeof(obj) { "@babel/helpers - typeof"; if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }; } return _typeof(obj); }
6072
7067
 
6073
7068
  function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
@@ -6138,6 +7133,21 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6138
7133
  self.scrollBox = {};
6139
7134
  self.visibleRows = [];
6140
7135
  self.visibleCells = [];
7136
+ /**
7137
+ * This array stored all groups information with context for drawing,
7138
+ * it is generated by drawing functions,
7139
+ * and be used for searching groups when users operate on the spreadsheet
7140
+ * Each item of this array contains these properties:
7141
+ * - `type`: its available values: 'c' and 'r'. indicates the type of this item, 'c' for column group
7142
+ * and 'r' for row group.
7143
+ * - `x`,`y`: the left-top point of this group's rendering area.
7144
+ * - `x2`, `y2`: the right-bottom of this group's rendering area.
7145
+ * - `collapsed`: this value indicates the collapsed status of this group.
7146
+ * - `from`, `to`: The column index range of this group (We use this value for searching the group)
7147
+ * - `row`: The row index for column groups (We use this value for searching the group)
7148
+ */
7149
+
7150
+ self.visibleGroups = [];
6141
7151
  self.sizes = {
6142
7152
  rows: {},
6143
7153
  columns: {},
@@ -6152,6 +7162,18 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6152
7162
  columnIndex: -1,
6153
7163
  rowIndex: -1
6154
7164
  };
7165
+ self.cellTree = {
7166
+ rows: [],
7167
+ columns: {},
7168
+ tempSchema: {},
7169
+ rowTreeColIndex: 0,
7170
+ columnTreeRowStartIndex: 0,
7171
+ columnTreeRowEndIndex: 0,
7172
+ origin: {
7173
+ rows: [],
7174
+ columns: {}
7175
+ }
7176
+ };
6155
7177
  self.hovers = {};
6156
7178
  self.attributes = {};
6157
7179
  self.style = {};
@@ -6167,9 +7189,31 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6167
7189
  self.scrollPixelLeft = 0;
6168
7190
  self.childGrids = {};
6169
7191
  self.openChildren = {};
7192
+ /**
7193
+ * Array for grouped columns
7194
+ * Each item in this array is an array and it represents some grouping in one row
7195
+ * A grouping descriptor has three properties:
7196
+ * - `from`: The column index of the first column
7197
+ * - `to`: The column index of the last column
7198
+ * - `collapsed`: Is this group be collapsed
7199
+ * @example [[{ from: 1, to: 2, collapsed: false }]]
7200
+ */
7201
+
7202
+ self.groupedColumns = [];
7203
+ /**
7204
+ * Array for grouped rows
7205
+ * Each item in this array is an array and it represents some grouping in one column
7206
+ * A grouping descriptor has three properties:
7207
+ * - `from`: The row index of the first row
7208
+ * - `to`: The row index of the last row
7209
+ * - `collapsed`: Is this group be collapsed
7210
+ * @example [[{ from: 1, to: 2, collapsed: false }]]
7211
+ */
7212
+
7213
+ self.groupedRows = [];
6170
7214
  self.scrollModes = ['vertical-scroll-box', 'vertical-scroll-top', 'vertical-scroll-bottom', 'horizontal-scroll-box', 'horizontal-scroll-right', 'horizontal-scroll-left'];
6171
7215
  self.componentL1Events = {};
6172
- self.eventNames = ['afterdraw', 'afterrendercell', 'afterrenderfilterbutton', 'attributechanged', 'beforebeginedit', 'beforecreatecellgrid', 'beforedraw', 'beforeendedit', 'beforerendercell', 'beforerendercellgrid', 'beforerenderfilterbutton', 'beginedit', 'cellmouseout', 'cellmouseover', 'click', 'collapsetree', 'contextmenu', 'copy', 'datachanged', 'dblclick', 'endedit', 'expandtree', 'formatcellvalue', 'keydown', 'keypress', 'keyup', 'mousedown', 'mousemove', 'mouseup', 'newrow', 'ordercolumn', 'rendercell', 'rendercellgrid', 'renderorderbyarrow', 'rendertext', 'rendertreearrow', 'reorder', 'reordering', 'resize', 'resizecolumn', 'resizerow', 'schemachanged', 'scroll', 'selectionchanged', 'stylechanged', 'touchcancel', 'touchend', 'touchmove', 'touchstart', 'wheel'];
7216
+ self.eventNames = ['afterdraw', 'afterrendercell', 'afterrenderfilterbutton', 'aftercreategroup', 'attributechanged', 'beforebeginedit', 'beforecreatecellgrid', 'beforedraw', 'beforeendedit', 'beforerendercell', 'beforerendercellgrid', 'beforerenderfilterbutton', 'beginedit', 'cellmouseout', 'cellmouseover', 'click', 'collapsetree', 'contextmenu', 'copy', 'datachanged', 'dblclick', 'endedit', 'expandtree', 'formatcellvalue', 'keydown', 'keypress', 'keyup', 'mousedown', 'mousemove', 'mouseup', 'newrow', 'ordercolumn', 'rendercell', 'rendercellgrid', 'renderorderbyarrow', 'rendertext', 'rendertreearrow', 'reorder', 'reordering', 'resize', 'resizecolumn', 'resizerow', 'schemachanged', 'scroll', 'selectionchanged', 'stylechanged', 'touchcancel', 'touchend', 'touchmove', 'touchstart', 'wheel'];
6173
7217
  self.mouse = {
6174
7218
  x: 0,
6175
7219
  y: 0
@@ -6416,6 +7460,166 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6416
7460
  self.getBoundColumnIndexFromViewColumnIndex = function (viewColumnIndex) {
6417
7461
  return self.orders.columns[viewColumnIndex];
6418
7462
  };
7463
+ /**
7464
+ * Get the height of the area about column groups for rendering and handling events.
7465
+ */
7466
+
7467
+
7468
+ self.getColumnGroupAreaHeight = function () {
7469
+ if (!self.attributes.allowGroupingColumns) {
7470
+ return 0;
7471
+ }
7472
+
7473
+ var groups = self.groupedColumns.length;
7474
+ var base = self.style.columnGroupRowHeight * self.scale;
7475
+ return base * groups;
7476
+ };
7477
+ /**
7478
+ * Get the width of the area about row groups for rendering and handling events.
7479
+ */
7480
+
7481
+
7482
+ self.getRowGroupAreaWidth = function () {
7483
+ if (!self.attributes.allowGroupingRows) {
7484
+ return 0;
7485
+ }
7486
+
7487
+ var groups = self.groupedRows.length;
7488
+ var base = self.style.rowGroupColumnWidth * self.scale;
7489
+ return base * groups;
7490
+ };
7491
+
7492
+ self.getCollapsedColumnGroups = function () {
7493
+ var result = [];
7494
+
7495
+ for (var rowIndex = 0; rowIndex < self.groupedColumns.length; rowIndex++) {
7496
+ var groups = self.groupedColumns[rowIndex];
7497
+
7498
+ for (var groupIndex = 0; groupIndex < groups.length; groupIndex++) {
7499
+ var group = groups[groupIndex];
7500
+ if (group.collapsed) result.push(group);
7501
+ }
7502
+ }
7503
+
7504
+ return result;
7505
+ };
7506
+
7507
+ self.getCollapsedRowGroups = function () {
7508
+ var result = [];
7509
+
7510
+ for (var rowIndex = 0; rowIndex < self.groupedRows.length; rowIndex++) {
7511
+ var groups = self.groupedRows[rowIndex];
7512
+
7513
+ for (var groupIndex = 0; groupIndex < groups.length; groupIndex++) {
7514
+ var group = groups[groupIndex];
7515
+ if (group.collapsed) result.push(group);
7516
+ }
7517
+ }
7518
+
7519
+ return result;
7520
+ };
7521
+ /**
7522
+ * Toggle the collapse status of a group (expanded/collapsed)
7523
+ * @param {{type:string,from:number,to:number}} group
7524
+ */
7525
+
7526
+
7527
+ self.toggleGroup = function (group) {
7528
+ if (group.type === 'c') {
7529
+ var from = group.from,
7530
+ to = group.to;
7531
+ /** @type {{from:number,to:number,collapsed:boolean}} */
7532
+
7533
+ var matchedGroup;
7534
+ /** @type {Array<Array<{from:number,to:number,collapsed:boolean}>>} */
7535
+
7536
+ var allGroups = self.groupedColumns;
7537
+
7538
+ for (var i = 0; i < allGroups.length; i++) {
7539
+ var groups = allGroups[i];
7540
+
7541
+ for (var gi = 0; gi < groups.length; gi++) {
7542
+ var _group = groups[gi];
7543
+
7544
+ if (_group.from === from && _group.to === to) {
7545
+ matchedGroup = _group;
7546
+ break;
7547
+ }
7548
+ }
7549
+
7550
+ if (matchedGroup) break;
7551
+ }
7552
+
7553
+ if (!matchedGroup) return;
7554
+ var nextCollapsed = !matchedGroup.collapsed;
7555
+ matchedGroup.collapsed = nextCollapsed;
7556
+ return true;
7557
+ }
7558
+
7559
+ if (group.type === 'r') {
7560
+ var _from = group.from,
7561
+ _to = group.to;
7562
+ /** @type {{from:number,to:number,collapsed:boolean}} */
7563
+
7564
+ var _matchedGroup;
7565
+ /** @type {Array<Array<{from:number,to:number,collapsed:boolean}>>} */
7566
+
7567
+
7568
+ var _allGroups = self.groupedRows;
7569
+
7570
+ for (var _i3 = 0; _i3 < _allGroups.length; _i3++) {
7571
+ var _groups = _allGroups[_i3];
7572
+
7573
+ for (var _gi = 0; _gi < _groups.length; _gi++) {
7574
+ var _group2 = _groups[_gi];
7575
+
7576
+ if (_group2.from === _from && _group2.to === _to) {
7577
+ _matchedGroup = _group2;
7578
+ break;
7579
+ }
7580
+ }
7581
+
7582
+ if (_matchedGroup) break;
7583
+ }
7584
+
7585
+ if (!_matchedGroup) return;
7586
+
7587
+ var _nextCollapsed = !_matchedGroup.collapsed;
7588
+
7589
+ _matchedGroup.collapsed = _nextCollapsed;
7590
+ return true;
7591
+ }
7592
+
7593
+ return false;
7594
+ };
7595
+
7596
+ self.isNewGroupRangeValid = function (groupsArray, from, to) {
7597
+ for (var i = 0; i < groupsArray.length; i++) {
7598
+ var groups = groupsArray[i];
7599
+
7600
+ for (var gIndex = 0; gIndex < groups.length; gIndex++) {
7601
+ var group = groups[gIndex];
7602
+ if (from === group.to + 1) return false;
7603
+ if (from > group.to) continue;
7604
+
7605
+ if (from === group.from) {
7606
+ if (to === group.to) return false;
7607
+ if (to > group.to) return true;
7608
+ break; // check smaller range
7609
+ }
7610
+
7611
+ if (from > group.from) {
7612
+ if (to > group.to) return false;
7613
+ break; // check smaller range
7614
+ }
7615
+
7616
+ if (to < group.to) return false;
7617
+ return true;
7618
+ }
7619
+ }
7620
+
7621
+ return true;
7622
+ };
6419
7623
 
6420
7624
  self.getColumnHeaderCellHeight = function () {
6421
7625
  if (!self.attributes.showColumnHeaders) {
@@ -6568,6 +7772,19 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6568
7772
  return self.columnFilters && Object.keys(self.columnFilters).length > 0;
6569
7773
  };
6570
7774
 
7775
+ self.hasCollapsedRowGroup = function () {
7776
+ for (var i = 0; i < self.groupedRows.length; i++) {
7777
+ var groups = self.groupedRows[i];
7778
+
7779
+ for (var j = 0; j < groups.length; j++) {
7780
+ var g = groups[j];
7781
+ if (g.collapsed) return true;
7782
+ }
7783
+ }
7784
+
7785
+ return false;
7786
+ };
7787
+
6571
7788
  self.getFilteredAndSortedViewData = function (originalData) {
6572
7789
  // We make a copy of originalData here in order be able to
6573
7790
  // filter and sort rows without modifying the original array.
@@ -6580,7 +7797,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6580
7797
  }); // Apply filtering
6581
7798
 
6582
7799
  var _loop = function _loop() {
6583
- var _Object$entries2$_i = _slicedToArray(_Object$entries2[_i3], 2),
7800
+ var _Object$entries2$_i = _slicedToArray(_Object$entries2[_i4], 2),
6584
7801
  headerName = _Object$entries2$_i[0],
6585
7802
  filterText = _Object$entries2$_i[1];
6586
7803
 
@@ -6601,11 +7818,81 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6601
7818
  });
6602
7819
  };
6603
7820
 
6604
- for (var _i3 = 0, _Object$entries2 = Object.entries(self.columnFilters); _i3 < _Object$entries2.length; _i3++) {
7821
+ for (var _i4 = 0, _Object$entries2 = Object.entries(self.columnFilters); _i4 < _Object$entries2.length; _i4++) {
6605
7822
  var _ret = _loop();
6606
7823
 
6607
7824
  if (_ret === "continue") continue;
6608
- } // Apply sorting
7825
+ } //#region Hide rows from collapsed group
7826
+
7827
+ /** @type {number[][]} */
7828
+
7829
+
7830
+ var collapsedGroups = [];
7831
+
7832
+ for (var i = 0; i < self.groupedRows.length; i++) {
7833
+ var rows = self.groupedRows[i];
7834
+
7835
+ for (var j = 0; j < rows.length; j++) {
7836
+ var r = rows[j];
7837
+ if (!r.collapsed) continue;
7838
+ collapsedGroups.push([r.from, r.to]);
7839
+ }
7840
+ }
7841
+
7842
+ if (collapsedGroups.length > 0) {
7843
+ //#region merge groups
7844
+ collapsedGroups.sort(function (a, b) {
7845
+ return a[0] - b[0];
7846
+ });
7847
+ var newLen = 0;
7848
+ var len = collapsedGroups.length;
7849
+
7850
+ for (var _i5 = 0; _i5 < len; _i5++) {
7851
+ var _r = collapsedGroups[_i5];
7852
+
7853
+ if (_i5 === len - 1) {
7854
+ collapsedGroups[newLen++] = _r;
7855
+ break;
7856
+ }
7857
+
7858
+ var to = _r[1];
7859
+
7860
+ var _collapsedGroups = _slicedToArray(collapsedGroups[_i5 + 1], 2),
7861
+ from2 = _collapsedGroups[0],
7862
+ to2 = _collapsedGroups[1];
7863
+
7864
+ if (from2 > to + 1) {
7865
+ collapsedGroups[newLen++] = _r;
7866
+ continue;
7867
+ }
7868
+
7869
+ collapsedGroups[_i5 + 1] = _r;
7870
+ if (to2 > to) collapsedGroups[_i5 + 1][1] = to2;
7871
+ }
7872
+
7873
+ collapsedGroups = collapsedGroups.slice(0, newLen); //#endregion merge groups
7874
+ //#region omit rows by groups
7875
+
7876
+ var g = collapsedGroups.shift();
7877
+
7878
+ for (var start = 0; start < newViewData.length; start++) {
7879
+ var it = newViewData[start][1];
7880
+ if (it < g[0]) continue;
7881
+ var end = start + 1;
7882
+
7883
+ for (; end < newViewData.length; end++) {
7884
+ var it2 = newViewData[end][1];
7885
+ if (it2 > g[1]) break;
7886
+ }
7887
+
7888
+ newViewData.splice(start, end - start);
7889
+ g = collapsedGroups.shift();
7890
+ if (!g) break;
7891
+ start--;
7892
+ } //#endregion omit rows by groups
7893
+
7894
+ } //#endregion Hide rows from collapsed group
7895
+ // Apply sorting
6609
7896
 
6610
7897
 
6611
7898
  var _iterator8 = _createForOfIteratorHelper(self.orderings.columns),
@@ -6811,13 +8098,336 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6811
8098
  self.orders.columns = self.storedSettings.orders.columns;
6812
8099
  }
6813
8100
 
6814
- self.orderBy = self.storedSettings.orderBy === undefined ? s[0].name : self.storedSettings.orderBy;
6815
- self.orderDirection = self.storedSettings.orderDirection === undefined ? 'asc' : self.storedSettings.orderDirection;
8101
+ self.orderBy = self.storedSettings.orderBy === undefined ? s[0].name : self.storedSettings.orderBy;
8102
+ self.orderDirection = self.storedSettings.orderDirection === undefined ? 'asc' : self.storedSettings.orderDirection;
8103
+
8104
+ if (self.storedSettings.orderBy !== undefined && self.getHeaderByName(self.orderBy) && self.orderDirection) {
8105
+ self.order(self.orderBy, self.orderDirection);
8106
+ }
8107
+ }
8108
+ };
8109
+
8110
+ self.toggleCollapseTree = function (rowIndex, columnIndex, type) {
8111
+ var tempData = [];
8112
+ var collapsedCount = 0;
8113
+
8114
+ if (columnIndex == self.cellTree.rowTreeColIndex && (rowIndex > 0 || rowIndex == 0 && self.cellTree.rows[0].icon)) {
8115
+ var ctr = self.cellTree.rows;
8116
+
8117
+ switch (type) {
8118
+ case 'Expand':
8119
+ ctr[rowIndex].expand = true;
8120
+ self.cellTree.origin.rows[ctr[rowIndex].index].expand = true;
8121
+ break;
8122
+
8123
+ case 'Collapse':
8124
+ ctr[rowIndex].expand = false;
8125
+ self.cellTree.origin.rows[ctr[rowIndex].index].expand = false;
8126
+ break;
8127
+
8128
+ default:
8129
+ ctr[rowIndex].expand = !ctr[rowIndex].expand;
8130
+ self.cellTree.origin.rows[ctr[rowIndex].index].expand = ctr[rowIndex].expand;
8131
+ }
8132
+
8133
+ for (var ri = ctr[rowIndex].index + 1; ri <= ctr[rowIndex].lastchild; ri++) {
8134
+ var orTree = self.cellTree.origin.rows[ri];
8135
+
8136
+ if (ctr[rowIndex].expand) {
8137
+ orTree.hide = false;
8138
+ if (orTree.icon && !orTree.expand) ri = orTree.lastchild;
8139
+ } else {
8140
+ orTree.hide = true;
8141
+ }
8142
+ }
8143
+ } else if (self.cellTree.columns[rowIndex]) {
8144
+ var ctc = self.cellTree.columns[rowIndex];
8145
+
8146
+ switch (type) {
8147
+ case 'Expand':
8148
+ ctc[columnIndex].expand = true;
8149
+ break;
8150
+
8151
+ case 'Collapse':
8152
+ ctc[columnIndex].expand = false;
8153
+ break;
8154
+
8155
+ default:
8156
+ ctc[columnIndex].expand = !ctc[columnIndex].expand;
8157
+ }
8158
+
8159
+ for (var ci = ctc[columnIndex].index + 1; ci <= ctc[columnIndex].lastchild; ci++) {
8160
+ if (ctc[columnIndex].expand) self.cellTree.tempSchema[ci].hidden = false;else self.cellTree.tempSchema[ci].hidden = true;
8161
+ }
8162
+
8163
+ var rc = 0,
8164
+ _ri;
8165
+
8166
+ if (ctc[columnIndex].expand) {
8167
+ while (rc < ctc[columnIndex].child) {
8168
+ _ri = rowIndex + rc + 1;
8169
+
8170
+ for (var _ci = ctc[columnIndex].index; _ci <= ctc[columnIndex].lastchild; _ci++) {
8171
+ if (self.cellTree.origin.columns[_ri] && self.cellTree.origin.columns[_ri][_ci].icon && !self.cellTree.origin.columns[_ri][_ci].expand) {
8172
+ for (var si = _ci + 1; si <= self.cellTree.origin.columns[_ri][_ci].lastchild; si++) {
8173
+ self.cellTree.tempSchema[si].hidden = true;
8174
+ }
8175
+ }
8176
+ }
8177
+
8178
+ rc++;
8179
+ }
8180
+ }
8181
+ }
8182
+
8183
+ var otherData = {};
8184
+ var collapsed = [];
8185
+ self.cellTree.rows = [];
8186
+ self.cellTree.columns = {};
8187
+
8188
+ for (var k in self.cellTree.origin.rows) {
8189
+ var tempRow = [];
8190
+ var tree = self.cellTree.origin.rows[k];
8191
+
8192
+ if (!tree.hide) {
8193
+ var colTrees = [];
8194
+ var collapsedColCount = 0;
8195
+
8196
+ if (k < self.cellTree.columnTreeRowStartIndex) {
8197
+ tempData.push(self.originalData[k]);
8198
+ } else {
8199
+ if (k > self.cellTree.columnTreeRowEndIndex) {
8200
+ otherData[k] = self.viewData[k];
8201
+ collapsedCount++;
8202
+ } else {
8203
+ for (var l = 0; l < self.originalData[k].length; l++) {
8204
+ if (!self.cellTree.tempSchema[l].hidden) {
8205
+ if (l < self.cellTree.rowTreeColIndex) {
8206
+ if (!Object.prototype.hasOwnProperty.call(otherData, k)) otherData[k] = [];
8207
+ otherData[k].push(self.viewData[k][l]);
8208
+ }
8209
+
8210
+ tempRow.push(self.originalData[k][l]);
8211
+ if (Object.prototype.hasOwnProperty.call(self.cellTree.origin.columns, k)) colTrees.push(self.cellTree.origin.columns[k][l]);
8212
+ } else collapsedColCount++;
8213
+ }
8214
+
8215
+ tempRow.push.apply(tempRow, _toConsumableArray(Array(collapsedColCount).fill().map(function () {
8216
+ return '';
8217
+ })));
8218
+
8219
+ if (colTrees.length) {
8220
+ colTrees.push.apply(colTrees, _toConsumableArray(Array(collapsedColCount).fill().map(function () {
8221
+ return {};
8222
+ })));
8223
+ self.cellTree.columns[k] = colTrees;
8224
+ }
8225
+
8226
+ tempData.push(tempRow);
8227
+ }
8228
+ }
8229
+
8230
+ self.cellTree.rows.push(tree);
8231
+ } else {
8232
+ for (var _l = 0; _l < self.cellTree.rowTreeColIndex; _l++) {
8233
+ tempRow.push(self.viewData[k][_l]);
8234
+ }
8235
+
8236
+ otherData[k] = tempRow;
8237
+ collapsed.push(Array(self.viewData[0].length).fill().map(function () {
8238
+ return '';
8239
+ }));
8240
+ collapsedCount++;
8241
+ }
8242
+ }
8243
+
8244
+ if (collapsedCount) {
8245
+ var _self$cellTree$rows;
8246
+
8247
+ (_self$cellTree$rows = self.cellTree.rows).push.apply(_self$cellTree$rows, _toConsumableArray(Array(collapsedCount).fill().map(function (u, index) {
8248
+ return {
8249
+ index: self.cellTree.rows.length + index
8250
+ };
8251
+ })));
8252
+
8253
+ tempData.push.apply(tempData, collapsed);
8254
+ }
8255
+
8256
+ for (var _k in otherData) {
8257
+ if (_k > self.cellTree.columnTreeRowEndIndex) tempData[_k] = otherData[_k];else for (var _l2 in otherData[_k]) {
8258
+ tempData[_k][_l2] = otherData[_k][_l2];
8259
+ }
8260
+ }
8261
+
8262
+ self.viewData = tempData;
8263
+ };
8264
+
8265
+ self.cellTreeExpandCollapse = function (rowIndex, columnIndex, type) {
8266
+ if (columnIndex == self.cellTree.rowTreeColIndex && (rowIndex > 0 || rowIndex == 0 && self.cellTree.rows[0].icon)) {
8267
+ var ctr = self.cellTree.rows;
8268
+
8269
+ switch (type) {
8270
+ case 'Expand':
8271
+ ctr[rowIndex].expand = true;
8272
+ break;
8273
+
8274
+ case 'Collapse':
8275
+ ctr[rowIndex].expand = false;
8276
+ break;
8277
+
8278
+ default:
8279
+ ctr[rowIndex].expand = !ctr[rowIndex].expand;
8280
+ }
8281
+
8282
+ for (var ri = rowIndex + 1; ri <= ctr[rowIndex].lastchild; ri++) {
8283
+ if (ctr[rowIndex].expand) {
8284
+ ctr[ri].hide = false;
8285
+ if (ctr[ri].icon && !ctr[ri].expand) ri = ctr[ri].lastchild;
8286
+ } else {
8287
+ ctr[ri].hide = true;
8288
+ }
8289
+ }
8290
+ } else if (self.cellTree.columns[rowIndex]) {
8291
+ var ctc = self.cellTree.columns[rowIndex];
8292
+
8293
+ switch (type) {
8294
+ case 'Expand':
8295
+ ctc[columnIndex].expand = true;
8296
+ break;
8297
+
8298
+ case 'Collapse':
8299
+ ctc[columnIndex].expand = false;
8300
+ break;
8301
+
8302
+ default:
8303
+ ctc[columnIndex].expand = !ctc[columnIndex].expand;
8304
+ }
8305
+
8306
+ for (var ci = columnIndex + 1; ci <= ctc[columnIndex].lastchild; ci++) {
8307
+ if (ctc[columnIndex].expand) self.tempSchema[ci].hidden = false;else self.tempSchema[ci].hidden = true;
8308
+ }
8309
+
8310
+ var rc = 0,
8311
+ _ri2;
8312
+
8313
+ if (ctc[columnIndex].expand) {
8314
+ while (rc < ctc[columnIndex].child) {
8315
+ _ri2 = rowIndex + rc + 1;
8316
+
8317
+ for (var _ci2 = columnIndex; _ci2 <= ctc[columnIndex].lastchild; _ci2++) {
8318
+ if (self.cellTree.columns[_ri2] && self.cellTree.columns[_ri2][_ci2].icon && !self.cellTree.columns[_ri2][_ci2].expand) {
8319
+ for (var si = _ci2 + 1; si <= self.cellTree.columns[_ri2][_ci2].lastchild; si++) {
8320
+ self.tempSchema[si].hidden = true;
8321
+ }
8322
+ }
8323
+ }
8324
+
8325
+ rc++;
8326
+ }
8327
+ }
8328
+ }
8329
+ };
8330
+
8331
+ self.initCellTreeSettings = function () {
8332
+ if (self.viewData === undefined) return;
8333
+
8334
+ if (self.attributes.rowTree.length > 0 && self.viewData.length > 0) {
8335
+ self.cellTree.rows = Array(self.viewData.length).fill().map(function (u, index) {
8336
+ return {
8337
+ index: index
8338
+ };
8339
+ });
8340
+ self.cellTree.rowTreeColIndex = self.attributes.rowTreeColIndex;
8341
+ var invalidRowTree = false;
8342
+
8343
+ var _iterator9 = _createForOfIteratorHelper(self.attributes.rowTree),
8344
+ _step9;
8345
+
8346
+ try {
8347
+ for (_iterator9.s(); !(_step9 = _iterator9.n()).done;) {
8348
+ var rt = _step9.value;
8349
+
8350
+ if (self.cellTree.rows.length <= rt.end) {
8351
+ invalidRowTree = true;
8352
+ break;
8353
+ }
8354
+
8355
+ for (var ri = rt.begin; ri <= rt.end; ri++) {
8356
+ if (ri == rt.begin) {
8357
+ self.cellTree.rows[ri].icon = true;
8358
+ self.cellTree.rows[ri].lastchild = rt.end;
8359
+ self.cellTree.rows[ri].expand = true;
8360
+ if (!self.cellTree.rows[ri].parentCount) self.cellTree.rows[ri].parentCount = 0;
8361
+ } else {
8362
+ self.cellTree.rows[ri].hide = false;
8363
+ self.cellTree.rows[ri].parentIndex = rt.begin;
8364
+ if (self.cellTree.rows[ri] && self.cellTree.rows[ri].parentCount) self.cellTree.rows[ri].parentCount += 1;else self.cellTree.rows[ri].parentCount = 1;
8365
+ }
8366
+ }
8367
+ }
8368
+ } catch (err) {
8369
+ _iterator9.e(err);
8370
+ } finally {
8371
+ _iterator9.f();
8372
+ }
8373
+
8374
+ if (invalidRowTree) self.cellTree.rows = {};
8375
+ }
8376
+
8377
+ if (self.attributes.columnTree.length > 0 && self.viewData.length > 0) {
8378
+ self.cellTree.columnTreeRowStartIndex = self.attributes.columnTreeRowStartIndex;
8379
+ self.cellTree.columnTreeRowEndIndex = self.attributes.columnTreeRowEndIndex;
8380
+ var dataColumnLength = Object.keys(self.viewData[0]).length;
8381
+ var invalidColumnTree = false;
8382
+
8383
+ var _iterator10 = _createForOfIteratorHelper(self.attributes.columnTree),
8384
+ _step10;
8385
+
8386
+ try {
8387
+ for (_iterator10.s(); !(_step10 = _iterator10.n()).done;) {
8388
+ var ct = _step10.value;
8389
+
8390
+ if (dataColumnLength <= ct.end) {
8391
+ invalidColumnTree = true;
8392
+ break;
8393
+ }
8394
+
8395
+ if (!self.cellTree.columns[ct.row]) self.cellTree.columns[ct.row] = Array(dataColumnLength).fill().map(function (u, index) {
8396
+ return {
8397
+ index: index
8398
+ };
8399
+ });
8400
+
8401
+ for (var i = ct.begin; i <= ct.end; i++) {
8402
+ var ctc = self.cellTree.columns[ct.row][i];
6816
8403
 
6817
- if (self.storedSettings.orderBy !== undefined && self.getHeaderByName(self.orderBy) && self.orderDirection) {
6818
- self.order(self.orderBy, self.orderDirection);
8404
+ if (i == ct.begin) {
8405
+ ctc.icon = true;
8406
+ ctc.lastchild = ct.end;
8407
+ ctc.length = ct.end - ct.begin;
8408
+ ctc.expand = true;
8409
+ if (ct.child) ctc.child = ct.child;else ctc.child = 0;
8410
+ }
8411
+ }
8412
+ }
8413
+ } catch (err) {
8414
+ _iterator10.e(err);
8415
+ } finally {
8416
+ _iterator10.f();
6819
8417
  }
8418
+
8419
+ self.cellTree.tempSchema = Array(dataColumnLength).fill().map(function () {
8420
+ return {
8421
+ hidden: false
8422
+ };
8423
+ });
8424
+ if (invalidColumnTree) self.cellTree.columns = {};
6820
8425
  }
8426
+
8427
+ self.cellTree.origin = {
8428
+ rows: self.cellTree.rows,
8429
+ columns: self.cellTree.columns
8430
+ };
6821
8431
  };
6822
8432
 
6823
8433
  self.getDomRoot = function () {
@@ -7000,6 +8610,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
7000
8610
  self.intf.gotoCell = self.gotoCell;
7001
8611
  self.intf.gotoRow = self.gotoRow;
7002
8612
  self.intf.addButton = self.addButton;
8613
+ self.intf.toggleCellCollapseTree = self.toggleCellCollapseTree;
8614
+ self.intf.expandCollapseCellTree = self.expandCollapseCellTree;
7003
8615
  self.intf.getHeaderByName = self.getHeaderByName;
7004
8616
  self.intf.findColumnScrollLeft = self.findColumnScrollLeft;
7005
8617
  self.intf.findRowScrollTop = self.findRowScrollTop;
@@ -7007,6 +8619,14 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
7007
8619
  self.intf.findColumnMaxTextLength = self.findColumnMaxTextLength;
7008
8620
  self.intf.disposeContextMenu = self.disposeContextMenu;
7009
8621
  self.intf.getCellAt = self.getCellAt;
8622
+ self.intf.groupColumns = self.groupColumns;
8623
+ self.intf.groupRows = self.groupRows;
8624
+ self.intf.removeGroupColumns = self.removeGroupColumns;
8625
+ self.intf.removeGroupRows = self.removeGroupRows;
8626
+ self.intf.toggleGroupColumns = self.toggleGroupColumns;
8627
+ self.intf.toggleGroupRows = self.toggleGroupRows;
8628
+ self.intf.getGroupsColumnBelongsTo = self.getGroupsColumnBelongsTo;
8629
+ self.intf.getGroupsRowBelongsTo = self.getGroupsRowBelongsTo;
7010
8630
  self.intf.isCellVisible = self.isCellVisible;
7011
8631
  self.intf.isRowVisible = self.isRowVisible;
7012
8632
  self.intf.isColumnVisible = self.isColumnVisible;
@@ -7137,6 +8757,10 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
7137
8757
  self.tryLoadStoredSettings();
7138
8758
  }
7139
8759
 
8760
+ if (key === 'rowTree' || key === 'columnTree' || key === 'columnTreeRowEndIndex') {
8761
+ self.initCellTreeSettings();
8762
+ }
8763
+
7140
8764
  self.draw(true);
7141
8765
  self.dispatchEvent('attributechanged', {
7142
8766
  name: key,
@@ -7771,6 +9395,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
7771
9395
  self.dispatchEvent('datachanged', {
7772
9396
  data: self.originalData
7773
9397
  });
9398
+ self.initCellTreeSettings();
7774
9399
  self.resize(true);
7775
9400
  });
7776
9401
  }
@@ -8120,6 +9745,12 @@ __webpack_require__.r(__webpack_exports__);
8120
9745
  /*globals define: true, MutationObserver: false, requestAnimationFrame: false, performance: false, btoa: false*/
8121
9746
 
8122
9747
 
9748
+ function _createForOfIteratorHelper(o, allowArrayLike) { var it; if (typeof Symbol === "undefined" || o[Symbol.iterator] == null) { if (Array.isArray(o) || (it = _unsupportedIterableToArray(o)) || allowArrayLike && o && typeof o.length === "number") { if (it) o = it; var i = 0; var F = function F() {}; return { s: F, n: function n() { if (i >= o.length) return { done: true }; return { done: false, value: o[i++] }; }, e: function e(_e) { throw _e; }, f: F }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } var normalCompletion = true, didErr = false, err; return { s: function s() { it = o[Symbol.iterator](); }, n: function n() { var step = it.next(); normalCompletion = step.done; return step; }, e: function e(_e2) { didErr = true; err = _e2; }, f: function f() { try { if (!normalCompletion && it["return"] != null) it["return"](); } finally { if (didErr) throw err; } } }; }
9749
+
9750
+ function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
9751
+
9752
+ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
9753
+
8123
9754
  /* harmony default export */ function __WEBPACK_DEFAULT_EXPORT__(self) {
8124
9755
  /**
8125
9756
  * Converts a integer into a letter A - ZZZZZ...
@@ -8466,6 +10097,62 @@ __webpack_require__.r(__webpack_exports__);
8466
10097
  left: cells[0].x + cells[0].width + offset.x
8467
10098
  }, items, imgSrc);
8468
10099
  };
10100
+ /**
10101
+ * Expand/Collapse CellTree.
10102
+ * @memberof canvasDatagrid
10103
+ * @name toggleCellCollapseTree
10104
+ * @method
10105
+ * @param {array} treeData The array of cellTree to expand or collapse.
10106
+ */
10107
+
10108
+
10109
+ self.toggleCellCollapseTree = function (treeData) {
10110
+ for (var type in treeData) {
10111
+ var _iterator = _createForOfIteratorHelper(treeData[type]),
10112
+ _step;
10113
+
10114
+ try {
10115
+ for (_iterator.s(); !(_step = _iterator.n()).done;) {
10116
+ var t = _step.value;
10117
+ if (t.length > 0) self.toggleCollapseTree(t[0], t[1], type);
10118
+ }
10119
+ } catch (err) {
10120
+ _iterator.e(err);
10121
+ } finally {
10122
+ _iterator.f();
10123
+ }
10124
+ }
10125
+
10126
+ self.draw();
10127
+ };
10128
+ /**
10129
+ * Expand/Collapse CellTree.
10130
+ * @memberof canvasDatagrid
10131
+ * @name expandCollapseCellTree
10132
+ * @method
10133
+ * @param {array} treeData The array of cellTree to expand or collapse.
10134
+ */
10135
+
10136
+
10137
+ self.expandCollapseCellTree = function (treeData) {
10138
+ for (var type in treeData) {
10139
+ var _iterator2 = _createForOfIteratorHelper(treeData[type]),
10140
+ _step2;
10141
+
10142
+ try {
10143
+ for (_iterator2.s(); !(_step2 = _iterator2.n()).done;) {
10144
+ var t = _step2.value;
10145
+ if (t.length > 0) self.cellTreeExpandCollapse(t[0], t[1], type);
10146
+ }
10147
+ } catch (err) {
10148
+ _iterator2.e(err);
10149
+ } finally {
10150
+ _iterator2.f();
10151
+ }
10152
+ }
10153
+
10154
+ self.draw();
10155
+ };
8469
10156
  /**
8470
10157
  * Scrolls the cell at cell x, row y into view if it is not already.
8471
10158
  * @memberof canvasDatagrid
@@ -9017,6 +10704,315 @@ __webpack_require__.r(__webpack_exports__);
9017
10704
 
9018
10705
  self.setStorageData();
9019
10706
  };
10707
+ /**
10708
+ * Add grouping
10709
+ * @param {'columns'|'rows'} groupFor
10710
+ * @param {number} from
10711
+ * @param {number} to
10712
+ */
10713
+
10714
+
10715
+ function addGroup(groupFor, from, to) {
10716
+ var newRow = false;
10717
+ var allGroups = groupFor === 'rows' ? self.groupedRows : self.groupedColumns;
10718
+
10719
+ for (var i = allGroups.length - 1; i >= 0; i--) {
10720
+ var groups = allGroups[i];
10721
+ var min = groups[0].from,
10722
+ max = groups[groups.length - 1].to;
10723
+
10724
+ if (from <= min && to >= max) {
10725
+ if (from === min && to === max && groups.length === 1) return; // nothings happened
10726
+ // new group wrap this row
10727
+
10728
+ continue;
10729
+ }
10730
+
10731
+ for (var gi = 0; gi < groups.length; gi++) {
10732
+ var g = groups[gi];
10733
+ if (from > g.to) continue;
10734
+
10735
+ if (from >= g.from) {
10736
+ if (to > g.to) {
10737
+ if (from === g.from) {
10738
+ allGroups.splice(i, 0, [{
10739
+ from: from,
10740
+ to: to,
10741
+ collapsed: false
10742
+ }]);
10743
+ self.refresh();
10744
+ return;
10745
+ }
10746
+
10747
+ throw new Error("Can't group these ".concat(groupFor));
10748
+ }
10749
+
10750
+ if (to === g.to) {
10751
+ if (from === g.from) return; // nothings happened
10752
+ }
10753
+
10754
+ newRow = true;
10755
+ break;
10756
+ }
10757
+
10758
+ if (to >= g.from) {
10759
+ if (to < g.to) throw new Error("Can't group these ".concat(groupFor));
10760
+ allGroups.splice(i, 0, [{
10761
+ from: from,
10762
+ to: to,
10763
+ collapsed: false
10764
+ }]);
10765
+ } else {
10766
+ groups.splice(gi, 0, {
10767
+ from: from,
10768
+ to: to,
10769
+ collapsed: false
10770
+ });
10771
+ }
10772
+
10773
+ self.refresh();
10774
+ return;
10775
+ }
10776
+
10777
+ if (newRow) continue;
10778
+ groups.push({
10779
+ from: from,
10780
+ to: to,
10781
+ collapsed: false
10782
+ });
10783
+ self.refresh();
10784
+ return;
10785
+ }
10786
+
10787
+ if (newRow) allGroups.push([{
10788
+ from: from,
10789
+ to: to,
10790
+ collapsed: false
10791
+ }]);else allGroups.unshift([{
10792
+ from: from,
10793
+ to: to,
10794
+ collapsed: false
10795
+ }]);
10796
+ self.refresh();
10797
+ }
10798
+ /**
10799
+ * Remove grouping
10800
+ * @param {Array<Array<{from:number,to:number,collapsed:boolean}>>} allGroups
10801
+ * @param {number} from
10802
+ * @param {number} to
10803
+ */
10804
+
10805
+
10806
+ function removeGroup(allGroups, from, to) {
10807
+ for (var i = 0; i < allGroups.length; i++) {
10808
+ var groups = allGroups[i];
10809
+
10810
+ for (var gi = 0; gi < groups.length; gi++) {
10811
+ var group = groups[gi];
10812
+
10813
+ if (group.from === from && group.to === to) {
10814
+ if (groups.length <= 1) allGroups.splice(i, 1);else groups.splice(gi, 1);
10815
+ self.refresh();
10816
+ return;
10817
+ }
10818
+ }
10819
+ }
10820
+ }
10821
+ /**
10822
+ * Grouping columns
10823
+ * @memberof canvasDatagrid
10824
+ * @name groupColumns
10825
+ * @method
10826
+ * @param {number|string} firstColumnName Name of the first column to be grouped.
10827
+ * @param {number|string} lastColumnName Name of the last column to be grouped.
10828
+ */
10829
+
10830
+
10831
+ self.groupColumns = function (firstColumnName, lastColumnName) {
10832
+ /** @type {Array<{name: string,columnIndex:number}>} */
10833
+ var schema = self.getSchema();
10834
+ var firstOne, lastOne;
10835
+
10836
+ for (var i = 0; i < schema.length; i++) {
10837
+ var it = schema[i];
10838
+ if (firstOne && lastOne) break;
10839
+
10840
+ if (it.name === firstColumnName) {
10841
+ firstOne = it;
10842
+ continue;
10843
+ }
10844
+
10845
+ if (it.name === lastColumnName) {
10846
+ lastOne = it;
10847
+ continue;
10848
+ }
10849
+ }
10850
+
10851
+ if (!firstOne) throw new Error("No such column name for first column");
10852
+ if (!lastOne) throw new Error("No such column name for last column");
10853
+ if (lastOne.columnIndex > firstOne.columnIndex !== true) throw new Error("Can't group these columns");
10854
+ var from = firstOne.columnIndex;
10855
+ var to = lastOne.columnIndex;
10856
+ var ev = {
10857
+ group: {
10858
+ type: 'columns',
10859
+ from: from,
10860
+ to: to
10861
+ }
10862
+ };
10863
+
10864
+ try {
10865
+ addGroup('columns', from, to);
10866
+ } catch (error) {
10867
+ ev.error = error;
10868
+ }
10869
+
10870
+ self.dispatchEvent('aftercreategroup', ev);
10871
+ };
10872
+ /**
10873
+ * Grouping columns
10874
+ * @memberof canvasDatagrid
10875
+ * @name groupRows
10876
+ * @method
10877
+ * @param {number} rowIndexFrom The row index which is the beginning of the group
10878
+ * @param {number} rowIndexTo The row index which is the end of the group
10879
+ */
10880
+
10881
+
10882
+ self.groupRows = function (rowIndexFrom, rowIndexTo) {
10883
+ if (!Number.isInteger(rowIndexFrom) || rowIndexFrom < 0) throw new Error("No such row for the beginning of the group");
10884
+ var dataLength = self.viewData.length;
10885
+ if (!Number.isInteger(rowIndexFrom) || rowIndexTo <= rowIndexFrom || rowIndexTo >= dataLength) throw new Error("No such row for the end of the group");
10886
+ var ev = {
10887
+ group: {
10888
+ type: 'rows',
10889
+ from: rowIndexFrom,
10890
+ to: rowIndexTo
10891
+ }
10892
+ };
10893
+
10894
+ try {
10895
+ addGroup('rows', rowIndexFrom, rowIndexTo);
10896
+ } catch (error) {
10897
+ ev.error = error;
10898
+ }
10899
+
10900
+ self.dispatchEvent('aftercreategroup', ev);
10901
+ };
10902
+ /**
10903
+ * Remove grouping columns
10904
+ * @memberof canvasDatagrid
10905
+ * @name removeGroupColumns
10906
+ * @method
10907
+ * @param {number|string} firstColumnName Name of the first column to be grouped.
10908
+ * @param {number|string} lastColumnName Name of the last column to be grouped.
10909
+ */
10910
+
10911
+
10912
+ self.removeGroupColumns = function (firstColumnName, lastColumnName) {
10913
+ /** @type {Array<{name:string,columnIndex:number}>} */
10914
+ var schema = self.getSchema();
10915
+ var firstOne, lastOne;
10916
+
10917
+ for (var i = 0; i < schema.length; i++) {
10918
+ var it = schema[i];
10919
+ if (firstOne && lastOne) break;
10920
+
10921
+ if (it.name === firstColumnName) {
10922
+ firstOne = it;
10923
+ continue;
10924
+ }
10925
+
10926
+ if (it.name === lastColumnName) {
10927
+ lastOne = it;
10928
+ continue;
10929
+ }
10930
+ }
10931
+
10932
+ if (!firstOne) throw new Error("No such column name for first column");
10933
+ if (!lastOne) throw new Error("No such column name for last column");
10934
+ var from = firstOne.columnIndex;
10935
+ var to = lastOne.columnIndex;
10936
+ removeGroup(self.groupedColumns, from, to);
10937
+ };
10938
+ /**
10939
+ * Remove grouping columns
10940
+ * @memberof canvasDatagrid
10941
+ * @name removeGroupRows
10942
+ * @method
10943
+ * @param {number} rowIndexFrom The row index which is the beginning of the group
10944
+ * @param {number} rowIndexTo The row index which is the end of the group
10945
+ */
10946
+
10947
+
10948
+ self.removeGroupRows = function (rowIndexFrom, rowIndexTo) {
10949
+ removeGroup(self.groupedRows, rowIndexFrom, rowIndexTo);
10950
+ };
10951
+ /**
10952
+ * Toggle(expand/collapsed) grouping columns
10953
+ * @memberof canvasDatagrid
10954
+ * @name toggleGroupColumns
10955
+ * @method
10956
+ * @param {number|string} firstColumnName Name of the first column to be grouped.
10957
+ * @param {number|string} lastColumnName Name of the last column to be grouped.
10958
+ */
10959
+
10960
+
10961
+ self.toggleGroupColumns = function (firstColumnName, lastColumnName) {
10962
+ /** @type {Array<{name:string,columnIndex:number}>} */
10963
+ var schema = self.getSchema();
10964
+ var firstOne, lastOne;
10965
+
10966
+ for (var i = 0; i < schema.length; i++) {
10967
+ var it = schema[i];
10968
+ if (firstOne && lastOne) break;
10969
+
10970
+ if (it.name === firstColumnName) {
10971
+ firstOne = it;
10972
+ continue;
10973
+ }
10974
+
10975
+ if (it.name === lastColumnName) {
10976
+ lastOne = it;
10977
+ continue;
10978
+ }
10979
+ }
10980
+
10981
+ if (!firstOne || !lastOne) return;
10982
+ var from = firstOne.columnIndex;
10983
+ var to = lastOne.columnIndex;
10984
+
10985
+ if (self.toggleGroup({
10986
+ type: 'c',
10987
+ from: from,
10988
+ to: to
10989
+ })) {
10990
+ self.disposeContextMenu();
10991
+ self.setStorageData();
10992
+ self.refresh();
10993
+ }
10994
+ };
10995
+ /**
10996
+ * Toggle(expand/collapsed) grouping rows
10997
+ * @memberof canvasDatagrid
10998
+ * @name toggleGroupRows
10999
+ * @method
11000
+ * @param {number} rowIndexFrom The row index which is the beginning of the group
11001
+ * @param {number} rowIndexTo The row index which is the end of the group
11002
+ */
11003
+
11004
+
11005
+ self.toggleGroupRows = function (rowIndexFrom, rowIndexTo) {
11006
+ if (self.toggleGroup({
11007
+ type: 'r',
11008
+ from: rowIndexFrom,
11009
+ to: rowIndexTo
11010
+ })) {
11011
+ self.disposeContextMenu();
11012
+ self.setStorageData();
11013
+ self.refresh();
11014
+ }
11015
+ };
9020
11016
 
9021
11017
  self.isInGrid = function (e) {
9022
11018
  if (e.x < 0 || e.x > self.width || e.y < 0 || e.y > self.height) {
@@ -9107,6 +11103,10 @@ __webpack_require__.r(__webpack_exports__);
9107
11103
  } // TODO:
9108
11104
 
9109
11105
 
11106
+ if (!self.data) {
11107
+ self.data = {};
11108
+ }
11109
+
9110
11110
  if (!self.data[rowIndex]) {
9111
11111
  self.data[rowIndex] = {};
9112
11112
  } // TODO:
@@ -9145,6 +11145,64 @@ __webpack_require__.r(__webpack_exports__);
9145
11145
  });
9146
11146
  });
9147
11147
  };
11148
+ /**
11149
+ * Get the column group info given column belongs to
11150
+ * @memberof canvasDatagrid
11151
+ * @name getGroupsColumnBelongsTo
11152
+ * @method
11153
+ * @param {number} columnIndex Column index.
11154
+ * @returns {Array<{from:number,to:number,collapsed:boolean}>}
11155
+ */
11156
+
11157
+
11158
+ self.getGroupsColumnBelongsTo = function (columnIndex) {
11159
+ if (!self.attributes.allowGroupingColumns) return [];
11160
+ var result = [];
11161
+
11162
+ for (var i = 0; i < self.groupedColumns.length; i++) {
11163
+ var groups = self.groupedColumns[i];
11164
+
11165
+ for (var j = 0; j < groups.length; j++) {
11166
+ var group = groups[j];
11167
+
11168
+ if (columnIndex >= group.from && columnIndex <= group.to) {
11169
+ result.push(group);
11170
+ break;
11171
+ }
11172
+ }
11173
+ }
11174
+
11175
+ return result;
11176
+ };
11177
+ /**
11178
+ * Get the row group info given row belongs to
11179
+ * @memberof canvasDatagrid
11180
+ * @name getGroupsRowBelongsTo
11181
+ * @method
11182
+ * @param {number} rowIndex Row index.
11183
+ * @returns {Array<{from:number,to:number,collapsed:boolean}>}
11184
+ */
11185
+
11186
+
11187
+ self.getGroupsRowBelongsTo = function (rowIndex) {
11188
+ if (!self.attributes.allowGroupingRows) return [];
11189
+ var result = [];
11190
+
11191
+ for (var i = 0; i < self.groupedRows.length; i++) {
11192
+ var groups = self.groupedRows[i];
11193
+
11194
+ for (var j = 0; j < groups.length; j++) {
11195
+ var group = groups[j];
11196
+
11197
+ if (rowIndex >= group.from && rowIndex <= group.to) {
11198
+ result.push(group);
11199
+ break;
11200
+ }
11201
+ }
11202
+ }
11203
+
11204
+ return result;
11205
+ };
9148
11206
  /**
9149
11207
  * Checks if a given column is visible.
9150
11208
  * @memberof canvasDatagrid
@@ -9191,6 +11249,48 @@ __webpack_require__.r(__webpack_exports__);
9191
11249
  return c.columnIndex === x && c.rowIndex === y;
9192
11250
  })[0];
9193
11251
  };
11252
+ /**
11253
+ * @memberof canvasDatagrid
11254
+ * @name getColumnGroupAt
11255
+ * @method
11256
+ * @param {number} x Number of pixels from the left.
11257
+ * @param {number} y Number of pixels from the top.
11258
+ */
11259
+
11260
+
11261
+ self.getColumnGroupAt = function (x, y) {
11262
+ var groups = self.groupedColumns.length;
11263
+ if (groups <= 0) return;
11264
+ var yZero = self.getColumnGroupAreaHeight();
11265
+ if (y >= yZero) return;
11266
+
11267
+ for (var i = 0; i < self.visibleGroups.length; i++) {
11268
+ var g = self.visibleGroups[i];
11269
+ if (g.type !== 'c') continue;
11270
+ if (x >= g.x && y >= g.y && x <= g.x2 && y <= g.y2) return g;
11271
+ }
11272
+ };
11273
+ /**
11274
+ * @memberof canvasDatagrid
11275
+ * @name getRowGroupAt
11276
+ * @method
11277
+ * @param {number} x Number of pixels from the left.
11278
+ * @param {number} y Number of pixels from the top.
11279
+ */
11280
+
11281
+
11282
+ self.getRowGroupAt = function (x, y) {
11283
+ var groups = self.groupedRows.length;
11284
+ if (groups <= 0) return;
11285
+ var xZero = self.getRowGroupAreaWidth();
11286
+ if (x >= xZero) return;
11287
+
11288
+ for (var i = 0; i < self.visibleGroups.length; i++) {
11289
+ var g = self.visibleGroups[i];
11290
+ if (g.type !== 'r') continue;
11291
+ if (x >= g.x && y >= g.y && x <= g.x2 && y <= g.y2) return g;
11292
+ }
11293
+ };
9194
11294
  /**
9195
11295
  * Gets the cell at grid pixel coordinate x and y. Author's note. This function ties drawing and events together. This is a very complex function and is core to the component.
9196
11296
  * @memberof canvasDatagrid
@@ -9225,6 +11325,8 @@ __webpack_require__.r(__webpack_exports__);
9225
11325
  return;
9226
11326
  }
9227
11327
 
11328
+ x -= self.getRowGroupAreaWidth();
11329
+ y -= self.getColumnGroupAreaHeight();
9228
11330
  var border,
9229
11331
  tsz = useTouchScrollZones ? self.attributes.touchScrollZone : 0,
9230
11332
  moveMode = self.attributes.borderDragBehavior === 'move',