@everymatrix/stage-mm-verification-report 1.0.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.
- package/chunk-A3NTIEMP.js +1 -0
- package/chunk-CAY35YP7.js +7 -0
- package/chunk-H3QHLLCN.js +1 -0
- package/chunk-KE4BCZO4.js +851 -0
- package/chunk-OHPEWN32.js +1198 -0
- package/chunk-WSQOM5HU.js +1 -0
- package/component-lib.js +1 -0
- package/index.html +12 -0
- package/main.js +3264 -0
- package/modules/angular/LICENSE.md +21 -0
- package/modules/angular/README.md +67 -0
- package/modules/angular/angular-csp.css +25 -0
- package/modules/angular/angular.js +36600 -0
- package/modules/angular/angular.min.js +352 -0
- package/modules/angular/angular.min.js.gzip +0 -0
- package/modules/angular/angular.min.js.map +8 -0
- package/modules/angular/bower.json +9 -0
- package/modules/angular/index.js +2 -0
- package/modules/angular/package.json +25 -0
- package/modules/angular-ui-grid/CHANGELOG.md +1973 -0
- package/modules/angular-ui-grid/README.md +59 -0
- package/modules/angular-ui-grid/css/ui-grid.cellnav.css +25 -0
- package/modules/angular-ui-grid/css/ui-grid.cellnav.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.core.css +866 -0
- package/modules/angular-ui-grid/css/ui-grid.core.min.css +5 -0
- package/modules/angular-ui-grid/css/ui-grid.edit.css +23 -0
- package/modules/angular-ui-grid/css/ui-grid.edit.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.empty-base-layer.css +6 -0
- package/modules/angular-ui-grid/css/ui-grid.empty-base-layer.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.expandable.css +16 -0
- package/modules/angular-ui-grid/css/ui-grid.expandable.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.exporter.css +0 -0
- package/modules/angular-ui-grid/css/ui-grid.exporter.min.css +0 -0
- package/modules/angular-ui-grid/css/ui-grid.grouping.css +3 -0
- package/modules/angular-ui-grid/css/ui-grid.grouping.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.importer.css +0 -0
- package/modules/angular-ui-grid/css/ui-grid.importer.min.css +0 -0
- package/modules/angular-ui-grid/css/ui-grid.move-columns.css +9 -0
- package/modules/angular-ui-grid/css/ui-grid.move-columns.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.pagination.css +299 -0
- package/modules/angular-ui-grid/css/ui-grid.pagination.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.pinning.css +67 -0
- package/modules/angular-ui-grid/css/ui-grid.pinning.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.resize-columns.css +38 -0
- package/modules/angular-ui-grid/css/ui-grid.resize-columns.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.row-edit.css +9 -0
- package/modules/angular-ui-grid/css/ui-grid.row-edit.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.selection.css +25 -0
- package/modules/angular-ui-grid/css/ui-grid.selection.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.tree-base.css +4 -0
- package/modules/angular-ui-grid/css/ui-grid.tree-base.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.tree-view.css +6 -0
- package/modules/angular-ui-grid/css/ui-grid.tree-view.min.css +1 -0
- package/modules/angular-ui-grid/css/ui-grid.validate.css +3 -0
- package/modules/angular-ui-grid/css/ui-grid.validate.min.css +1 -0
- package/modules/angular-ui-grid/fonts/ui-grid.eot +0 -0
- package/modules/angular-ui-grid/fonts/ui-grid.svg +56 -0
- package/modules/angular-ui-grid/fonts/ui-grid.ttf +0 -0
- package/modules/angular-ui-grid/fonts/ui-grid.woff +0 -0
- package/modules/angular-ui-grid/less/animation.less +85 -0
- package/modules/angular-ui-grid/less/body.less +84 -0
- package/modules/angular-ui-grid/less/cell.less +46 -0
- package/modules/angular-ui-grid/less/cellnav.less +29 -0
- package/modules/angular-ui-grid/less/core.less +11 -0
- package/modules/angular-ui-grid/less/edit.less +27 -0
- package/modules/angular-ui-grid/less/elements.less +156 -0
- package/modules/angular-ui-grid/less/emptyBaseLayer.less +8 -0
- package/modules/angular-ui-grid/less/expandable.less +29 -0
- package/modules/angular-ui-grid/less/exporter.less +4 -0
- package/modules/angular-ui-grid/less/footer.less +76 -0
- package/modules/angular-ui-grid/less/grid.less +86 -0
- package/modules/angular-ui-grid/less/grouping.less +5 -0
- package/modules/angular-ui-grid/less/header.less +250 -0
- package/modules/angular-ui-grid/less/icons.less +151 -0
- package/modules/angular-ui-grid/less/importer.less +4 -0
- package/modules/angular-ui-grid/less/main.less +2 -0
- package/modules/angular-ui-grid/less/menu.less +91 -0
- package/modules/angular-ui-grid/less/moveColumns.less +12 -0
- package/modules/angular-ui-grid/less/pagination.less +297 -0
- package/modules/angular-ui-grid/less/pinning.less +86 -0
- package/modules/angular-ui-grid/less/resizeColumns.less +53 -0
- package/modules/angular-ui-grid/less/rowEdit.less +19 -0
- package/modules/angular-ui-grid/less/rtl.less +67 -0
- package/modules/angular-ui-grid/less/selection.less +29 -0
- package/modules/angular-ui-grid/less/sorting.less +16 -0
- package/modules/angular-ui-grid/less/treeBase.less +6 -0
- package/modules/angular-ui-grid/less/treeView.less +8 -0
- package/modules/angular-ui-grid/less/validate.less +5 -0
- package/modules/angular-ui-grid/less/variables.less +90 -0
- package/modules/angular-ui-grid/package.json +144 -0
- package/modules/angular-ui-grid/ui-grid.auto-resize.js +69 -0
- package/modules/angular-ui-grid/ui-grid.auto-resize.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.cellnav.js +1181 -0
- package/modules/angular-ui-grid/ui-grid.cellnav.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.core.js +12737 -0
- package/modules/angular-ui-grid/ui-grid.core.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.css +3208 -0
- package/modules/angular-ui-grid/ui-grid.edit.js +1325 -0
- package/modules/angular-ui-grid/ui-grid.edit.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.empty-base-layer.js +178 -0
- package/modules/angular-ui-grid/ui-grid.empty-base-layer.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.expandable.js +651 -0
- package/modules/angular-ui-grid/ui-grid.expandable.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.exporter.js +1777 -0
- package/modules/angular-ui-grid/ui-grid.exporter.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.grouping.js +1291 -0
- package/modules/angular-ui-grid/ui-grid.grouping.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.importer.js +791 -0
- package/modules/angular-ui-grid/ui-grid.importer.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.infinite-scroll.js +552 -0
- package/modules/angular-ui-grid/ui-grid.infinite-scroll.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.js +30867 -0
- package/modules/angular-ui-grid/ui-grid.language.all.js +3214 -0
- package/modules/angular-ui-grid/ui-grid.language.all.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.ar.js +118 -0
- package/modules/angular-ui-grid/ui-grid.language.ar.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.bg.js +115 -0
- package/modules/angular-ui-grid/ui-grid.language.bg.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.cs.js +96 -0
- package/modules/angular-ui-grid/ui-grid.language.cs.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.da.js +90 -0
- package/modules/angular-ui-grid/ui-grid.language.da.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.de.js +133 -0
- package/modules/angular-ui-grid/ui-grid.language.de.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.es-ct.js +133 -0
- package/modules/angular-ui-grid/ui-grid.language.es-ct.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.es.js +106 -0
- package/modules/angular-ui-grid/ui-grid.language.es.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.fa.js +93 -0
- package/modules/angular-ui-grid/ui-grid.language.fa.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.fi.js +76 -0
- package/modules/angular-ui-grid/ui-grid.language.fi.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.fr.js +128 -0
- package/modules/angular-ui-grid/ui-grid.language.fr.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.he.js +71 -0
- package/modules/angular-ui-grid/ui-grid.language.he.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.hy.js +76 -0
- package/modules/angular-ui-grid/ui-grid.language.hy.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.is.js +118 -0
- package/modules/angular-ui-grid/ui-grid.language.is.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.it.js +112 -0
- package/modules/angular-ui-grid/ui-grid.language.it.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.ja.js +118 -0
- package/modules/angular-ui-grid/ui-grid.language.ja.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.ko.js +77 -0
- package/modules/angular-ui-grid/ui-grid.language.ko.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.nl.js +91 -0
- package/modules/angular-ui-grid/ui-grid.language.nl.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.no.js +115 -0
- package/modules/angular-ui-grid/ui-grid.language.no.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.pl.js +126 -0
- package/modules/angular-ui-grid/ui-grid.language.pl.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.pt-br.js +133 -0
- package/modules/angular-ui-grid/ui-grid.language.pt-br.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.pt.js +133 -0
- package/modules/angular-ui-grid/ui-grid.language.pt.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.ro.js +112 -0
- package/modules/angular-ui-grid/ui-grid.language.ro.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.rs-lat.js +126 -0
- package/modules/angular-ui-grid/ui-grid.language.rs-lat.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.ru.js +115 -0
- package/modules/angular-ui-grid/ui-grid.language.ru.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.sk.js +127 -0
- package/modules/angular-ui-grid/ui-grid.language.sk.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.sv.js +126 -0
- package/modules/angular-ui-grid/ui-grid.language.sv.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.ta.js +87 -0
- package/modules/angular-ui-grid/ui-grid.language.ta.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.tr.js +112 -0
- package/modules/angular-ui-grid/ui-grid.language.tr.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.ua.js +112 -0
- package/modules/angular-ui-grid/ui-grid.language.ua.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.zh-cn.js +112 -0
- package/modules/angular-ui-grid/ui-grid.language.zh-cn.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.language.zh-tw.js +77 -0
- package/modules/angular-ui-grid/ui-grid.language.zh-tw.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.min.css +5 -0
- package/modules/angular-ui-grid/ui-grid.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.move-columns.js +582 -0
- package/modules/angular-ui-grid/ui-grid.move-columns.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.pagination.js +510 -0
- package/modules/angular-ui-grid/ui-grid.pagination.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.pinning.js +281 -0
- package/modules/angular-ui-grid/ui-grid.pinning.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.resize-columns.js +574 -0
- package/modules/angular-ui-grid/ui-grid.resize-columns.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.row-edit.js +717 -0
- package/modules/angular-ui-grid/ui-grid.row-edit.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.saveState.js +831 -0
- package/modules/angular-ui-grid/ui-grid.saveState.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.selection.js +1196 -0
- package/modules/angular-ui-grid/ui-grid.selection.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.tree-base.js +1743 -0
- package/modules/angular-ui-grid/ui-grid.tree-base.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.tree-view.js +218 -0
- package/modules/angular-ui-grid/ui-grid.tree-view.min.js +6 -0
- package/modules/angular-ui-grid/ui-grid.validate.js +589 -0
- package/modules/angular-ui-grid/ui-grid.validate.min.js +6 -0
- package/package.json +8 -0
- package/polyfills.js +2 -0
- package/styles.css +1 -0
|
@@ -0,0 +1,1291 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* ui-grid - v4.12.7 - 2024-04-12
|
|
3
|
+
* http://ui-grid.info/
|
|
4
|
+
* Copyright (c) 2024 ; License: MIT
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
(function () {
|
|
8
|
+
'use strict';
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* @ngdoc overview
|
|
12
|
+
* @name ui.grid.grouping
|
|
13
|
+
* @description
|
|
14
|
+
*
|
|
15
|
+
* # ui.grid.grouping
|
|
16
|
+
*
|
|
17
|
+
* <div class="alert alert-warning" role="alert"><strong>Beta</strong> This feature is ready for testing, but it either hasn't seen a lot of use or has some known bugs.</div>
|
|
18
|
+
*
|
|
19
|
+
* This module provides grouping of rows based on the data in them, similar
|
|
20
|
+
* in concept to excel grouping. You can group multiple columns, resulting in
|
|
21
|
+
* nested grouping.
|
|
22
|
+
*
|
|
23
|
+
* In concept this feature is similar to sorting + grid footer/aggregation, it
|
|
24
|
+
* sorts the data based on the grouped columns, then creates group rows that
|
|
25
|
+
* reflect a break in the data. Each of those group rows can have aggregations for
|
|
26
|
+
* the data within that group.
|
|
27
|
+
*
|
|
28
|
+
* This feature leverages treeBase to provide the tree functionality itself,
|
|
29
|
+
* the key thing this feature does therefore is to set treeLevels on the rows
|
|
30
|
+
* and insert the group headers.
|
|
31
|
+
*
|
|
32
|
+
* Design information:
|
|
33
|
+
* -------------------
|
|
34
|
+
*
|
|
35
|
+
* Each column will get new menu items - group by, and aggregate by. Group by
|
|
36
|
+
* will cause this column to be sorted (if not already), and will move this column
|
|
37
|
+
* to the front of the sorted columns (i.e. grouped columns take precedence over
|
|
38
|
+
* sorted columns). It will respect the sort order already set if there is one,
|
|
39
|
+
* and it will allow the sorting logic to change that sort order, it just forces
|
|
40
|
+
* the column to the front of the sorting. You can group by multiple columns, the
|
|
41
|
+
* logic will add this column to the sorting after any already grouped columns.
|
|
42
|
+
*
|
|
43
|
+
* Once a grouping is defined, grouping logic is added to the rowsProcessors. This
|
|
44
|
+
* will process the rows, identifying a break in the data value, and inserting a grouping row.
|
|
45
|
+
* Grouping rows have specific attributes on them:
|
|
46
|
+
*
|
|
47
|
+
* - internalRow = true: tells us that this isn't a real row, so we can ignore it
|
|
48
|
+
* from any processing that it looking at core data rows. This is used by the core
|
|
49
|
+
* logic (or will be one day), as it's not grouping specific
|
|
50
|
+
* - groupHeader = true: tells us this is a groupHeader. This is used by the grouping logic
|
|
51
|
+
* to know if this is a groupHeader row or not
|
|
52
|
+
*
|
|
53
|
+
* Since the logic is baked into the rowsProcessors, it should get triggered whenever
|
|
54
|
+
* row order or filtering or anything like that is changed. In order to avoid the row instantiation
|
|
55
|
+
* time, and to preserve state across invocations, we hold a cache of the rows that we created
|
|
56
|
+
* last time, and we use them again this time if we can.
|
|
57
|
+
*
|
|
58
|
+
* By default rows are collapsed, which means all data rows have their visible property
|
|
59
|
+
* set to false, and only level 0 group rows are set to visible.
|
|
60
|
+
*
|
|
61
|
+
* <br/>
|
|
62
|
+
* <br/>
|
|
63
|
+
*
|
|
64
|
+
* <div doc-module-components="ui.grid.grouping"></div>
|
|
65
|
+
*/
|
|
66
|
+
|
|
67
|
+
var module = angular.module('ui.grid.grouping', ['ui.grid', 'ui.grid.treeBase']);
|
|
68
|
+
|
|
69
|
+
/**
|
|
70
|
+
* @ngdoc object
|
|
71
|
+
* @name ui.grid.grouping.constant:uiGridGroupingConstants
|
|
72
|
+
*
|
|
73
|
+
* @description constants available in grouping module, this includes
|
|
74
|
+
* all the constants declared in the treeBase module (these are manually copied
|
|
75
|
+
* as there isn't an easy way to include constants in another constants file, and
|
|
76
|
+
* we don't want to make users include treeBase)
|
|
77
|
+
*
|
|
78
|
+
*/
|
|
79
|
+
module.constant('uiGridGroupingConstants', {
|
|
80
|
+
featureName: "grouping",
|
|
81
|
+
rowHeaderColName: 'treeBaseRowHeaderCol',
|
|
82
|
+
EXPANDED: 'expanded',
|
|
83
|
+
COLLAPSED: 'collapsed',
|
|
84
|
+
aggregation: {
|
|
85
|
+
COUNT: 'count',
|
|
86
|
+
SUM: 'sum',
|
|
87
|
+
MAX: 'max',
|
|
88
|
+
MIN: 'min',
|
|
89
|
+
AVG: 'avg'
|
|
90
|
+
}
|
|
91
|
+
});
|
|
92
|
+
|
|
93
|
+
/**
|
|
94
|
+
* @ngdoc service
|
|
95
|
+
* @name ui.grid.grouping.service:uiGridGroupingService
|
|
96
|
+
*
|
|
97
|
+
* @description Services for grouping features
|
|
98
|
+
*/
|
|
99
|
+
module.service('uiGridGroupingService', ['$q', 'uiGridGroupingConstants', 'gridUtil', 'rowSorter', 'GridRow', 'gridClassFactory', 'i18nService', 'uiGridConstants', 'uiGridTreeBaseService',
|
|
100
|
+
function ($q, uiGridGroupingConstants, gridUtil, rowSorter, GridRow, gridClassFactory, i18nService, uiGridConstants, uiGridTreeBaseService) {
|
|
101
|
+
var service = {
|
|
102
|
+
initializeGrid: function (grid, $scope) {
|
|
103
|
+
uiGridTreeBaseService.initializeGrid( grid, $scope );
|
|
104
|
+
|
|
105
|
+
// add feature namespace and any properties to grid for needed
|
|
106
|
+
/**
|
|
107
|
+
* @ngdoc object
|
|
108
|
+
* @name ui.grid.grouping.grid:grouping
|
|
109
|
+
*
|
|
110
|
+
* @description Grid properties and functions added for grouping
|
|
111
|
+
*/
|
|
112
|
+
grid.grouping = {};
|
|
113
|
+
|
|
114
|
+
/**
|
|
115
|
+
* @ngdoc property
|
|
116
|
+
* @propertyOf ui.grid.grouping.grid:grouping
|
|
117
|
+
* @name groupHeaderCache
|
|
118
|
+
*
|
|
119
|
+
* @description Cache that holds the group header rows we created last time, we'll
|
|
120
|
+
* reuse these next time, not least because they hold our expanded states.
|
|
121
|
+
*
|
|
122
|
+
* We need to take care with these that they don't become a memory leak, we
|
|
123
|
+
* create a new cache each time using the values from the old cache. This works
|
|
124
|
+
* so long as we're creating group rows for invisible rows as well.
|
|
125
|
+
*
|
|
126
|
+
* The cache is a nested hash, indexed on the value we grouped by. So if we
|
|
127
|
+
* grouped by gender then age, we'd maybe have something like:
|
|
128
|
+
* ```
|
|
129
|
+
* {
|
|
130
|
+
* male: {
|
|
131
|
+
* row: <pointer to the old row>,
|
|
132
|
+
* children: {
|
|
133
|
+
* 22: { row: <pointer to the old row> },
|
|
134
|
+
* 31: { row: <pointer to the old row> }
|
|
135
|
+
* },
|
|
136
|
+
* female: {
|
|
137
|
+
* row: <pointer to the old row>,
|
|
138
|
+
* children: {
|
|
139
|
+
* 28: { row: <pointer to the old row> },
|
|
140
|
+
* 55: { row: <pointer to the old row> }
|
|
141
|
+
* }
|
|
142
|
+
* }
|
|
143
|
+
* ```
|
|
144
|
+
*
|
|
145
|
+
* We create new rows for any missing rows, this means that they come in as collapsed.
|
|
146
|
+
*
|
|
147
|
+
*/
|
|
148
|
+
grid.grouping.groupHeaderCache = {};
|
|
149
|
+
|
|
150
|
+
service.defaultGridOptions(grid.options);
|
|
151
|
+
|
|
152
|
+
grid.registerRowsProcessor(service.groupRows, 400);
|
|
153
|
+
|
|
154
|
+
grid.registerColumnBuilder( service.groupingColumnBuilder);
|
|
155
|
+
|
|
156
|
+
grid.registerColumnsProcessor(service.groupingColumnProcessor, 400);
|
|
157
|
+
|
|
158
|
+
/**
|
|
159
|
+
* @ngdoc object
|
|
160
|
+
* @name ui.grid.grouping.api:PublicApi
|
|
161
|
+
*
|
|
162
|
+
* @description Public Api for grouping feature
|
|
163
|
+
*/
|
|
164
|
+
var publicApi = {
|
|
165
|
+
events: {
|
|
166
|
+
grouping: {
|
|
167
|
+
/**
|
|
168
|
+
* @ngdoc event
|
|
169
|
+
* @eventOf ui.grid.grouping.api:PublicApi
|
|
170
|
+
* @name aggregationChanged
|
|
171
|
+
* @description raised whenever aggregation is changed, added or removed from a column
|
|
172
|
+
*
|
|
173
|
+
* <pre>
|
|
174
|
+
* gridApi.grouping.on.aggregationChanged(scope,function(col) {})
|
|
175
|
+
* </pre>
|
|
176
|
+
* @param {GridColumn} col the column on which aggregation changed. The aggregation
|
|
177
|
+
* type is available as `col.treeAggregation.type`
|
|
178
|
+
*/
|
|
179
|
+
aggregationChanged: {},
|
|
180
|
+
/**
|
|
181
|
+
* @ngdoc event
|
|
182
|
+
* @eventOf ui.grid.grouping.api:PublicApi
|
|
183
|
+
* @name groupingChanged
|
|
184
|
+
* @description raised whenever the grouped columns changes
|
|
185
|
+
*
|
|
186
|
+
* <pre>
|
|
187
|
+
* gridApi.grouping.on.groupingChanged(scope,function(col) {})
|
|
188
|
+
* </pre>
|
|
189
|
+
* @param {GridColumn} col the column on which grouping changed. The new grouping is
|
|
190
|
+
* available as `col.grouping`
|
|
191
|
+
*/
|
|
192
|
+
groupingChanged: {}
|
|
193
|
+
}
|
|
194
|
+
},
|
|
195
|
+
methods: {
|
|
196
|
+
grouping: {
|
|
197
|
+
/**
|
|
198
|
+
* @ngdoc function
|
|
199
|
+
* @name getGrouping
|
|
200
|
+
* @methodOf ui.grid.grouping.api:PublicApi
|
|
201
|
+
* @description Get the grouping configuration for this grid,
|
|
202
|
+
* used by the saveState feature. Adds expandedState to the information
|
|
203
|
+
* provided by the internal getGrouping, and removes any aggregations that have a source
|
|
204
|
+
* of grouping (i.e. will be automatically reapplied when we regroup the column)
|
|
205
|
+
* Returned grouping is an object
|
|
206
|
+
* `{ grouping: groupArray, treeAggregations: aggregateArray, expandedState: hash }`
|
|
207
|
+
* where grouping contains an array of objects:
|
|
208
|
+
* `{ field: column.field, colName: column.name, groupPriority: column.grouping.groupPriority }`
|
|
209
|
+
* and aggregations contains an array of objects:
|
|
210
|
+
* `{ field: column.field, colName: column.name, aggregation: column.grouping.aggregation }`
|
|
211
|
+
* and expandedState is a hash of the currently expanded nodes
|
|
212
|
+
*
|
|
213
|
+
* The groupArray will be sorted by groupPriority.
|
|
214
|
+
*
|
|
215
|
+
* @param {boolean} getExpanded whether or not to return the expanded state
|
|
216
|
+
* @returns {object} grouping configuration
|
|
217
|
+
*/
|
|
218
|
+
getGrouping: function ( getExpanded ) {
|
|
219
|
+
var grouping = service.getGrouping(grid);
|
|
220
|
+
|
|
221
|
+
grouping.grouping.forEach( function( group ) {
|
|
222
|
+
group.colName = group.col.name;
|
|
223
|
+
delete group.col;
|
|
224
|
+
});
|
|
225
|
+
|
|
226
|
+
grouping.aggregations.forEach( function( aggregation ) {
|
|
227
|
+
aggregation.colName = aggregation.col.name;
|
|
228
|
+
delete aggregation.col;
|
|
229
|
+
});
|
|
230
|
+
|
|
231
|
+
grouping.aggregations = grouping.aggregations.filter( function( aggregation ) {
|
|
232
|
+
return !aggregation.aggregation.source || aggregation.aggregation.source !== 'grouping';
|
|
233
|
+
});
|
|
234
|
+
|
|
235
|
+
if ( getExpanded ) {
|
|
236
|
+
grouping.rowExpandedStates = service.getRowExpandedStates( grid.grouping.groupingHeaderCache );
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
return grouping;
|
|
240
|
+
},
|
|
241
|
+
|
|
242
|
+
/**
|
|
243
|
+
* @ngdoc function
|
|
244
|
+
* @name setGrouping
|
|
245
|
+
* @methodOf ui.grid.grouping.api:PublicApi
|
|
246
|
+
* @description Set the grouping configuration for this grid,
|
|
247
|
+
* used by the saveState feature, but can also be used by any
|
|
248
|
+
* user to specify a combined grouping and aggregation configuration
|
|
249
|
+
* @param {object} config the config you want to apply, in the format
|
|
250
|
+
* provided out by getGrouping
|
|
251
|
+
*/
|
|
252
|
+
setGrouping: function ( config ) {
|
|
253
|
+
service.setGrouping(grid, config);
|
|
254
|
+
},
|
|
255
|
+
|
|
256
|
+
/**
|
|
257
|
+
* @ngdoc function
|
|
258
|
+
* @name groupColumn
|
|
259
|
+
* @methodOf ui.grid.grouping.api:PublicApi
|
|
260
|
+
* @description Adds this column to the existing grouping, at the end of the priority order.
|
|
261
|
+
* If the column doesn't have a sort, adds one, by default ASC
|
|
262
|
+
*
|
|
263
|
+
* This column will move to the left of any non-group columns, the
|
|
264
|
+
* move is handled in a columnProcessor, so gets called as part of refresh
|
|
265
|
+
*
|
|
266
|
+
* @param {string} columnName the name of the column we want to group
|
|
267
|
+
*/
|
|
268
|
+
groupColumn: function(columnName) {
|
|
269
|
+
var column = grid.getColumn(columnName);
|
|
270
|
+
|
|
271
|
+
service.groupColumn(grid, column);
|
|
272
|
+
},
|
|
273
|
+
|
|
274
|
+
/**
|
|
275
|
+
* @ngdoc function
|
|
276
|
+
* @name ungroupColumn
|
|
277
|
+
* @methodOf ui.grid.grouping.api:PublicApi
|
|
278
|
+
* @description Removes the groupPriority from this column. If the
|
|
279
|
+
* column was previously aggregated the aggregation will come back.
|
|
280
|
+
* The sort will remain.
|
|
281
|
+
*
|
|
282
|
+
* This column will move to the right of any other group columns, the
|
|
283
|
+
* move is handled in a columnProcessor, so gets called as part of refresh
|
|
284
|
+
*
|
|
285
|
+
* @param {string} columnName the name of the column we want to ungroup
|
|
286
|
+
*/
|
|
287
|
+
ungroupColumn: function(columnName) {
|
|
288
|
+
var column = grid.getColumn(columnName);
|
|
289
|
+
|
|
290
|
+
service.ungroupColumn(grid, column);
|
|
291
|
+
},
|
|
292
|
+
|
|
293
|
+
/**
|
|
294
|
+
* @ngdoc function
|
|
295
|
+
* @name clearGrouping
|
|
296
|
+
* @methodOf ui.grid.grouping.api:PublicApi
|
|
297
|
+
* @description Clear any grouped columns and any aggregations. Doesn't remove sorting,
|
|
298
|
+
* as we don't know whether that sorting was added by grouping or was there beforehand
|
|
299
|
+
*
|
|
300
|
+
*/
|
|
301
|
+
clearGrouping: function() {
|
|
302
|
+
service.clearGrouping(grid);
|
|
303
|
+
},
|
|
304
|
+
|
|
305
|
+
/**
|
|
306
|
+
* @ngdoc function
|
|
307
|
+
* @name aggregateColumn
|
|
308
|
+
* @methodOf ui.grid.grouping.api:PublicApi
|
|
309
|
+
* @description Sets the aggregation type on a column, if the
|
|
310
|
+
* column is currently grouped then it removes the grouping first.
|
|
311
|
+
* If the aggregationDef is null then will result in the aggregation
|
|
312
|
+
* being removed
|
|
313
|
+
*
|
|
314
|
+
* @param {string} columnName the column we want to aggregate
|
|
315
|
+
* @param {string|function} aggregationDef one of the recognised types
|
|
316
|
+
* from uiGridGroupingConstants or a custom aggregation function.
|
|
317
|
+
* @param {string} aggregationLabel (optional) The label to use for this aggregation.
|
|
318
|
+
*/
|
|
319
|
+
aggregateColumn: function(columnName, aggregationDef, aggregationLabel) {
|
|
320
|
+
var column = grid.getColumn(columnName);
|
|
321
|
+
|
|
322
|
+
service.aggregateColumn(grid, column, aggregationDef, aggregationLabel);
|
|
323
|
+
}
|
|
324
|
+
}
|
|
325
|
+
}
|
|
326
|
+
};
|
|
327
|
+
|
|
328
|
+
grid.api.registerEventsFromObject(publicApi.events);
|
|
329
|
+
|
|
330
|
+
grid.api.registerMethodsFromObject(publicApi.methods);
|
|
331
|
+
|
|
332
|
+
grid.api.core.on.sortChanged($scope, service.tidyPriorities);
|
|
333
|
+
},
|
|
334
|
+
|
|
335
|
+
defaultGridOptions: function (gridOptions) {
|
|
336
|
+
// default option to true unless it was explicitly set to false
|
|
337
|
+
/**
|
|
338
|
+
* @ngdoc object
|
|
339
|
+
* @name ui.grid.grouping.api:GridOptions
|
|
340
|
+
*
|
|
341
|
+
* @description GridOptions for grouping feature, these are available to be
|
|
342
|
+
* set using the ui-grid {@link ui.grid.class:GridOptions gridOptions}
|
|
343
|
+
*/
|
|
344
|
+
|
|
345
|
+
/**
|
|
346
|
+
* @ngdoc object
|
|
347
|
+
* @name enableGrouping
|
|
348
|
+
* @propertyOf ui.grid.grouping.api:GridOptions
|
|
349
|
+
* @description Enable row grouping for entire grid.
|
|
350
|
+
* <br/>Defaults to true
|
|
351
|
+
*/
|
|
352
|
+
gridOptions.enableGrouping = gridOptions.enableGrouping !== false;
|
|
353
|
+
|
|
354
|
+
/**
|
|
355
|
+
* @ngdoc object
|
|
356
|
+
* @name groupingShowCounts
|
|
357
|
+
* @propertyOf ui.grid.grouping.api:GridOptions
|
|
358
|
+
* @description shows counts on the groupHeader rows. Not that if you are using a cellFilter or a
|
|
359
|
+
* sortingAlgorithm which relies on a specific format or data type, showing counts may cause that
|
|
360
|
+
* to break, since the group header rows will always be a string with groupingShowCounts enabled.
|
|
361
|
+
* <br/>Defaults to true except on columns of types 'date' and 'object'
|
|
362
|
+
*/
|
|
363
|
+
gridOptions.groupingShowCounts = gridOptions.groupingShowCounts !== false;
|
|
364
|
+
|
|
365
|
+
/**
|
|
366
|
+
* @ngdoc object
|
|
367
|
+
* @name groupingNullLabel
|
|
368
|
+
* @propertyOf ui.grid.grouping.api:GridOptions
|
|
369
|
+
* @description The string to use for the grouping header row label on rows which contain a null or undefined value in the grouped column.
|
|
370
|
+
* <br/>Defaults to "Null"
|
|
371
|
+
*/
|
|
372
|
+
gridOptions.groupingNullLabel = typeof(gridOptions.groupingNullLabel) === 'undefined' ? 'Null' : gridOptions.groupingNullLabel;
|
|
373
|
+
|
|
374
|
+
/**
|
|
375
|
+
* @ngdoc object
|
|
376
|
+
* @name enableGroupHeaderSelection
|
|
377
|
+
* @propertyOf ui.grid.grouping.api:GridOptions
|
|
378
|
+
* @description Allows group header rows to be selected.
|
|
379
|
+
* <br/>Defaults to false
|
|
380
|
+
*/
|
|
381
|
+
gridOptions.enableGroupHeaderSelection = gridOptions.enableGroupHeaderSelection === true;
|
|
382
|
+
},
|
|
383
|
+
|
|
384
|
+
|
|
385
|
+
/**
|
|
386
|
+
* @ngdoc function
|
|
387
|
+
* @name groupingColumnBuilder
|
|
388
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
389
|
+
* @description Sets the grouping defaults based on the columnDefs
|
|
390
|
+
*
|
|
391
|
+
* @param {object} colDef columnDef we're basing on
|
|
392
|
+
* @param {GridColumn} col the column we're to update
|
|
393
|
+
* @param {object} gridOptions the options we should use
|
|
394
|
+
* @returns {promise} promise for the builder - actually we do it all inline so it's immediately resolved
|
|
395
|
+
*/
|
|
396
|
+
groupingColumnBuilder: function (colDef, col, gridOptions) {
|
|
397
|
+
/**
|
|
398
|
+
* @ngdoc object
|
|
399
|
+
* @name ui.grid.grouping.api:ColumnDef
|
|
400
|
+
*
|
|
401
|
+
* @description ColumnDef for grouping feature, these are available to be
|
|
402
|
+
* set using the ui-grid {@link ui.grid.class:GridOptions.columnDef gridOptions.columnDefs}
|
|
403
|
+
*/
|
|
404
|
+
|
|
405
|
+
/**
|
|
406
|
+
* @ngdoc object
|
|
407
|
+
* @name enableGrouping
|
|
408
|
+
* @propertyOf ui.grid.grouping.api:ColumnDef
|
|
409
|
+
* @description Enable grouping on this column
|
|
410
|
+
* <br/>Defaults to true.
|
|
411
|
+
*/
|
|
412
|
+
if (colDef.enableGrouping === false) {
|
|
413
|
+
return;
|
|
414
|
+
}
|
|
415
|
+
|
|
416
|
+
/**
|
|
417
|
+
* @ngdoc object
|
|
418
|
+
* @name grouping
|
|
419
|
+
* @propertyOf ui.grid.grouping.api:ColumnDef
|
|
420
|
+
* @description Set the grouping for a column. Format is:
|
|
421
|
+
* ```
|
|
422
|
+
* {
|
|
423
|
+
* groupPriority: <number, starts at 0, if less than 0 or undefined then we're aggregating in this column>
|
|
424
|
+
* }
|
|
425
|
+
* ```
|
|
426
|
+
*
|
|
427
|
+
* **Note that aggregation used to be included in grouping, but is now separately set on the column via treeAggregation
|
|
428
|
+
* setting in treeBase**
|
|
429
|
+
*
|
|
430
|
+
* We group in the priority order given, this will also put these columns to the high order of the sort irrespective
|
|
431
|
+
* of the sort priority given them. If there is no sort defined then we sort ascending, if there is a sort defined then
|
|
432
|
+
* we use that sort.
|
|
433
|
+
*
|
|
434
|
+
* If the groupPriority is undefined or less than 0, then we expect to be aggregating, and we look at the
|
|
435
|
+
* aggregation types to determine what sort of aggregation we can do. Values are in the constants file, but
|
|
436
|
+
* include SUM, COUNT, MAX, MIN
|
|
437
|
+
*
|
|
438
|
+
* groupPriorities should generally be sequential, if they're not then the next time getGrouping is called
|
|
439
|
+
* we'll renumber them to be sequential.
|
|
440
|
+
* <br/>Defaults to undefined.
|
|
441
|
+
*/
|
|
442
|
+
|
|
443
|
+
if ( typeof(col.grouping) === 'undefined' && typeof(colDef.grouping) !== 'undefined') {
|
|
444
|
+
col.grouping = angular.copy(colDef.grouping);
|
|
445
|
+
if ( typeof(col.grouping.groupPriority) !== 'undefined' && col.grouping.groupPriority > -1 ) {
|
|
446
|
+
col.treeAggregationFn = uiGridTreeBaseService.nativeAggregations()[uiGridGroupingConstants.aggregation.COUNT].aggregationFn;
|
|
447
|
+
col.treeAggregationFinalizerFn = service.groupedFinalizerFn;
|
|
448
|
+
}
|
|
449
|
+
} else if (typeof(col.grouping) === 'undefined') {
|
|
450
|
+
col.grouping = {};
|
|
451
|
+
}
|
|
452
|
+
|
|
453
|
+
if (typeof(col.grouping) !== 'undefined' && typeof(col.grouping.groupPriority) !== 'undefined' && col.grouping.groupPriority >= 0) {
|
|
454
|
+
col.suppressRemoveSort = true;
|
|
455
|
+
}
|
|
456
|
+
|
|
457
|
+
var groupColumn = {
|
|
458
|
+
name: 'ui.grid.grouping.group',
|
|
459
|
+
title: i18nService.get().grouping.group,
|
|
460
|
+
icon: 'ui-grid-icon-indent-right',
|
|
461
|
+
shown: function () {
|
|
462
|
+
return typeof(this.context.col.grouping) === 'undefined' ||
|
|
463
|
+
typeof(this.context.col.grouping.groupPriority) === 'undefined' ||
|
|
464
|
+
this.context.col.grouping.groupPriority < 0;
|
|
465
|
+
},
|
|
466
|
+
action: function () {
|
|
467
|
+
service.groupColumn( this.context.col.grid, this.context.col );
|
|
468
|
+
}
|
|
469
|
+
};
|
|
470
|
+
|
|
471
|
+
var ungroupColumn = {
|
|
472
|
+
name: 'ui.grid.grouping.ungroup',
|
|
473
|
+
title: i18nService.get().grouping.ungroup,
|
|
474
|
+
icon: 'ui-grid-icon-indent-left',
|
|
475
|
+
shown: function () {
|
|
476
|
+
return typeof(this.context.col.grouping) !== 'undefined' &&
|
|
477
|
+
typeof(this.context.col.grouping.groupPriority) !== 'undefined' &&
|
|
478
|
+
this.context.col.grouping.groupPriority >= 0;
|
|
479
|
+
},
|
|
480
|
+
action: function () {
|
|
481
|
+
service.ungroupColumn( this.context.col.grid, this.context.col );
|
|
482
|
+
}
|
|
483
|
+
};
|
|
484
|
+
|
|
485
|
+
var aggregateRemove = {
|
|
486
|
+
name: 'ui.grid.grouping.aggregateRemove',
|
|
487
|
+
title: i18nService.get().grouping.aggregate_remove,
|
|
488
|
+
shown: function () {
|
|
489
|
+
return typeof(this.context.col.treeAggregationFn) !== 'undefined';
|
|
490
|
+
},
|
|
491
|
+
action: function () {
|
|
492
|
+
service.aggregateColumn( this.context.col.grid, this.context.col, null);
|
|
493
|
+
}
|
|
494
|
+
};
|
|
495
|
+
|
|
496
|
+
// generic adder for the aggregation menus, which follow a pattern
|
|
497
|
+
var addAggregationMenu = function(type, title) {
|
|
498
|
+
title = title || i18nService.get().grouping['aggregate_' + type] || type;
|
|
499
|
+
var menuItem = {
|
|
500
|
+
name: 'ui.grid.grouping.aggregate' + type,
|
|
501
|
+
title: title,
|
|
502
|
+
shown: function () {
|
|
503
|
+
return typeof(this.context.col.treeAggregation) === 'undefined' ||
|
|
504
|
+
typeof(this.context.col.treeAggregation.type) === 'undefined' ||
|
|
505
|
+
this.context.col.treeAggregation.type !== type;
|
|
506
|
+
},
|
|
507
|
+
action: function () {
|
|
508
|
+
service.aggregateColumn( this.context.col.grid, this.context.col, type);
|
|
509
|
+
}
|
|
510
|
+
};
|
|
511
|
+
|
|
512
|
+
if (!gridUtil.arrayContainsObjectWithProperty(col.menuItems, 'name', 'ui.grid.grouping.aggregate' + type)) {
|
|
513
|
+
col.menuItems.push(menuItem);
|
|
514
|
+
}
|
|
515
|
+
};
|
|
516
|
+
|
|
517
|
+
/**
|
|
518
|
+
* @ngdoc object
|
|
519
|
+
* @name groupingShowGroupingMenu
|
|
520
|
+
* @propertyOf ui.grid.grouping.api:ColumnDef
|
|
521
|
+
* @description Show the grouping (group and ungroup items) menu on this column
|
|
522
|
+
* <br/>Defaults to true.
|
|
523
|
+
*/
|
|
524
|
+
if ( col.colDef.groupingShowGroupingMenu !== false ) {
|
|
525
|
+
if (!gridUtil.arrayContainsObjectWithProperty(col.menuItems, 'name', 'ui.grid.grouping.group')) {
|
|
526
|
+
col.menuItems.push(groupColumn);
|
|
527
|
+
}
|
|
528
|
+
|
|
529
|
+
if (!gridUtil.arrayContainsObjectWithProperty(col.menuItems, 'name', 'ui.grid.grouping.ungroup')) {
|
|
530
|
+
col.menuItems.push(ungroupColumn);
|
|
531
|
+
}
|
|
532
|
+
}
|
|
533
|
+
|
|
534
|
+
|
|
535
|
+
/**
|
|
536
|
+
* @ngdoc object
|
|
537
|
+
* @name groupingShowAggregationMenu
|
|
538
|
+
* @propertyOf ui.grid.grouping.api:ColumnDef
|
|
539
|
+
* @description Show the aggregation menu on this column
|
|
540
|
+
* <br/>Defaults to true.
|
|
541
|
+
*/
|
|
542
|
+
if ( col.colDef.groupingShowAggregationMenu !== false ) {
|
|
543
|
+
angular.forEach(uiGridTreeBaseService.nativeAggregations(), function(aggregationDef, name) {
|
|
544
|
+
addAggregationMenu(name);
|
|
545
|
+
});
|
|
546
|
+
angular.forEach(gridOptions.treeCustomAggregations, function(aggregationDef, name) {
|
|
547
|
+
addAggregationMenu(name, aggregationDef.menuTitle);
|
|
548
|
+
});
|
|
549
|
+
|
|
550
|
+
if (!gridUtil.arrayContainsObjectWithProperty(col.menuItems, 'name', 'ui.grid.grouping.aggregateRemove')) {
|
|
551
|
+
col.menuItems.push(aggregateRemove);
|
|
552
|
+
}
|
|
553
|
+
}
|
|
554
|
+
},
|
|
555
|
+
|
|
556
|
+
|
|
557
|
+
|
|
558
|
+
|
|
559
|
+
/**
|
|
560
|
+
* @ngdoc function
|
|
561
|
+
* @name groupingColumnProcessor
|
|
562
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
563
|
+
* @description Moves the columns around based on which are grouped
|
|
564
|
+
*
|
|
565
|
+
* @param {array} columns the columns to consider rendering
|
|
566
|
+
* @param {array} rows the grid rows, which we don't use but are passed to us
|
|
567
|
+
* @returns {array} updated columns array
|
|
568
|
+
*/
|
|
569
|
+
groupingColumnProcessor: function( columns, rows ) {
|
|
570
|
+
columns = service.moveGroupColumns(this, columns, rows);
|
|
571
|
+
return columns;
|
|
572
|
+
},
|
|
573
|
+
|
|
574
|
+
/**
|
|
575
|
+
* @ngdoc function
|
|
576
|
+
* @name groupedFinalizerFn
|
|
577
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
578
|
+
* @description Used on group columns to display the rendered value and optionally
|
|
579
|
+
* display the count of rows.
|
|
580
|
+
*
|
|
581
|
+
* @param {aggregation} aggregation The aggregation entity for a grouped column
|
|
582
|
+
*/
|
|
583
|
+
groupedFinalizerFn: function( aggregation ) {
|
|
584
|
+
var col = this;
|
|
585
|
+
|
|
586
|
+
if ( typeof(aggregation.groupVal) !== 'undefined') {
|
|
587
|
+
aggregation.rendered = aggregation.groupVal;
|
|
588
|
+
if ( col.grid.options.groupingShowCounts && col.colDef.type !== 'date' && col.colDef.type !== 'object' ) {
|
|
589
|
+
aggregation.rendered += (' (' + aggregation.value + ')');
|
|
590
|
+
}
|
|
591
|
+
} else {
|
|
592
|
+
aggregation.rendered = null;
|
|
593
|
+
}
|
|
594
|
+
},
|
|
595
|
+
|
|
596
|
+
/**
|
|
597
|
+
* @ngdoc function
|
|
598
|
+
* @name moveGroupColumns
|
|
599
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
600
|
+
* @description Moves the column order so that the grouped columns are lined up
|
|
601
|
+
* to the left (well, unless you're RTL, then it's the right). By doing this in
|
|
602
|
+
* the columnsProcessor, we make it transient - when the column is ungrouped it'll
|
|
603
|
+
* go back to where it was.
|
|
604
|
+
*
|
|
605
|
+
* Does nothing if the option `moveGroupColumns` is set to false.
|
|
606
|
+
*
|
|
607
|
+
* @param {Grid} grid grid object
|
|
608
|
+
* @param {array} columns the columns that we should process/move
|
|
609
|
+
* @returns {array} updated columns
|
|
610
|
+
*/
|
|
611
|
+
moveGroupColumns: function( grid, columns ) {
|
|
612
|
+
if ( grid.options.moveGroupColumns === false) {
|
|
613
|
+
return columns;
|
|
614
|
+
}
|
|
615
|
+
|
|
616
|
+
columns.forEach(function(column, index) {
|
|
617
|
+
// position used to make stable sort in moveGroupColumns
|
|
618
|
+
column.groupingPosition = index;
|
|
619
|
+
});
|
|
620
|
+
|
|
621
|
+
columns.sort(function(a, b) {
|
|
622
|
+
var a_group, b_group;
|
|
623
|
+
|
|
624
|
+
if (a.isRowHeader) {
|
|
625
|
+
a_group = a.headerPriority;
|
|
626
|
+
}
|
|
627
|
+
else if ( typeof(a.grouping) === 'undefined' || typeof(a.grouping.groupPriority) === 'undefined' || a.grouping.groupPriority < 0) {
|
|
628
|
+
a_group = null;
|
|
629
|
+
}
|
|
630
|
+
else {
|
|
631
|
+
a_group = a.grouping.groupPriority;
|
|
632
|
+
}
|
|
633
|
+
|
|
634
|
+
if (b.isRowHeader) {
|
|
635
|
+
b_group = b.headerPriority;
|
|
636
|
+
}
|
|
637
|
+
else if ( typeof(b.grouping) === 'undefined' || typeof(b.grouping.groupPriority) === 'undefined' || b.grouping.groupPriority < 0) {
|
|
638
|
+
b_group = null;
|
|
639
|
+
}
|
|
640
|
+
else {
|
|
641
|
+
b_group = b.grouping.groupPriority;
|
|
642
|
+
}
|
|
643
|
+
|
|
644
|
+
// groups get sorted to the top
|
|
645
|
+
if ( a_group !== null && b_group === null) { return -1; }
|
|
646
|
+
if ( b_group !== null && a_group === null) { return 1; }
|
|
647
|
+
if ( a_group !== null && b_group !== null) {return a_group - b_group; }
|
|
648
|
+
|
|
649
|
+
return a.groupingPosition - b.groupingPosition;
|
|
650
|
+
});
|
|
651
|
+
|
|
652
|
+
columns.forEach( function(column) {
|
|
653
|
+
delete column.groupingPosition;
|
|
654
|
+
});
|
|
655
|
+
|
|
656
|
+
return columns;
|
|
657
|
+
},
|
|
658
|
+
|
|
659
|
+
|
|
660
|
+
/**
|
|
661
|
+
* @ngdoc function
|
|
662
|
+
* @name groupColumn
|
|
663
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
664
|
+
* @description Adds this column to the existing grouping, at the end of the priority order.
|
|
665
|
+
* If the column doesn't have a sort, adds one, by default ASC
|
|
666
|
+
*
|
|
667
|
+
* This column will move to the left of any non-group columns, the
|
|
668
|
+
* move is handled in a columnProcessor, so gets called as part of refresh
|
|
669
|
+
*
|
|
670
|
+
* @param {Grid} grid grid object
|
|
671
|
+
* @param {GridColumn} column the column we want to group
|
|
672
|
+
*/
|
|
673
|
+
groupColumn: function( grid, column) {
|
|
674
|
+
if ( typeof(column.grouping) === 'undefined' ) {
|
|
675
|
+
column.grouping = {};
|
|
676
|
+
}
|
|
677
|
+
|
|
678
|
+
// set the group priority to the next number in the hierarchy
|
|
679
|
+
var existingGrouping = service.getGrouping( grid );
|
|
680
|
+
column.grouping.groupPriority = existingGrouping.grouping.length;
|
|
681
|
+
|
|
682
|
+
// save sort in order to restore it when column is ungrouped
|
|
683
|
+
column.previousSort = angular.copy(column.sort);
|
|
684
|
+
|
|
685
|
+
// add sort if not present
|
|
686
|
+
if ( !column.sort ) {
|
|
687
|
+
column.sort = { direction: uiGridConstants.ASC };
|
|
688
|
+
} else if ( typeof(column.sort.direction) === 'undefined' || column.sort.direction === null ) {
|
|
689
|
+
column.sort.direction = uiGridConstants.ASC;
|
|
690
|
+
}
|
|
691
|
+
|
|
692
|
+
column.treeAggregation = { type: uiGridGroupingConstants.aggregation.COUNT, source: 'grouping' };
|
|
693
|
+
|
|
694
|
+
if ( column.colDef && angular.isFunction(column.colDef.customTreeAggregationFn) ) {
|
|
695
|
+
column.treeAggregationFn = column.colDef.customTreeAggregationFn;
|
|
696
|
+
} else {
|
|
697
|
+
column.treeAggregationFn = uiGridTreeBaseService.nativeAggregations()[uiGridGroupingConstants.aggregation.COUNT].aggregationFn;
|
|
698
|
+
}
|
|
699
|
+
|
|
700
|
+
column.treeAggregationFinalizerFn = service.groupedFinalizerFn;
|
|
701
|
+
|
|
702
|
+
grid.api.grouping.raise.groupingChanged(column);
|
|
703
|
+
// This indirectly calls service.tidyPriorities( grid );
|
|
704
|
+
grid.api.core.raise.sortChanged(grid, grid.getColumnSorting());
|
|
705
|
+
|
|
706
|
+
grid.queueGridRefresh();
|
|
707
|
+
},
|
|
708
|
+
|
|
709
|
+
|
|
710
|
+
/**
|
|
711
|
+
* @ngdoc function
|
|
712
|
+
* @name ungroupColumn
|
|
713
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
714
|
+
* @description Removes the groupPriority from this column. If the
|
|
715
|
+
* column was previously aggregated the aggregation will come back.
|
|
716
|
+
* The sort will remain.
|
|
717
|
+
*
|
|
718
|
+
* This column will move to the right of any other group columns, the
|
|
719
|
+
* move is handled in a columnProcessor, so gets called as part of refresh
|
|
720
|
+
*
|
|
721
|
+
* @param {Grid} grid grid object
|
|
722
|
+
* @param {GridColumn} column the column we want to ungroup
|
|
723
|
+
*/
|
|
724
|
+
ungroupColumn: function( grid, column) {
|
|
725
|
+
if ( typeof(column.grouping) === 'undefined' ) {
|
|
726
|
+
return;
|
|
727
|
+
}
|
|
728
|
+
|
|
729
|
+
delete column.grouping.groupPriority;
|
|
730
|
+
delete column.treeAggregation;
|
|
731
|
+
delete column.customTreeAggregationFinalizer;
|
|
732
|
+
|
|
733
|
+
if (column.previousSort) {
|
|
734
|
+
column.sort = column.previousSort;
|
|
735
|
+
delete column.previousSort;
|
|
736
|
+
}
|
|
737
|
+
|
|
738
|
+
service.tidyPriorities( grid );
|
|
739
|
+
|
|
740
|
+
grid.api.grouping.raise.groupingChanged(column);
|
|
741
|
+
grid.api.core.raise.sortChanged(grid, grid.getColumnSorting());
|
|
742
|
+
|
|
743
|
+
grid.queueGridRefresh();
|
|
744
|
+
},
|
|
745
|
+
|
|
746
|
+
/**
|
|
747
|
+
* @ngdoc function
|
|
748
|
+
* @name aggregateColumn
|
|
749
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
750
|
+
* @description Sets the aggregation type on a column, if the
|
|
751
|
+
* column is currently grouped then it removes the grouping first.
|
|
752
|
+
*
|
|
753
|
+
* @param {Grid} grid grid object
|
|
754
|
+
* @param {GridColumn} column the column we want to aggregate
|
|
755
|
+
* @param {string} aggregationType of the recognised types from uiGridGroupingConstants or one of the custom aggregations from gridOptions
|
|
756
|
+
* @param {string} aggregationLabel to be used instead of the default label. If empty string is passed, label is omitted
|
|
757
|
+
*/
|
|
758
|
+
aggregateColumn: function( grid, column, aggregationType, aggregationLabel ) {
|
|
759
|
+
if (typeof(column.grouping) !== 'undefined' && typeof(column.grouping.groupPriority) !== 'undefined' && column.grouping.groupPriority >= 0) {
|
|
760
|
+
service.ungroupColumn( grid, column );
|
|
761
|
+
}
|
|
762
|
+
|
|
763
|
+
var aggregationDef = {};
|
|
764
|
+
|
|
765
|
+
if ( typeof(grid.options.treeCustomAggregations[aggregationType]) !== 'undefined' ) {
|
|
766
|
+
aggregationDef = grid.options.treeCustomAggregations[aggregationType];
|
|
767
|
+
} else if ( typeof(uiGridTreeBaseService.nativeAggregations()[aggregationType]) !== 'undefined' ) {
|
|
768
|
+
aggregationDef = uiGridTreeBaseService.nativeAggregations()[aggregationType];
|
|
769
|
+
}
|
|
770
|
+
|
|
771
|
+
column.treeAggregation = {
|
|
772
|
+
type: aggregationType,
|
|
773
|
+
label: ( typeof aggregationLabel === 'string') ?
|
|
774
|
+
aggregationLabel :
|
|
775
|
+
i18nService.get().aggregation[aggregationDef.label] || aggregationDef.label
|
|
776
|
+
};
|
|
777
|
+
column.treeAggregationFn = aggregationDef.aggregationFn;
|
|
778
|
+
column.treeAggregationFinalizerFn = aggregationDef.finalizerFn;
|
|
779
|
+
|
|
780
|
+
grid.api.grouping.raise.aggregationChanged(column);
|
|
781
|
+
|
|
782
|
+
grid.queueGridRefresh();
|
|
783
|
+
},
|
|
784
|
+
|
|
785
|
+
|
|
786
|
+
/**
|
|
787
|
+
* @ngdoc function
|
|
788
|
+
* @name setGrouping
|
|
789
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
790
|
+
* @description Set the grouping based on a config object, used by the save state feature
|
|
791
|
+
* (more specifically, by the restore function in that feature )
|
|
792
|
+
*
|
|
793
|
+
* @param {Grid} grid grid object
|
|
794
|
+
* @param {object} config the config we want to set, same format as that returned by getGrouping
|
|
795
|
+
*/
|
|
796
|
+
setGrouping: function ( grid, config ) {
|
|
797
|
+
if ( typeof(config) === 'undefined' ) {
|
|
798
|
+
return;
|
|
799
|
+
}
|
|
800
|
+
|
|
801
|
+
// first remove any existing grouping
|
|
802
|
+
service.clearGrouping(grid);
|
|
803
|
+
|
|
804
|
+
if ( config.grouping && config.grouping.length && config.grouping.length > 0 ) {
|
|
805
|
+
config.grouping.forEach( function( group ) {
|
|
806
|
+
var col = grid.getColumn(group.colName);
|
|
807
|
+
|
|
808
|
+
if ( col ) {
|
|
809
|
+
service.groupColumn( grid, col );
|
|
810
|
+
}
|
|
811
|
+
});
|
|
812
|
+
}
|
|
813
|
+
|
|
814
|
+
if ( config.aggregations && config.aggregations.length ) {
|
|
815
|
+
config.aggregations.forEach( function( aggregation ) {
|
|
816
|
+
var col = grid.getColumn(aggregation.colName);
|
|
817
|
+
|
|
818
|
+
if ( col ) {
|
|
819
|
+
service.aggregateColumn( grid, col, aggregation.aggregation.type );
|
|
820
|
+
}
|
|
821
|
+
});
|
|
822
|
+
}
|
|
823
|
+
|
|
824
|
+
if ( config.rowExpandedStates ) {
|
|
825
|
+
service.applyRowExpandedStates( grid.grouping.groupingHeaderCache, config.rowExpandedStates );
|
|
826
|
+
}
|
|
827
|
+
},
|
|
828
|
+
|
|
829
|
+
|
|
830
|
+
/**
|
|
831
|
+
* @ngdoc function
|
|
832
|
+
* @name clearGrouping
|
|
833
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
834
|
+
* @description Clear any grouped columns and any aggregations. Doesn't remove sorting,
|
|
835
|
+
* as we don't know whether that sorting was added by grouping or was there beforehand
|
|
836
|
+
*
|
|
837
|
+
* @param {Grid} grid grid object
|
|
838
|
+
*/
|
|
839
|
+
clearGrouping: function( grid ) {
|
|
840
|
+
var currentGrouping = service.getGrouping(grid);
|
|
841
|
+
|
|
842
|
+
if ( currentGrouping.grouping.length > 0 ) {
|
|
843
|
+
currentGrouping.grouping.forEach( function( group ) {
|
|
844
|
+
if (!group.col) {
|
|
845
|
+
// should have a group.colName if there's no col
|
|
846
|
+
group.col = grid.getColumn(group.colName);
|
|
847
|
+
}
|
|
848
|
+
service.ungroupColumn(grid, group.col);
|
|
849
|
+
});
|
|
850
|
+
}
|
|
851
|
+
|
|
852
|
+
if ( currentGrouping.aggregations.length > 0 ) {
|
|
853
|
+
currentGrouping.aggregations.forEach( function( aggregation ) {
|
|
854
|
+
if (!aggregation.col) {
|
|
855
|
+
// should have a group.colName if there's no col
|
|
856
|
+
aggregation.col = grid.getColumn(aggregation.colName);
|
|
857
|
+
}
|
|
858
|
+
service.aggregateColumn(grid, aggregation.col, null);
|
|
859
|
+
});
|
|
860
|
+
}
|
|
861
|
+
},
|
|
862
|
+
|
|
863
|
+
|
|
864
|
+
/**
|
|
865
|
+
* @ngdoc function
|
|
866
|
+
* @name tidyPriorities
|
|
867
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
868
|
+
* @description Renumbers groupPriority and sortPriority such that
|
|
869
|
+
* groupPriority is contiguous, and sortPriority either matches
|
|
870
|
+
* groupPriority (for group columns), and otherwise is contiguous and
|
|
871
|
+
* higher than groupPriority.
|
|
872
|
+
*
|
|
873
|
+
* @param {Grid} grid grid object
|
|
874
|
+
*/
|
|
875
|
+
tidyPriorities: function( grid ) {
|
|
876
|
+
// if we're called from sortChanged, grid is in this, not passed as param, the param can be a column or undefined
|
|
877
|
+
if ( ( typeof(grid) === 'undefined' || typeof(grid.grid) !== 'undefined' ) && typeof(this.grid) !== 'undefined' ) {
|
|
878
|
+
grid = this.grid;
|
|
879
|
+
}
|
|
880
|
+
|
|
881
|
+
var groupArray = [],
|
|
882
|
+
sortArray = [];
|
|
883
|
+
|
|
884
|
+
grid.columns.forEach( function(column, index) {
|
|
885
|
+
if ( typeof(column.grouping) !== 'undefined' && typeof(column.grouping.groupPriority) !== 'undefined' && column.grouping.groupPriority >= 0) {
|
|
886
|
+
groupArray.push(column);
|
|
887
|
+
}
|
|
888
|
+
else if ( typeof(column.sort) !== 'undefined' && typeof(column.sort.priority) !== 'undefined' && column.sort.priority >= 0) {
|
|
889
|
+
sortArray.push(column);
|
|
890
|
+
}
|
|
891
|
+
});
|
|
892
|
+
|
|
893
|
+
groupArray.sort(function(a, b) { return a.grouping.groupPriority - b.grouping.groupPriority; });
|
|
894
|
+
groupArray.forEach( function(column, index) {
|
|
895
|
+
column.grouping.groupPriority = index;
|
|
896
|
+
column.suppressRemoveSort = true;
|
|
897
|
+
if ( typeof(column.sort) === 'undefined') {
|
|
898
|
+
column.sort = {};
|
|
899
|
+
}
|
|
900
|
+
column.sort.priority = index;
|
|
901
|
+
});
|
|
902
|
+
|
|
903
|
+
var i = groupArray.length;
|
|
904
|
+
|
|
905
|
+
sortArray.sort(function(a, b) { return a.sort.priority - b.sort.priority; });
|
|
906
|
+
sortArray.forEach(function(column) {
|
|
907
|
+
column.sort.priority = i;
|
|
908
|
+
column.suppressRemoveSort = column.colDef.suppressRemoveSort;
|
|
909
|
+
i++;
|
|
910
|
+
});
|
|
911
|
+
},
|
|
912
|
+
|
|
913
|
+
/**
|
|
914
|
+
* @ngdoc function
|
|
915
|
+
* @name groupRows
|
|
916
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
917
|
+
* @description The rowProcessor that creates the groupHeaders (i.e. does
|
|
918
|
+
* the actual grouping).
|
|
919
|
+
*
|
|
920
|
+
* Assumes it is always called after the sorting processor, guaranteed by the priority setting
|
|
921
|
+
*
|
|
922
|
+
* Processes all the rows in order, inserting a groupHeader row whenever there is a change
|
|
923
|
+
* in value of a grouped row, based on the sortAlgorithm used for the column. The group header row
|
|
924
|
+
* is looked up in the groupHeaderCache, and used from there if there is one. The entity is reset
|
|
925
|
+
* to {} if one is found.
|
|
926
|
+
*
|
|
927
|
+
* As it processes it maintains a `processingState` array. This records, for each level of grouping we're
|
|
928
|
+
* working with, the following information:
|
|
929
|
+
* ```
|
|
930
|
+
* {
|
|
931
|
+
* fieldName: name,
|
|
932
|
+
* col: col,
|
|
933
|
+
* initialised: boolean,
|
|
934
|
+
* currentValue: value,
|
|
935
|
+
* currentRow: gridRow,
|
|
936
|
+
* }
|
|
937
|
+
* ```
|
|
938
|
+
* We look for changes in the currentValue at any of the levels. Where we find a change we:
|
|
939
|
+
*
|
|
940
|
+
* - create a new groupHeader row in the array
|
|
941
|
+
*
|
|
942
|
+
* @param {array} renderableRows the rows we want to process, usually the output from the previous rowProcessor
|
|
943
|
+
* @returns {array} the updated rows, including our new group rows
|
|
944
|
+
*/
|
|
945
|
+
groupRows: function( renderableRows ) {
|
|
946
|
+
if (renderableRows.length === 0) {
|
|
947
|
+
return renderableRows;
|
|
948
|
+
}
|
|
949
|
+
|
|
950
|
+
var grid = this;
|
|
951
|
+
grid.grouping.oldGroupingHeaderCache = grid.grouping.groupingHeaderCache || {};
|
|
952
|
+
grid.grouping.groupingHeaderCache = {};
|
|
953
|
+
|
|
954
|
+
var processingState = service.initialiseProcessingState( grid );
|
|
955
|
+
|
|
956
|
+
// processes each of the fields we are grouping by, checks if the value has changed and inserts a groupHeader
|
|
957
|
+
// Broken out as shouldn't create functions in a loop.
|
|
958
|
+
var updateProcessingState = function( groupFieldState, stateIndex ) {
|
|
959
|
+
var fieldValue = grid.getCellValue(row, groupFieldState.col);
|
|
960
|
+
|
|
961
|
+
// look for change of value - and insert a header
|
|
962
|
+
if ( !groupFieldState.initialised || rowSorter.getSortFn(groupFieldState.col)(fieldValue, groupFieldState.currentValue) !== 0 ) {
|
|
963
|
+
service.insertGroupHeader( grid, renderableRows, i, processingState, stateIndex );
|
|
964
|
+
i++;
|
|
965
|
+
}
|
|
966
|
+
};
|
|
967
|
+
|
|
968
|
+
// use a for loop because it's tolerant of the array length changing whilst we go - we can
|
|
969
|
+
// manipulate the iterator when we insert groupHeader rows
|
|
970
|
+
for (var i = 0; i < renderableRows.length; i++ ) {
|
|
971
|
+
var row = renderableRows[i];
|
|
972
|
+
|
|
973
|
+
if ( row.visible ) {
|
|
974
|
+
processingState.forEach( updateProcessingState );
|
|
975
|
+
}
|
|
976
|
+
}
|
|
977
|
+
|
|
978
|
+
delete grid.grouping.oldGroupingHeaderCache;
|
|
979
|
+
return renderableRows;
|
|
980
|
+
},
|
|
981
|
+
|
|
982
|
+
|
|
983
|
+
/**
|
|
984
|
+
* @ngdoc function
|
|
985
|
+
* @name initialiseProcessingState
|
|
986
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
987
|
+
* @description Creates the processing state array that is used
|
|
988
|
+
* for groupRows.
|
|
989
|
+
*
|
|
990
|
+
* @param {Grid} grid grid object
|
|
991
|
+
* @returns {array} an array in the format described in the groupRows method,
|
|
992
|
+
* initialised with blank values
|
|
993
|
+
*/
|
|
994
|
+
initialiseProcessingState: function( grid ) {
|
|
995
|
+
var processingState = [];
|
|
996
|
+
var columnSettings = service.getGrouping( grid );
|
|
997
|
+
|
|
998
|
+
columnSettings.grouping.forEach( function( groupItem, index) {
|
|
999
|
+
processingState.push({
|
|
1000
|
+
fieldName: groupItem.field,
|
|
1001
|
+
col: groupItem.col,
|
|
1002
|
+
initialised: false,
|
|
1003
|
+
currentValue: null,
|
|
1004
|
+
currentRow: null
|
|
1005
|
+
});
|
|
1006
|
+
});
|
|
1007
|
+
|
|
1008
|
+
return processingState;
|
|
1009
|
+
},
|
|
1010
|
+
|
|
1011
|
+
|
|
1012
|
+
/**
|
|
1013
|
+
* @ngdoc function
|
|
1014
|
+
* @name getGrouping
|
|
1015
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
1016
|
+
* @description Get the grouping settings from the columns. As a side effect
|
|
1017
|
+
* this always renumbers the grouping starting at 0
|
|
1018
|
+
* @param {Grid} grid grid object
|
|
1019
|
+
* @returns {array} an array of the group fields, in order of priority
|
|
1020
|
+
*/
|
|
1021
|
+
getGrouping: function( grid ) {
|
|
1022
|
+
var groupArray = [],
|
|
1023
|
+
aggregateArray = [];
|
|
1024
|
+
|
|
1025
|
+
// get all the grouping
|
|
1026
|
+
grid.columns.forEach(function(column) {
|
|
1027
|
+
if ( column.grouping ) {
|
|
1028
|
+
if ( typeof(column.grouping.groupPriority) !== 'undefined' && column.grouping.groupPriority >= 0) {
|
|
1029
|
+
groupArray.push({ field: column.field, col: column, groupPriority: column.grouping.groupPriority, grouping: column.grouping });
|
|
1030
|
+
}
|
|
1031
|
+
}
|
|
1032
|
+
if ( column.treeAggregation && column.treeAggregation.type ) {
|
|
1033
|
+
aggregateArray.push({ field: column.field, col: column, aggregation: column.treeAggregation });
|
|
1034
|
+
}
|
|
1035
|
+
});
|
|
1036
|
+
|
|
1037
|
+
// sort grouping into priority order
|
|
1038
|
+
groupArray.sort( function(a, b) {
|
|
1039
|
+
return a.groupPriority - b.groupPriority;
|
|
1040
|
+
});
|
|
1041
|
+
|
|
1042
|
+
// renumber the priority in case it was somewhat messed up, then remove the grouping reference
|
|
1043
|
+
groupArray.forEach( function( group, index) {
|
|
1044
|
+
group.grouping.groupPriority = index;
|
|
1045
|
+
group.groupPriority = index;
|
|
1046
|
+
delete group.grouping;
|
|
1047
|
+
});
|
|
1048
|
+
|
|
1049
|
+
return { grouping: groupArray, aggregations: aggregateArray };
|
|
1050
|
+
},
|
|
1051
|
+
|
|
1052
|
+
|
|
1053
|
+
/**
|
|
1054
|
+
* @ngdoc function
|
|
1055
|
+
* @name insertGroupHeader
|
|
1056
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
1057
|
+
* @description Create a group header row, and link it to the various configuration
|
|
1058
|
+
* items that we use.
|
|
1059
|
+
*
|
|
1060
|
+
* Look for the row in the oldGroupingHeaderCache, write the row into the new groupingHeaderCache.
|
|
1061
|
+
*
|
|
1062
|
+
* @param {Grid} grid grid object
|
|
1063
|
+
* @param {array} renderableRows the rows that we are processing
|
|
1064
|
+
* @param {number} rowIndex the row we were up to processing
|
|
1065
|
+
* @param {array} processingState the current processing state
|
|
1066
|
+
* @param {number} stateIndex the processing state item that we were on when we triggered a new group header -
|
|
1067
|
+
* i.e. the column that we want to create a header for
|
|
1068
|
+
*/
|
|
1069
|
+
insertGroupHeader: function( grid, renderableRows, rowIndex, processingState, stateIndex ) {
|
|
1070
|
+
// set the value that caused the end of a group into the header row and the processing state
|
|
1071
|
+
var col = processingState[stateIndex].col,
|
|
1072
|
+
newValue = grid.getCellValue(renderableRows[rowIndex], col),
|
|
1073
|
+
newDisplayValue = newValue;
|
|
1074
|
+
|
|
1075
|
+
if ( typeof(newValue) === 'undefined' || newValue === null ) {
|
|
1076
|
+
newDisplayValue = grid.options.groupingNullLabel;
|
|
1077
|
+
}
|
|
1078
|
+
|
|
1079
|
+
function getKeyAsValueForCacheMap(key) {
|
|
1080
|
+
return angular.isObject(key) ? JSON.stringify(key) : key;
|
|
1081
|
+
}
|
|
1082
|
+
|
|
1083
|
+
var cacheItem = grid.grouping.oldGroupingHeaderCache;
|
|
1084
|
+
|
|
1085
|
+
for ( var i = 0; i < stateIndex; i++ ) {
|
|
1086
|
+
if ( cacheItem && cacheItem[getKeyAsValueForCacheMap(processingState[i].currentValue)] ) {
|
|
1087
|
+
cacheItem = cacheItem[getKeyAsValueForCacheMap(processingState[i].currentValue)].children;
|
|
1088
|
+
}
|
|
1089
|
+
}
|
|
1090
|
+
|
|
1091
|
+
var headerRow;
|
|
1092
|
+
|
|
1093
|
+
if ( cacheItem && cacheItem[getKeyAsValueForCacheMap(newValue)]) {
|
|
1094
|
+
headerRow = cacheItem[getKeyAsValueForCacheMap(newValue)].row;
|
|
1095
|
+
headerRow.entity = {};
|
|
1096
|
+
} else {
|
|
1097
|
+
headerRow = new GridRow( {}, null, grid );
|
|
1098
|
+
gridClassFactory.rowTemplateAssigner.call(grid, headerRow);
|
|
1099
|
+
}
|
|
1100
|
+
|
|
1101
|
+
headerRow.entity['$$' + processingState[stateIndex].col.uid] = { groupVal: newDisplayValue };
|
|
1102
|
+
headerRow.treeLevel = stateIndex;
|
|
1103
|
+
headerRow.groupHeader = true;
|
|
1104
|
+
headerRow.internalRow = true;
|
|
1105
|
+
headerRow.enableCellEdit = false;
|
|
1106
|
+
headerRow.enableSelection = grid.options.enableGroupHeaderSelection;
|
|
1107
|
+
processingState[stateIndex].initialised = true;
|
|
1108
|
+
processingState[stateIndex].currentValue = newValue;
|
|
1109
|
+
processingState[stateIndex].currentRow = headerRow;
|
|
1110
|
+
|
|
1111
|
+
// set all processing states below this one to not be initialised - change of this state
|
|
1112
|
+
// means all those need to start again
|
|
1113
|
+
service.finaliseProcessingState( processingState, stateIndex + 1);
|
|
1114
|
+
|
|
1115
|
+
// insert our new header row
|
|
1116
|
+
renderableRows.splice(rowIndex, 0, headerRow);
|
|
1117
|
+
|
|
1118
|
+
// add our new header row to the cache
|
|
1119
|
+
cacheItem = grid.grouping.groupingHeaderCache;
|
|
1120
|
+
for ( i = 0; i < stateIndex; i++ ) {
|
|
1121
|
+
cacheItem = cacheItem[getKeyAsValueForCacheMap(processingState[i].currentValue)].children;
|
|
1122
|
+
}
|
|
1123
|
+
cacheItem[getKeyAsValueForCacheMap(newValue)] = { row: headerRow, children: {} };
|
|
1124
|
+
},
|
|
1125
|
+
|
|
1126
|
+
|
|
1127
|
+
/**
|
|
1128
|
+
* @ngdoc function
|
|
1129
|
+
* @name finaliseProcessingState
|
|
1130
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
1131
|
+
* @description Set all processing states lower than the one that had a break in value to
|
|
1132
|
+
* no longer be initialised. Render the counts into the entity ready for display.
|
|
1133
|
+
*
|
|
1134
|
+
* @param {array} processingState the current processing state
|
|
1135
|
+
* @param {number} stateIndex the processing state item that we were on when we triggered a new group header, all
|
|
1136
|
+
* processing states after this need to be finalised
|
|
1137
|
+
*/
|
|
1138
|
+
finaliseProcessingState: function( processingState, stateIndex ) {
|
|
1139
|
+
for ( var i = stateIndex; i < processingState.length; i++) {
|
|
1140
|
+
processingState[i].initialised = false;
|
|
1141
|
+
processingState[i].currentRow = null;
|
|
1142
|
+
processingState[i].currentValue = null;
|
|
1143
|
+
}
|
|
1144
|
+
},
|
|
1145
|
+
|
|
1146
|
+
|
|
1147
|
+
/**
|
|
1148
|
+
* @ngdoc function
|
|
1149
|
+
* @name getRowExpandedStates
|
|
1150
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
1151
|
+
* @description Extract the groupHeaderCache hash, pulling out only the states.
|
|
1152
|
+
*
|
|
1153
|
+
* The example below shows a grid that is grouped by gender then age
|
|
1154
|
+
*
|
|
1155
|
+
* <pre>
|
|
1156
|
+
* {
|
|
1157
|
+
* male: {
|
|
1158
|
+
* state: 'expanded',
|
|
1159
|
+
* children: {
|
|
1160
|
+
* 22: { state: 'expanded' },
|
|
1161
|
+
* 30: { state: 'collapsed' }
|
|
1162
|
+
* }
|
|
1163
|
+
* },
|
|
1164
|
+
* female: {
|
|
1165
|
+
* state: 'expanded',
|
|
1166
|
+
* children: {
|
|
1167
|
+
* 28: { state: 'expanded' },
|
|
1168
|
+
* 55: { state: 'collapsed' }
|
|
1169
|
+
* }
|
|
1170
|
+
* }
|
|
1171
|
+
* }
|
|
1172
|
+
* </pre>
|
|
1173
|
+
*
|
|
1174
|
+
* @param {object} treeChildren The tree children elements object
|
|
1175
|
+
* @returns {object} the expanded states as an object
|
|
1176
|
+
*/
|
|
1177
|
+
getRowExpandedStates: function(treeChildren) {
|
|
1178
|
+
if ( typeof(treeChildren) === 'undefined' ) {
|
|
1179
|
+
return {};
|
|
1180
|
+
}
|
|
1181
|
+
|
|
1182
|
+
var newChildren = {};
|
|
1183
|
+
|
|
1184
|
+
angular.forEach( treeChildren, function( value, key ) {
|
|
1185
|
+
newChildren[key] = { state: value.row.treeNode.state };
|
|
1186
|
+
if ( value.children ) {
|
|
1187
|
+
newChildren[key].children = service.getRowExpandedStates( value.children );
|
|
1188
|
+
} else {
|
|
1189
|
+
newChildren[key].children = {};
|
|
1190
|
+
}
|
|
1191
|
+
});
|
|
1192
|
+
|
|
1193
|
+
return newChildren;
|
|
1194
|
+
},
|
|
1195
|
+
|
|
1196
|
+
|
|
1197
|
+
/**
|
|
1198
|
+
* @ngdoc function
|
|
1199
|
+
* @name applyRowExpandedStates
|
|
1200
|
+
* @methodOf ui.grid.grouping.service:uiGridGroupingService
|
|
1201
|
+
* @description Take a hash in the format as created by getRowExpandedStates,
|
|
1202
|
+
* and apply it to the grid.grouping.groupHeaderCache.
|
|
1203
|
+
*
|
|
1204
|
+
* Takes a treeSubset, and applies to a treeSubset - so can be called
|
|
1205
|
+
* recursively.
|
|
1206
|
+
*
|
|
1207
|
+
* @param {object} currentNode can be grid.grouping.groupHeaderCache, or any of
|
|
1208
|
+
* the children of that hash
|
|
1209
|
+
* @param {object} expandedStates can be the full expanded states, or children
|
|
1210
|
+
* of that expanded states (which hopefully matches the subset of the groupHeaderCache)
|
|
1211
|
+
*/
|
|
1212
|
+
applyRowExpandedStates: function( currentNode, expandedStates ) {
|
|
1213
|
+
if ( typeof(expandedStates) === 'undefined' ) {
|
|
1214
|
+
return;
|
|
1215
|
+
}
|
|
1216
|
+
|
|
1217
|
+
angular.forEach(expandedStates, function( value, key ) {
|
|
1218
|
+
if ( currentNode[key] ) {
|
|
1219
|
+
currentNode[key].row.treeNode.state = value.state;
|
|
1220
|
+
|
|
1221
|
+
if (value.children && currentNode[key].children) {
|
|
1222
|
+
service.applyRowExpandedStates( currentNode[key].children, value.children );
|
|
1223
|
+
}
|
|
1224
|
+
}
|
|
1225
|
+
});
|
|
1226
|
+
}
|
|
1227
|
+
|
|
1228
|
+
|
|
1229
|
+
};
|
|
1230
|
+
|
|
1231
|
+
return service;
|
|
1232
|
+
|
|
1233
|
+
}]);
|
|
1234
|
+
|
|
1235
|
+
|
|
1236
|
+
/**
|
|
1237
|
+
* @ngdoc directive
|
|
1238
|
+
* @name ui.grid.grouping.directive:uiGridGrouping
|
|
1239
|
+
* @element div
|
|
1240
|
+
* @restrict A
|
|
1241
|
+
*
|
|
1242
|
+
* @description Adds grouping features to grid
|
|
1243
|
+
*
|
|
1244
|
+
* @example
|
|
1245
|
+
<example module="app">
|
|
1246
|
+
<file name="app.js">
|
|
1247
|
+
var app = angular.module('app', ['ui.grid', 'ui.grid.grouping']);
|
|
1248
|
+
|
|
1249
|
+
app.controller('MainCtrl', ['$scope', function ($scope) {
|
|
1250
|
+
$scope.data = [
|
|
1251
|
+
{ name: 'Bob', title: 'CEO' },
|
|
1252
|
+
{ name: 'Frank', title: 'Lowly Developer' }
|
|
1253
|
+
];
|
|
1254
|
+
|
|
1255
|
+
$scope.columnDefs = [
|
|
1256
|
+
{name: 'name', enableCellEdit: true},
|
|
1257
|
+
{name: 'title', enableCellEdit: true}
|
|
1258
|
+
];
|
|
1259
|
+
|
|
1260
|
+
$scope.gridOptions = { columnDefs: $scope.columnDefs, data: $scope.data };
|
|
1261
|
+
}]);
|
|
1262
|
+
</file>
|
|
1263
|
+
<file name="index.html">
|
|
1264
|
+
<div ng-controller="MainCtrl">
|
|
1265
|
+
<div ui-grid="gridOptions" ui-grid-grouping></div>
|
|
1266
|
+
</div>
|
|
1267
|
+
</file>
|
|
1268
|
+
</example>
|
|
1269
|
+
*/
|
|
1270
|
+
module.directive('uiGridGrouping', ['uiGridGroupingConstants', 'uiGridGroupingService',
|
|
1271
|
+
function (uiGridGroupingConstants, uiGridGroupingService) {
|
|
1272
|
+
return {
|
|
1273
|
+
replace: true,
|
|
1274
|
+
priority: 0,
|
|
1275
|
+
require: '^uiGrid',
|
|
1276
|
+
scope: false,
|
|
1277
|
+
compile: function () {
|
|
1278
|
+
return {
|
|
1279
|
+
pre: function ($scope, $elm, $attrs, uiGridCtrl) {
|
|
1280
|
+
if (uiGridCtrl.grid.options.enableGrouping !== false) {
|
|
1281
|
+
uiGridGroupingService.initializeGrid(uiGridCtrl.grid, $scope);
|
|
1282
|
+
}
|
|
1283
|
+
},
|
|
1284
|
+
post: function ($scope, $elm, $attrs, uiGridCtrl) {
|
|
1285
|
+
}
|
|
1286
|
+
};
|
|
1287
|
+
}
|
|
1288
|
+
};
|
|
1289
|
+
}]);
|
|
1290
|
+
|
|
1291
|
+
})();
|