nexus site path corrected
[portal.git] / ecomp-portal-FE / client / bower_components / angular-smart-table / src / stTable.js
1 ng.module('smart-table')
2   .controller('stTableController', ['$scope', '$parse', '$filter', '$attrs', function StTableController ($scope, $parse, $filter, $attrs) {
3     var propertyName = $attrs.stTable;
4     var displayGetter = $parse(propertyName);
5     var displaySetter = displayGetter.assign;
6     var safeGetter;
7     var orderBy = $filter('orderBy');
8     var filter = $filter('filter');
9     var safeCopy = copyRefs(displayGetter($scope));
10     var tableState = {
11       sort: {},
12       search: {},
13       pagination: {
14         start: 0,
15         totalItemCount: 0
16       }
17     };
18     var filtered;
19     var pipeAfterSafeCopy = true;
20     var ctrl = this;
21     var lastSelected;
22
23     function copyRefs (src) {
24       return src ? [].concat(src) : [];
25     }
26
27     function updateSafeCopy () {
28       safeCopy = copyRefs(safeGetter($scope));
29       if (pipeAfterSafeCopy === true) {
30         ctrl.pipe();
31       }
32     }
33
34     function deepDelete (object, path) {
35       if (path.indexOf('.') != -1) {
36         var partials = path.split('.');
37         var key = partials.pop();
38         var parentPath = partials.join('.');
39         var parentObject = $parse(parentPath)(object)
40         delete parentObject[key];
41         if (Object.keys(parentObject).length == 0) {
42           deepDelete(object, parentPath);
43         }
44       } else {
45         delete object[path];
46       }
47     }
48
49     if ($attrs.stSafeSrc) {
50       safeGetter = $parse($attrs.stSafeSrc);
51       $scope.$watch(function () {
52         var safeSrc = safeGetter($scope);
53         return safeSrc && safeSrc.length ? safeSrc[0] : undefined;
54       }, function (newValue, oldValue) {
55         if (newValue !== oldValue) {
56           updateSafeCopy();
57         }
58       });
59       $scope.$watch(function () {
60         var safeSrc = safeGetter($scope);
61         return safeSrc ? safeSrc.length : 0;
62       }, function (newValue, oldValue) {
63         if (newValue !== safeCopy.length) {
64           updateSafeCopy();
65         }
66       });
67       $scope.$watch(function () {
68         return safeGetter($scope);
69       }, function (newValue, oldValue) {
70         if (newValue !== oldValue) {
71           tableState.pagination.start = 0;
72           updateSafeCopy();
73         }
74       });
75     }
76
77     /**
78      * sort the rows
79      * @param {Function | String} predicate - function or string which will be used as predicate for the sorting
80      * @param [reverse] - if you want to reverse the order
81      */
82     this.sortBy = function sortBy (predicate, reverse) {
83       tableState.sort.predicate = predicate;
84       tableState.sort.reverse = reverse === true;
85
86       if (ng.isFunction(predicate)) {
87         tableState.sort.functionName = predicate.name;
88       } else {
89         delete tableState.sort.functionName;
90       }
91
92       tableState.pagination.start = 0;
93       return this.pipe();
94     };
95
96     /**
97      * search matching rows
98      * @param {String} input - the input string
99      * @param {String} [predicate] - the property name against you want to check the match, otherwise it will search on all properties
100      */
101     this.search = function search (input, predicate) {
102       var predicateObject = tableState.search.predicateObject || {};
103       var prop = predicate ? predicate : '$';
104
105       input = ng.isString(input) ? input.trim() : input;
106       $parse(prop).assign(predicateObject, input);
107       // to avoid to filter out null value
108       if (!input) {
109         deepDelete(predicateObject, prop);
110       }
111       tableState.search.predicateObject = predicateObject;
112       tableState.pagination.start = 0;
113       return this.pipe();
114     };
115
116     /**
117      * this will chain the operations of sorting and filtering based on the current table state (sort options, filtering, ect)
118      */
119     this.pipe = function pipe () {
120       var pagination = tableState.pagination;
121       var output;
122       filtered = tableState.search.predicateObject ? filter(safeCopy, tableState.search.predicateObject) : safeCopy;
123       if (tableState.sort.predicate) {
124         filtered = orderBy(filtered, tableState.sort.predicate, tableState.sort.reverse);
125       }
126       pagination.totalItemCount = filtered.length;
127       if (pagination.number !== undefined) {
128         pagination.numberOfPages = filtered.length > 0 ? Math.ceil(filtered.length / pagination.number) : 1;
129         pagination.start = pagination.start >= filtered.length ? (pagination.numberOfPages - 1) * pagination.number : pagination.start;
130         output = filtered.slice(pagination.start, pagination.start + parseInt(pagination.number));
131       }
132       displaySetter($scope, output || filtered);
133     };
134
135     /**
136      * select a dataRow (it will add the attribute isSelected to the row object)
137      * @param {Object} row - the row to select
138      * @param {String} [mode] - "single" or "multiple" (multiple by default)
139      */
140     this.select = function select (row, mode) {
141       var rows = copyRefs(displayGetter($scope));
142       var index = rows.indexOf(row);
143       if (index !== -1) {
144         if (mode === 'single') {
145           row.isSelected = row.isSelected !== true;
146           if (lastSelected) {
147             lastSelected.isSelected = false;
148           }
149           lastSelected = row.isSelected === true ? row : undefined;
150         } else {
151           rows[index].isSelected = !rows[index].isSelected;
152         }
153       }
154     };
155
156     /**
157      * take a slice of the current sorted/filtered collection (pagination)
158      *
159      * @param {Number} start - start index of the slice
160      * @param {Number} number - the number of item in the slice
161      */
162     this.slice = function splice (start, number) {
163       tableState.pagination.start = start;
164       tableState.pagination.number = number;
165       return this.pipe();
166     };
167
168     /**
169      * return the current state of the table
170      * @returns {{sort: {}, search: {}, pagination: {start: number}}}
171      */
172     this.tableState = function getTableState () {
173       return tableState;
174     };
175
176     this.getFilteredCollection = function getFilteredCollection () {
177       return filtered || safeCopy;
178     };
179
180     /**
181      * Use a different filter function than the angular FilterFilter
182      * @param filterName the name under which the custom filter is registered
183      */
184     this.setFilterFunction = function setFilterFunction (filterName) {
185       filter = $filter(filterName);
186     };
187
188     /**
189      * Use a different function than the angular orderBy
190      * @param sortFunctionName the name under which the custom order function is registered
191      */
192     this.setSortFunction = function setSortFunction (sortFunctionName) {
193       orderBy = $filter(sortFunctionName);
194     };
195
196     /**
197      * Usually when the safe copy is updated the pipe function is called.
198      * Calling this method will prevent it, which is something required when using a custom pipe function
199      */
200     this.preventPipeOnWatch = function preventPipe () {
201       pipeAfterSafeCopy = false;
202     };
203   }])
204   .directive('stTable', function () {
205     return {
206       restrict: 'A',
207       controller: 'stTableController',
208       link: function (scope, element, attr, ctrl) {
209
210         if (attr.stSetFilter) {
211           ctrl.setFilterFunction(attr.stSetFilter);
212         }
213
214         if (attr.stSetSort) {
215           ctrl.setSortFunction(attr.stSetSort);
216         }
217       }
218     };
219   });