UNPKG

pure-angular-advanced-searchbox

Version:
2,147 lines (1,170 loc) 107 kB
'use strict'; angular.module('paasb', [ 'paasb.config' ]); 'use strict'; angular.module('paasb.config', []) .constant('FILTERS', {SELECTORS:[{name:'Contains',key:'contains',selected:true,notAllowed:['restrictedSuggestedValues']},{name:'Does not contain',key:'doesNotContain',notAllowed:['restrictedSuggestedValues']},{name:'Is Equal To',key:'isEqualTo'},{name:'Is Not Equal To',key:'isNotEqualTo'},{name:'Starts with',key:'startsWith'},{name:'Ends with',key:'endsWith'},{name:'Similiarity',key:'similiarity'}],OPERATORS:[{name:'AND',selected:true},{name:'OR'}]}) ; 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbAutoSize * @description * # Implementation of paasbAutoSize */ angular.module('paasb') .directive('paasbAutoSize', [ '$parse', '$window', '$timeout', 'paasbUtils', function ($parse, $window, $timeout, paasbUtils) { return { 'restrict': 'A', controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var filter = null, Filtering = null, type = $attrs.paasbAutoSizeType; $attrs.$observe('paasbAutoSize', function () { filter = $parse($attrs.paasbAutoSize)($scope) || {}; Filtering = filter.$$filtering || {}; angular .element($element) .ready(function () { if(type) { return Filtering.addAutoSizeElementToFilter(filter, $element, type); } }); }); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbDraggable * @description * # Implementation of paasbDraggable */ angular.module('paasb') .directive('paasbDraggable', [ 'paasbUtils', function (paasbUtils) { return { 'restrict': 'A', controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { $element.on('dragstart dragend', function (ev) { switch(ev.type) { case 'dragstart': var elem = angular.element(this), id = paasbUtils.uuid(), data = { 'id': id, 'draggable': true, 'trash': true }; if(!elem.attr('id')) { elem.attr('id', id); } ev.dataTransfer.setData('text', JSON.stringify(data)); break; case 'dragend': if($scope.Search && $scope.Search.Filtering) { var Filtering = $scope.Search.Filtering; Filtering .removeClassAllFilters('over-placement-1') .removeClassAllFilters('over-placement-2') .removeClassAllFilters('over-placement-3') .removeClassAllFilters('dragged-item'); } break; } }); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxAddedFilter * @description * # Implementation of paasbSearchBoxAddedFilter */ angular.module('paasb') .directive('paasbSearchBoxAddedFilter', [ '$timeout', '$document', 'paasbUi', 'paasbUtils', function ($timeout, $document, paasbUi, paasbUtils) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-added-filter.html', 'require': '^paasbSearchBoxFiltering', 'scope': { 'filter': '=', 'filtering': '=', 'toValue': '=', 'operators': '=' }, controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var Filtering = $scope.filtering, Grouping = Filtering.getGrouping(), EventHandling = Filtering.getEventHandler(), filter = $scope.filter, operators = $scope.operators, config = null, input, dragSourceElem = null, dragSourceCount = 0; angular.extend(filter, { 'loading': false, '$$filtering': Filtering }); $element.attr('id', paasbUtils.uuid()); if(typeof filter.suggestedValues === 'string') { config = Filtering.getConfig(); var deepValue = paasbUtils.getDeepValue(config, filter.suggestedValues); if(deepValue) { filter.suggestedValues = deepValue; } } if($scope.toValue) { $scope.value = $scope.toValue; $scope.dontOpen = true; } if(paasbUtils.isURL(filter.suggestedValues) || (paasbUtils.isURL(filter.source) && filter.reloadOnCreate)) { paasbUi.safeApply($scope, function () { var url = filter.source || filter.suggestedValues; angular.extend(filter, { 'loading': true, 'suggestedValues': [], 'source': url }); }); Filtering .loadSource(filter) .then(function (data) { paasbUi.safeApply($scope, function () { angular.extend(filter, { 'suggestedValues': data, 'loading': false, 'value': '' }); }); }); } else { filter.value = ''; } var scope = Filtering.getFilterScope(filter); angular.extend(scope, { enableGrouping: function () { $document.on('mouseover mouseout', $scope.events.groupingEvents); }, disableGrouping: function () { $document.off('mouseover mouseout', $scope.events.groupingEvents); } }); paasbUi.extend($scope, { 'inputId': paasbUtils.uuid(), 'Utils': paasbUtils, getDirection: function (placement) { var dir = null; if(typeof placement === 'undefined' || placement === null) { return dir; } if(typeof placement === 'string') { placement = parseInt(placement); } switch(placement) { case 1: dir = 'before'; break; case 3: dir = 'after'; break; } return dir; }, 'events': { groupingEvents: function (ev) { var isChild = $element[0].contains(ev.target), isSelf = $element[0] == ev.target, isInside = isChild || isSelf; switch(ev.type) { case 'mouseover': if(isInside) { Grouping.addFake($element); } break; case 'mouseout': if(!isInside) { Grouping.removeLastFake(); } break; } }, searchboxClick: function (ev) { var isChild = $element[0].contains(ev.target), isSelf = $element[0] == ev.target, isInside = isChild || isSelf; if(!isInside) { $scope.closeFilter(); } }, inputKeyEvents: function (ev) { if(ev.keyCode === 13) { $scope.closeFilter(); } }, dragEvents: function (ev) { switch(ev.type) { case 'dragstart': dragSourceElem = angular.element(this); ev.dataTransfer.effectAllowed = 'copyMove'; if(!dragSourceElem.attr('id')) { dragSourceElem.attr('id', paasbUtils.uuid()); } ev.dataTransfer.setData('text', dragSourceElem.attr('id')); dragSourceElem.addClass('dragged-item'); break; case 'dragenter': ev.preventDefault(); dragSourceCount ++; break; case 'dragleave': dragSourceCount --; if(dragSourceCount === 0) { angular.element(this).removeClass('over'); } break; case 'dragover': var bounding = this.getBoundingClientRect(), w = (bounding.width / 3); var placement = Math.abs(Math.ceil((ev.pageX - bounding.left) / w)) || 1; Filtering .removeClassAllFilters('over-placement-1') .removeClassAllFilters('over-placement-2') .removeClassAllFilters('over-placement-3'); angular .element(this) .addClass('over-placement-' + placement) .attr('data-placement', placement); if(ev.preventDefault) { ev.preventDefault(); } ev.dataTransfer.dropEffect = 'copyMove'; return false; break; case 'drop': if(ev.stopPropagation) { ev.stopPropagation(); } var data = ev.dataTransfer.getData('text'), isJSON = false; if(paasbUtils.isJson(data)) { data = JSON.parse(data); isJSON = true; } if(data) { var id = data; if(isJSON) { id = data.id; } var elem = document.getElementById(id); if(isJSON && data.draggable) { if(data.trash) { Filtering.removeByElement(this); } } else { if(elem !== this) { var placement = parseInt(angular .element(this) .attr('data-placement') || null), direction = $scope.getDirection(placement); Filtering[placement === 2 ? 'swapFilter' : 'moveFilter'](elem, this, direction); } } } return false; break; case 'dragend': Filtering .removeClassAllFilters('over-placement-1') .removeClassAllFilters('over-placement-2') .removeClassAllFilters('over-placement-3') .removeClassAllFilters('dragged-item'); break; } } }, takeSuggestion: function (val) { $scope.value = val; }, closeFilter: function () { var self = this; paasbUi.safeApply($scope, function () { filter.editing = false; $scope.$broadcast('filter.isEditing', filter.editing); $document.unbind('click', self.events.searchboxClick); if(!filter.value) { Filtering.remove(filter, true); } else { if(filter.suggestedValue) { console.log(filter.suggestedValue, $scope.value, filter.$$lastValue); $scope.value = filter.suggestedValue.value; } else { if(filter.restrictedSuggestedValues) { Filtering.remove(filter, true); } } } EventHandling .onLeavedEditMode(filter); }); }, openFilter: function () { if(!$scope.dontOpen) { var self = this; if(!filter.editing) { filter.editing = true; $scope.$broadcast('filter.isEditing', filter.editing); $timeout(function () { $document.bind('click', self.events.searchboxClick); }, 25); $scope.setFocus(); EventHandling .onEnteredEditMode(filter); } } $scope.dontOpen = false; }, destroy: function () { return Filtering.remove($scope.filter, null, false); }, getElements: function () { input = $element.find('input'); filter.$$input = input; return $scope; }, registerEvents: function (events) { input.on('keyup', events.inputKeyEvents); $element.on('dragstart dragenter dragover dragleave drop dragend', events.dragEvents); return $scope; }, setFocus: function () { $timeout(function () { if(input) { input[0].focus(); } }, 50); return $scope; }, addWatch: function () { $scope.$watch('value', function (__new, __old) { Filtering.autoSizeByFilter(filter); filter.value = __new || ''; if(filter.value) { if(__new !== __old) { if(filter && filter.suggestedValues) { if(filter.suggestedValue && filter.suggestedValue.value === filter.$$lastValue) { return; } var matchesSuggestedValue = false; angular.forEach(filter.suggestedValues, function (suggestedValue) { if(suggestedValue === __new) { matchesSuggestedValue = true; } }); if(matchesSuggestedValue) { filter.$$lastValue = filter.value; Filtering.update(); EventHandling .onFilterChanged(filter); } } else { Filtering.update(); EventHandling .onFilterChanged(filter); } } } }); return $scope; } }); $scope .getElements() .registerEvents($scope.events) .addWatch() .openFilter(); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxAutoComplete * @description * # Implementation of paasbSearchBoxAutoComplete */ angular.module('paasb') .directive('paasbSearchBoxAutoComplete', [ '$window', '$document', '$timeout', '$interpolate', 'paasbUi', 'paasbUtils', 'paasbAutoComplete', 'paasbMemory', function ($window, $document, $timeout, $interpolate, paasbUi, paasbUtils, paasbAutoComplete, paasbMemory) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-auto-complete.html', 'require': '^paasbSearchBox', 'scope': { 'query': '=', 'config': '=', 'input': '=' }, controller: ['$scope', '$element', function ($scope, $element) { var config = $scope.config, initialQuery = paasbMemory.getAndSet('query'); $scope.$watch('query', function (__new) { if($scope.tookSuggestion !== __new) { $scope.tookSuggestion = null; if(__new && (initialQuery !== __new)) { paasbAutoComplete .load($interpolate(config.autoCompleteUrl)({ 'query': __new })) .then(function (data) { paasbUi.extend($scope, { 'autoSuggestions': data, 'showSuggestions': (data && data.length) ? true : false }); $scope.position(); }); } } }); angular.extend($scope, { 'Utils': paasbUtils, 'tookSuggestion': null, 'showSuggestions': false, autoCompleteClick: function (ev) { var tgt = ev.target, elem = $element[0]; if(!elem.contains(tgt)) { paasbUi.extend($scope, { 'showSuggestions': false }); } $document.unbind('click', $scope.autoCompleteClick); }, position: function () { $timeout(function () { var input = $scope.input[0], inputPadding = paasbUtils.getStyle(input, 'padding-left'), inputWidth = paasbUtils.getStyle(input, 'width') - paasbUtils.getStyle(input, 'padding-right') - inputPadding; $element .css('left', inputPadding + 'px') .css('width', inputWidth + 'px'); }); }, takeAutoComplete: function (suggestion) { paasbUi.extend($scope, { 'showSuggestions': false, 'tookSuggestion': suggestion }); $scope.$emit('take.autoSuggestion', suggestion); $document.unbind('click', $scope.autoCompleteClick); }, registerEvents: function () { angular .element($window) .on('resize', function () { $scope.position(); }); $scope.$on('input.focused', function () { if($scope.autoSuggestions && $scope.autoSuggestions.length) { paasbUi.extend($scope, { 'showSuggestions': true }); } }); $scope.$watch('showSuggestions', function (__new) { if(__new) { $document.bind('mousedown', $scope.autoCompleteClick); } }); return $scope; } }); $scope .registerEvents(); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxAutoSuggestions * @description * # Implementation of paasbSearchBoxAutoSuggestions */ angular.module('paasb') .directive('paasbSearchBoxAutoSuggestions', [ function () { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-auto-suggestions.html', 'require': '^paasbSearchBoxAddedFilter', 'scope': { 'filtering': '=', 'filter': '=' }, controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var Filtering = $scope.filtering, filter = $scope.filter; }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxCacheFilter * @description * # Implementation of paasbSearchBoxCacheFilter */ angular.module('paasb') .directive('paasbSearchBoxCacheFilter', [ 'paasbMemory', 'paasbUi', function (paasbMemory, paasbUi) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-cache-filters.html', 'require': '^paasbSearchBox', controller: ['$scope', function ($scope) { paasbUi.extend($scope, { 'cacheActive': paasbMemory.getAndSet('cache') || false, handleCache: function () { if(!$scope.paasbSearchBoxCacheFilterPermanent) { $scope.cacheActive = !$scope.cacheActive; paasbMemory.getAndSet('cache', $scope.cacheActive); } } }); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxFilterMovedAnimation * @description * # Implementation of paasbSearchBoxFilterMovedAnimation */ angular.module('paasb') .directive('paasbSearchBoxFilterMovedAnimation', [ 'paasbUtils', 'paasbUi', function (paasbUtils, paasbUi) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-filter-moved-animation.html', 'require': '^paasbSearchBoxAddedFilter', 'scope': { 'filter': '=' }, controller: ['$scope', '$element', function ($scope, $element) { var filter = $scope.filter, contents = $element.parent(), elem = null, boundingBox = null, height = 0, width = 0, radius = 0; if(filter) { elem = filter.element; boundingBox = contents[0].getBoundingClientRect(); radius = paasbUtils.getStyle(contents[0], 'border-radius') || 0; height = (boundingBox.bottom - boundingBox.top); width = (boundingBox.width); var hWidth = (width / 2) + 6; var hHeight = (height / 2) + 6; $element .css('border-left-width', hWidth + 'px') .css('border-right-width', hWidth + 'px') .css('border-top-width', hHeight + 'px') .css('border-bottom-width', hHeight + 'px') .css('border-radius', radius + 'px'); paasbUi.apply(function () { $element .addClass('transition') .css('border-left-width', '0px') .css('border-right-width', '0px') .css('border-top-width', '0px') .css('border-bottom-width', '0px') .css('border-radius', radius + 'px') .css('width', width + 'px') .css('height', height + 'px'); }, 50); } }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxFilterMoved * @description * # Implementation of paasbSearchBoxFilterMoved */ angular.module('paasb') .directive('paasbSearchBoxFilterMoved', [ '$parse', '$compile', function ($parse, $compile) { return { 'restrict': 'A', controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var filter = null; $scope.hasRecentlyMoved = function () { if(filter && filter.recentlyMoved) { var scope = $scope.$new(true), compiledTemplate = null; angular.extend(scope, { 'filter': filter }); compiledTemplate = $compile('<paasb-search-box-filter-moved-animation filter="filter" />')(scope); $element.prepend(compiledTemplate); } delete filter.recentlyMoved; }; $attrs.$observe('paasbSearchBoxFilterMoved', function () { filter = $parse($attrs.paasbSearchBoxFilterMoved)($scope); angular .element($element) .ready(function () { $scope.hasRecentlyMoved(); }); }); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxFilterOperators * @description * # Implementation of paasbSearchBoxFilterOperators */ angular.module('paasb') .directive('paasbSearchBoxFilterOperators', [ '$document', 'paasbUi', 'FILTERS', function ($document, paasbUi, FILTERS) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-filter-operators.html', 'require': '^paasbSearchBoxAddedFilter', 'scope': { 'filtering': '=', 'filter': '=' }, controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var Filtering = $scope.filtering, EventHandling = Filtering.getEventHandler(), operators = angular.copy(FILTERS.OPERATORS), filter = $scope.filter; if(Filtering.getFilterCount() > 1) { $scope.hasOperator = true; $scope.autoSizeElement = $element; angular.extend($scope, { 'availableOperators': operators, 'showOperators': false, 'events': { docClick: function (ev) { var isChild = $element[0].contains(ev.target); var isSelf = $element[0] == ev.target; var isInside = isChild || isSelf; if(!isInside) { $document.unbind('click', $scope.events.docClick); paasbUi.extend($scope, { 'showOperators': false }); } } }, openOperators: function () { $scope.showOperators = !$scope.showOperators; $document[$scope.showOperators ? 'bind': 'unbind']('click', $scope.events.docClick); Filtering.autoSizeByFilter(filter); }, takeOperator: function (operator) { angular.forEach(operators, function (availableOperator) { availableOperator.selected = false; }); $scope.operator = operator; Filtering.addOperatorToFilter(operator, filter); EventHandling .onOperatorChanged(operator, filter); operator.selected = true; }, takeOperatorByName: function (operatorName) { angular.forEach(operators, function (availableOperator) { if(availableOperator.name !== operatorName) { availableOperator.selected = false; } else { availableOperator.selected = true; $scope.operator = availableOperator; } }); }, setDefaultOperator: function () { var operatorByFilter = Filtering.getOperatorByFilterIndex(filter); if(operatorByFilter === null) { if(!filter.operator) { angular.forEach(operators, function (availableOperator) { if(availableOperator.selected) { $scope.operator = availableOperator; } }); if(!filter.selector && operators && operators.length) { var operator = operators[0]; operator.selected = true; $scope.operator = operator; } } else { angular.forEach(operators, function (availableOperator) { availableOperator.selected = (availableOperator.key === filter.selector.key); }); } } else { this.takeOperatorByName(operatorByFilter); } return $scope; }, registerOperator: function () { Filtering.registerOperator($scope); return $scope; }, addOperatorToFilter: function () { if(!Filtering.hasOperatorAlready(filter)) { Filtering.addOperatorToFilter($scope.operator, filter, true); } return $scope; } }); $scope .setDefaultOperator() .registerOperator() .addOperatorToFilter(); } }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxFilterSelectors * @description * # Implementation of paasbSearchBoxFilterSelectors */ angular.module('paasb') .directive('paasbSearchBoxFilterSelectors', [ 'FILTERS', function (FILTERS) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-filter-selectors.html', 'require': '^paasbSearchBoxAddedFilter', 'scope': { 'filtering': '=', 'filter': '=' }, controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var Filtering = $scope.filtering, EventHandling = Filtering.getEventHandler(), copy = angular.copy(FILTERS.SELECTORS), filter = $scope.filter; $scope.autoSizeElement = $element; angular.extend($scope, { 'availableSelectors': null, takeSelector: function (selector) { angular.forEach($scope.availableSelectors, function (availableSelector) { availableSelector.selected = false; }); filter.selector = selector; selector.selected = true; if(filter.value) { Filtering.update(); EventHandling .onFilterSelectorChanged(selector, filter); } Filtering.autoSizeByFilter(filter); var input = filter.element.find('input')[0]; input.focus(); }, setDefaultSelector: function () { if(!filter.selector) { angular.forEach($scope.availableSelectors, function (availableSelector) { if(availableSelector.selected) { filter.selector = availableSelector; } }); if(!filter.selector && $scope.availableSelectors && $scope.availableSelectors.length) { var selector = $scope.availableSelectors[0]; selector.selected = true; filter.selector = selector; } } else { angular.forEach($scope.availableSelectors, function (availableSelector) { availableSelector.selected = (availableSelector.key === filter.selector.key); }); } return $scope; }, setAvailableSelectors: function () { var availableSelectors = []; angular.forEach(copy, function (selector) { var allowed = true; angular.forEach(selector.notAllowed, function (notAllowed) { if(filter[notAllowed]) { allowed = false; } }); if(allowed) { availableSelectors.push(selector); } }); $scope.availableSelectors = availableSelectors; return $scope; } }); $scope.$on('filter.isEditing', function (ev, editing) { if(editing) { Filtering.autoSizeByFilter(filter); } }); $scope .setAvailableSelectors() .setDefaultSelector(); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxFiltering * @description * # Implementation of paasbSearchBoxFiltering */ angular.module('paasb') .directive('paasbSearchBoxFiltering', [ '$document', '$timeout', '$window', 'paasbUtils', 'paasbUi', function ($document, $timeout, $window, paasbUtils, paasbUi) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-filtering.html', 'require': '^paasbSearchBox', 'scope': { 'filters': '=', 'search': '=' }, controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var Search = null; $scope.$watch('active', function (__new, __old) { if(__new && !$scope.windowClickedFn) { $timeout(function () { $scope.windowClickedFn = $document.on('click', $scope.windowClicked); }, 25); } else { if($scope.windowClickedFn) { $document.off('click', $scope.windowClicked); $scope.windowClickedFn = null; } } }); angular.extend($scope, { 'active': false, 'Utils': paasbUtils, windowClicked: function (ev) { var target = ev.target, elem = $element[0]; if(!elem.contains(target)) { paasbUi.extend($scope, { 'active': false }); } }, position: function () { if($scope.active) { $timeout(function () { var el = $element.parent(), list = $element.find('ul'), listBoundingBox = list[0].getBoundingClientRect(), elBoundingBox = el[0].getBoundingClientRect(); list .css('top', (elBoundingBox.height - 5) + 'px') .css('width', (elBoundingBox.width + paasbUtils.getStyle(el[0], 'padding-right') + paasbUtils.getStyle(el[0], 'padding-left') - paasbUtils.getScrollbarWidth() / 2) + 'px'); }, 25); } }, toggleFilters: function () { paasbUi.extend($scope, { 'active': !$scope.active }); this.position(); }, addFilterAndClose: function (filter) { Search.Filtering.add(filter); paasbUi.extend($scope, { 'active': !$scope.active }); }, registerEvents: function () { angular .element($window) .on('resize', function () { $scope.position(); }); }, addFilter: function (ev) { var self = this, target = paasbUtils.getParentByAttribute(ev.target, 'li', 'data-filter-name'), filterName = target.attr('data-filter-name'); angular.forEach($scope.filters, function (filter) { if(filter.name === filterName) { if(filter.restrictedSuggestedValues) { self.addFilterAndClose(filter); } else { if(!filter.multi) { filter.notFiltered = !filter.notFiltered; if(!filter.notFiltered) { self.addFilterAndClose(filter); } } else { self.addFilterAndClose(filter); } } } }); } }); $scope.$watch('search', function (__new, __old) { if((__new !== __old) && angular.isObject(__new)) { Search = __new; $scope.filters = angular.copy($scope.filters); $scope.filters .slice() .reverse() .forEach(function (filter, filterIndex, filterObject) { filter.notFiltered = true; if(filter.root) { filter.filteredFrom = '<i class="fa fa-level-up"></i> (Derived from ' + 'Root <i class="fa fa-angle-double-right"></i> ' + filter.root + ')'; } if(filter.child) { filter.filteredFrom = '<i class="fa fa-level-down"></i> (Derived from ' + filter.child + ')'; } if(filter.dontFilter) { $scope.filters.splice(filterObject.length - 1 - filterIndex, 1); } }); $scope .registerEvents(); } }); }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBoxGrouping * @description * # Implementation of paasbSearchBoxGrouping */ angular.module('paasb') .directive('paasbSearchBoxGrouping', [ function () { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox-grouping.html', 'require': '^paasbSearchBox', controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var Grouper = null; if($scope.Search && $scope.Search.Grouper) { Grouper = $scope.Search.Grouper; angular.extend($scope, { toggleGrouping: function () { return Grouper.toggle(); } }); } }] }; }]); 'use strict'; /** * @ngdoc directive * @name paasb.directive:paasbSearchBox * @description * # Implementation of paasbSearchBox */ angular.module('paasb') .directive('paasbSearchBox', [ '$timeout', '$window', 'paasbApi', 'paasbUi', 'paasbFiltering', 'paasbGrouping', 'paasbPlaceholders', 'paasbEventHandling', 'paasbMemory', 'paasbUtils', 'FILTERS', function ($timeout, $window, paasbApi, paasbUi, paasbFiltering, paasbGrouping, paasbPlaceholders, paasbEventHandling, paasbMemory, paasbUtils, FILTERS) { return { 'restrict': 'E', 'replace': true, 'templateUrl': 'views/directives/searchbox.html', 'scope': { 'searchParams': '=?', 'paasbSearchBoxFiltering': '=?', 'paasbSearchBoxConfig': '=?', 'paasbSearchBoxAutoComplete': '=?', 'paasbSearchBoxCacheFilter': '=?', 'paasbSearchBoxEnableFilteringOperators': '=?', 'paasbSearchBoxFilterSelectors': '=?', 'paasbSearchBoxFilterOperators': '=?', 'paasbSearchBoxEnableGrouping': '=?', 'placeholder': '@' }, controller: ['$scope', '$element', '$attrs', function ($scope, $element, $attrs) { var params = null, config = null, autoComplete = null, Filterer = null, Grouper = null, Placeholding = null, API = null, EventHandling = null, timer = null, searchBox = { 'searchInputId': ('searchInput-' + paasbUtils.uuid()), hasAutoCompleteConfigurations: function () { return config && config.autoCompleteUrl; }, make: function (name, extend, method, related) { var val = $scope[name]; if(angular[method]) { if(!angular[method](val)) { if(method === 'isObject') { $scope[name] = angular.extend({}, extend); } else { $scope[name] = extend; } } else { if(extend && _.isEmpty(val)) { $scope[name] = extend; $scope[related] = extend[related]; } } } else { if(this[method]) { val = this[method](val); } } return this; }, 'events': { handleEraser: function () { $scope.query = ''; EventHandling .onEraser(); }, handleSearch: function () { EventHandling .onChange(params); }, handleGarbage: function () { if((params.query && params.query.length) || $scope.hasFilters) { Filterer.removeAll(true, true, { 'deleteOperators': true }); $scope.query = ''; EventHandling .onGarbage(); } } }, shouldStore: function () { return (paasbMemory.getAndSet('cache') || config.store) ? true : false; }, configure: function () { var defaultParams = { 'query': '', 'filters': {} }, configuredParams = {}; if($scope.paasbSearchBoxEnableFilteringOperators) { angular.extend(defaultParams, { 'operators': [] }); } if(FILTERS && FILTERS.SELECTORS && $scope.paasbSearchBoxFilterSelectors) { FILTERS.SELECTORS = $scope.paasbSearchBoxFilterSelectors; } if(FILTERS && FILTERS.OPERATORS && $scope.paasbSearchBoxFilterOperators) { FILTERS.OPERATORS = $scope.paasbSearchBoxFilterOperators; } this .make('paasbSearchBoxFiltering', [], 'isArray') .make('paasbSearchBoxConfig', {}, 'isObject') .make('paasbSearchBoxAutoComplete', {}, 'isObject'); config = $scope.paasbSearchBoxConfig; if(this.shouldStore()) { configuredParams = paasbMemory.getAll(); if(_.isEmpty(configuredParams)) { configuredParams = defaultParams; } } else { configuredParams = defaultParams; } this .make('searchParams', configuredParams, 'isObject', 'query'); params = $scope.searchParams; autoComplete = $scope.paasbSearchBoxAutoComplete; $scope.autoCompleteEnabled = this.hasAutoCompleteConfigurations(); if($scope.query) { paasbUi.extend($scope, {