UNPKG

generator-gsndnn

Version:

Scaffolds DNN extensions, including Modules (Webforms, SPA, and MVC), Persona Bar, Skin Object, Library, Scheduler, and Hotcakes Commerce projects (based on the generator built by Matt Rutledge).

1,522 lines (1,327 loc) 294 kB
/* * angular-ui-bootstrap * http://angular-ui.github.io/bootstrap/ * Version: 0.14.3 - 2015-10-23 * License: MIT */ angular.module("ui.bootstrap", ["ui.bootstrap.tpls", "ui.bootstrap.collapse","ui.bootstrap.accordion","ui.bootstrap.alert","ui.bootstrap.buttons","ui.bootstrap.carousel","ui.bootstrap.dateparser","ui.bootstrap.position","ui.bootstrap.datepicker","ui.bootstrap.dropdown","ui.bootstrap.stackedMap","ui.bootstrap.modal","ui.bootstrap.pagination","ui.bootstrap.tooltip","ui.bootstrap.popover","ui.bootstrap.progressbar","ui.bootstrap.rating","ui.bootstrap.tabs","ui.bootstrap.timepicker","ui.bootstrap.typeahead"]); angular.module("ui.bootstrap.tpls", ["template/accordion/accordion-group.html","template/accordion/accordion.html","template/alert/alert.html","template/carousel/carousel.html","template/carousel/slide.html","template/datepicker/datepicker.html","template/datepicker/day.html","template/datepicker/month.html","template/datepicker/popup.html","template/datepicker/year.html","template/modal/backdrop.html","template/modal/window.html","template/pagination/pager.html","template/pagination/pagination.html","template/tooltip/tooltip-html-popup.html","template/tooltip/tooltip-popup.html","template/tooltip/tooltip-template-popup.html","template/popover/popover-html.html","template/popover/popover-template.html","template/popover/popover.html","template/progressbar/bar.html","template/progressbar/progress.html","template/progressbar/progressbar.html","template/rating/rating.html","template/tabs/tab.html","template/tabs/tabset.html","template/timepicker/timepicker.html","template/typeahead/typeahead-match.html","template/typeahead/typeahead-popup.html"]); angular.module('ui.bootstrap.collapse', []) .directive('uibCollapse', ['$animate', '$injector', function($animate, $injector) { var $animateCss = $injector.has('$animateCss') ? $injector.get('$animateCss') : null; return { link: function(scope, element, attrs) { function expand() { element.removeClass('collapse') .addClass('collapsing') .attr('aria-expanded', true) .attr('aria-hidden', false); if ($animateCss) { $animateCss(element, { addClass: 'in', easing: 'ease', to: { height: element[0].scrollHeight + 'px' } }).start().finally(expandDone); } else { $animate.addClass(element, 'in', { to: { height: element[0].scrollHeight + 'px' } }).then(expandDone); } } function expandDone() { element.removeClass('collapsing') .addClass('collapse') .css({height: 'auto'}); } function collapse() { if (!element.hasClass('collapse') && !element.hasClass('in')) { return collapseDone(); } element // IMPORTANT: The height must be set before adding "collapsing" class. // Otherwise, the browser attempts to animate from height 0 (in // collapsing class) to the given height here. .css({height: element[0].scrollHeight + 'px'}) // initially all panel collapse have the collapse class, this removal // prevents the animation from jumping to collapsed state .removeClass('collapse') .addClass('collapsing') .attr('aria-expanded', false) .attr('aria-hidden', true); if ($animateCss) { $animateCss(element, { removeClass: 'in', to: {height: '0'} }).start().finally(collapseDone); } else { $animate.removeClass(element, 'in', { to: {height: '0'} }).then(collapseDone); } } function collapseDone() { element.css({height: '0'}); // Required so that collapse works when animation is disabled element.removeClass('collapsing') .addClass('collapse'); } scope.$watch(attrs.uibCollapse, function(shouldCollapse) { if (shouldCollapse) { collapse(); } else { expand(); } }); } }; }]); /* Deprecated collapse below */ angular.module('ui.bootstrap.collapse') .value('$collapseSuppressWarning', false) .directive('collapse', ['$animate', '$injector', '$log', '$collapseSuppressWarning', function($animate, $injector, $log, $collapseSuppressWarning) { var $animateCss = $injector.has('$animateCss') ? $injector.get('$animateCss') : null; return { link: function(scope, element, attrs) { if (!$collapseSuppressWarning) { $log.warn('collapse is now deprecated. Use uib-collapse instead.'); } function expand() { element.removeClass('collapse') .addClass('collapsing') .attr('aria-expanded', true) .attr('aria-hidden', false); if ($animateCss) { $animateCss(element, { easing: 'ease', to: { height: element[0].scrollHeight + 'px' } }).start().done(expandDone); } else { $animate.animate(element, {}, { height: element[0].scrollHeight + 'px' }).then(expandDone); } } function expandDone() { element.removeClass('collapsing') .addClass('collapse in') .css({height: 'auto'}); } function collapse() { if (!element.hasClass('collapse') && !element.hasClass('in')) { return collapseDone(); } element // IMPORTANT: The height must be set before adding "collapsing" class. // Otherwise, the browser attempts to animate from height 0 (in // collapsing class) to the given height here. .css({height: element[0].scrollHeight + 'px'}) // initially all panel collapse have the collapse class, this removal // prevents the animation from jumping to collapsed state .removeClass('collapse in') .addClass('collapsing') .attr('aria-expanded', false) .attr('aria-hidden', true); if ($animateCss) { $animateCss(element, { to: {height: '0'} }).start().done(collapseDone); } else { $animate.animate(element, {}, { height: '0' }).then(collapseDone); } } function collapseDone() { element.css({height: '0'}); // Required so that collapse works when animation is disabled element.removeClass('collapsing') .addClass('collapse'); } scope.$watch(attrs.collapse, function(shouldCollapse) { if (shouldCollapse) { collapse(); } else { expand(); } }); } }; }]); angular.module('ui.bootstrap.accordion', ['ui.bootstrap.collapse']) .constant('uibAccordionConfig', { closeOthers: true }) .controller('UibAccordionController', ['$scope', '$attrs', 'uibAccordionConfig', function($scope, $attrs, accordionConfig) { // This array keeps track of the accordion groups this.groups = []; // Ensure that all the groups in this accordion are closed, unless close-others explicitly says not to this.closeOthers = function(openGroup) { var closeOthers = angular.isDefined($attrs.closeOthers) ? $scope.$eval($attrs.closeOthers) : accordionConfig.closeOthers; if (closeOthers) { angular.forEach(this.groups, function(group) { if (group !== openGroup) { group.isOpen = false; } }); } }; // This is called from the accordion-group directive to add itself to the accordion this.addGroup = function(groupScope) { var that = this; this.groups.push(groupScope); groupScope.$on('$destroy', function(event) { that.removeGroup(groupScope); }); }; // This is called from the accordion-group directive when to remove itself this.removeGroup = function(group) { var index = this.groups.indexOf(group); if (index !== -1) { this.groups.splice(index, 1); } }; }]) // The accordion directive simply sets up the directive controller // and adds an accordion CSS class to itself element. .directive('uibAccordion', function() { return { controller: 'UibAccordionController', controllerAs: 'accordion', transclude: true, templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/accordion/accordion.html'; } }; }) // The accordion-group directive indicates a block of html that will expand and collapse in an accordion .directive('uibAccordionGroup', function() { return { require: '^uibAccordion', // We need this directive to be inside an accordion transclude: true, // It transcludes the contents of the directive into the template replace: true, // The element containing the directive will be replaced with the template templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/accordion/accordion-group.html'; }, scope: { heading: '@', // Interpolate the heading attribute onto this scope isOpen: '=?', isDisabled: '=?' }, controller: function() { this.setHeading = function(element) { this.heading = element; }; }, link: function(scope, element, attrs, accordionCtrl) { accordionCtrl.addGroup(scope); scope.openClass = attrs.openClass || 'panel-open'; scope.panelClass = attrs.panelClass; scope.$watch('isOpen', function(value) { element.toggleClass(scope.openClass, !!value); if (value) { accordionCtrl.closeOthers(scope); } }); scope.toggleOpen = function($event) { if (!scope.isDisabled) { if (!$event || $event.which === 32) { scope.isOpen = !scope.isOpen; } } }; } }; }) // Use accordion-heading below an accordion-group to provide a heading containing HTML .directive('uibAccordionHeading', function() { return { transclude: true, // Grab the contents to be used as the heading template: '', // In effect remove this element! replace: true, require: '^uibAccordionGroup', link: function(scope, element, attrs, accordionGroupCtrl, transclude) { // Pass the heading to the accordion-group controller // so that it can be transcluded into the right place in the template // [The second parameter to transclude causes the elements to be cloned so that they work in ng-repeat] accordionGroupCtrl.setHeading(transclude(scope, angular.noop)); } }; }) // Use in the accordion-group template to indicate where you want the heading to be transcluded // You must provide the property on the accordion-group controller that will hold the transcluded element .directive('uibAccordionTransclude', function() { return { require: ['?^uibAccordionGroup', '?^accordionGroup'], link: function(scope, element, attrs, controller) { controller = controller[0] ? controller[0] : controller[1]; // Delete after we remove deprecation scope.$watch(function() { return controller[attrs.uibAccordionTransclude]; }, function(heading) { if (heading) { element.find('span').html(''); element.find('span').append(heading); } }); } }; }); /* Deprecated accordion below */ angular.module('ui.bootstrap.accordion') .value('$accordionSuppressWarning', false) .controller('AccordionController', ['$scope', '$attrs', '$controller', '$log', '$accordionSuppressWarning', function($scope, $attrs, $controller, $log, $accordionSuppressWarning) { if (!$accordionSuppressWarning) { $log.warn('AccordionController is now deprecated. Use UibAccordionController instead.'); } angular.extend(this, $controller('UibAccordionController', { $scope: $scope, $attrs: $attrs })); }]) .directive('accordion', ['$log', '$accordionSuppressWarning', function($log, $accordionSuppressWarning) { return { restrict: 'EA', controller: 'AccordionController', controllerAs: 'accordion', transclude: true, replace: false, templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/accordion/accordion.html'; }, link: function() { if (!$accordionSuppressWarning) { $log.warn('accordion is now deprecated. Use uib-accordion instead.'); } } }; }]) .directive('accordionGroup', ['$log', '$accordionSuppressWarning', function($log, $accordionSuppressWarning) { return { require: '^accordion', // We need this directive to be inside an accordion restrict: 'EA', transclude: true, // It transcludes the contents of the directive into the template replace: true, // The element containing the directive will be replaced with the template templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/accordion/accordion-group.html'; }, scope: { heading: '@', // Interpolate the heading attribute onto this scope isOpen: '=?', isDisabled: '=?' }, controller: function() { this.setHeading = function(element) { this.heading = element; }; }, link: function(scope, element, attrs, accordionCtrl) { if (!$accordionSuppressWarning) { $log.warn('accordion-group is now deprecated. Use uib-accordion-group instead.'); } accordionCtrl.addGroup(scope); scope.openClass = attrs.openClass || 'panel-open'; scope.panelClass = attrs.panelClass; scope.$watch('isOpen', function(value) { element.toggleClass(scope.openClass, !!value); if (value) { accordionCtrl.closeOthers(scope); } }); scope.toggleOpen = function($event) { if (!scope.isDisabled) { if (!$event || $event.which === 32) { scope.isOpen = !scope.isOpen; } } }; } }; }]) .directive('accordionHeading', ['$log', '$accordionSuppressWarning', function($log, $accordionSuppressWarning) { return { restrict: 'EA', transclude: true, // Grab the contents to be used as the heading template: '', // In effect remove this element! replace: true, require: '^accordionGroup', link: function(scope, element, attr, accordionGroupCtrl, transclude) { if (!$accordionSuppressWarning) { $log.warn('accordion-heading is now deprecated. Use uib-accordion-heading instead.'); } // Pass the heading to the accordion-group controller // so that it can be transcluded into the right place in the template // [The second parameter to transclude causes the elements to be cloned so that they work in ng-repeat] accordionGroupCtrl.setHeading(transclude(scope, angular.noop)); } }; }]) .directive('accordionTransclude', ['$log', '$accordionSuppressWarning', function($log, $accordionSuppressWarning) { return { require: '^accordionGroup', link: function(scope, element, attr, controller) { if (!$accordionSuppressWarning) { $log.warn('accordion-transclude is now deprecated. Use uib-accordion-transclude instead.'); } scope.$watch(function() { return controller[attr.accordionTransclude]; }, function(heading) { if (heading) { element.find('span').html(''); element.find('span').append(heading); } }); } }; }]); angular.module('ui.bootstrap.alert', []) .controller('UibAlertController', ['$scope', '$attrs', '$interpolate', '$timeout', function($scope, $attrs, $interpolate, $timeout) { $scope.closeable = !!$attrs.close; var dismissOnTimeout = angular.isDefined($attrs.dismissOnTimeout) ? $interpolate($attrs.dismissOnTimeout)($scope.$parent) : null; if (dismissOnTimeout) { $timeout(function() { $scope.close(); }, parseInt(dismissOnTimeout, 10)); } }]) .directive('uibAlert', function() { return { controller: 'UibAlertController', controllerAs: 'alert', templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/alert/alert.html'; }, transclude: true, replace: true, scope: { type: '@', close: '&' } }; }); /* Deprecated alert below */ angular.module('ui.bootstrap.alert') .value('$alertSuppressWarning', false) .controller('AlertController', ['$scope', '$attrs', '$controller', '$log', '$alertSuppressWarning', function($scope, $attrs, $controller, $log, $alertSuppressWarning) { if (!$alertSuppressWarning) { $log.warn('AlertController is now deprecated. Use UibAlertController instead.'); } angular.extend(this, $controller('UibAlertController', { $scope: $scope, $attrs: $attrs })); }]) .directive('alert', ['$log', '$alertSuppressWarning', function($log, $alertSuppressWarning) { return { controller: 'AlertController', controllerAs: 'alert', templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/alert/alert.html'; }, transclude: true, replace: true, scope: { type: '@', close: '&' }, link: function() { if (!$alertSuppressWarning) { $log.warn('alert is now deprecated. Use uib-alert instead.'); } } }; }]); angular.module('ui.bootstrap.buttons', []) .constant('uibButtonConfig', { activeClass: 'active', toggleEvent: 'click' }) .controller('UibButtonsController', ['uibButtonConfig', function(buttonConfig) { this.activeClass = buttonConfig.activeClass || 'active'; this.toggleEvent = buttonConfig.toggleEvent || 'click'; }]) .directive('uibBtnRadio', function() { return { require: ['uibBtnRadio', 'ngModel'], controller: 'UibButtonsController', controllerAs: 'buttons', link: function(scope, element, attrs, ctrls) { var buttonsCtrl = ctrls[0], ngModelCtrl = ctrls[1]; element.find('input').css({display: 'none'}); //model -> UI ngModelCtrl.$render = function() { element.toggleClass(buttonsCtrl.activeClass, angular.equals(ngModelCtrl.$modelValue, scope.$eval(attrs.uibBtnRadio))); }; //ui->model element.on(buttonsCtrl.toggleEvent, function() { if (attrs.disabled) { return; } var isActive = element.hasClass(buttonsCtrl.activeClass); if (!isActive || angular.isDefined(attrs.uncheckable)) { scope.$apply(function() { ngModelCtrl.$setViewValue(isActive ? null : scope.$eval(attrs.uibBtnRadio)); ngModelCtrl.$render(); }); } }); } }; }) .directive('uibBtnCheckbox', function() { return { require: ['uibBtnCheckbox', 'ngModel'], controller: 'UibButtonsController', controllerAs: 'button', link: function(scope, element, attrs, ctrls) { var buttonsCtrl = ctrls[0], ngModelCtrl = ctrls[1]; element.find('input').css({display: 'none'}); function getTrueValue() { return getCheckboxValue(attrs.btnCheckboxTrue, true); } function getFalseValue() { return getCheckboxValue(attrs.btnCheckboxFalse, false); } function getCheckboxValue(attribute, defaultValue) { return angular.isDefined(attribute) ? scope.$eval(attribute) : defaultValue; } //model -> UI ngModelCtrl.$render = function() { element.toggleClass(buttonsCtrl.activeClass, angular.equals(ngModelCtrl.$modelValue, getTrueValue())); }; //ui->model element.on(buttonsCtrl.toggleEvent, function() { if (attrs.disabled) { return; } scope.$apply(function() { ngModelCtrl.$setViewValue(element.hasClass(buttonsCtrl.activeClass) ? getFalseValue() : getTrueValue()); ngModelCtrl.$render(); }); }); } }; }); /* Deprecated buttons below */ angular.module('ui.bootstrap.buttons') .value('$buttonsSuppressWarning', false) .controller('ButtonsController', ['$controller', '$log', '$buttonsSuppressWarning', function($controller, $log, $buttonsSuppressWarning) { if (!$buttonsSuppressWarning) { $log.warn('ButtonsController is now deprecated. Use UibButtonsController instead.'); } angular.extend(this, $controller('UibButtonsController')); }]) .directive('btnRadio', ['$log', '$buttonsSuppressWarning', function($log, $buttonsSuppressWarning) { return { require: ['btnRadio', 'ngModel'], controller: 'ButtonsController', controllerAs: 'buttons', link: function(scope, element, attrs, ctrls) { if (!$buttonsSuppressWarning) { $log.warn('btn-radio is now deprecated. Use uib-btn-radio instead.'); } var buttonsCtrl = ctrls[0], ngModelCtrl = ctrls[1]; element.find('input').css({display: 'none'}); //model -> UI ngModelCtrl.$render = function() { element.toggleClass(buttonsCtrl.activeClass, angular.equals(ngModelCtrl.$modelValue, scope.$eval(attrs.btnRadio))); }; //ui->model element.bind(buttonsCtrl.toggleEvent, function() { if (attrs.disabled) { return; } var isActive = element.hasClass(buttonsCtrl.activeClass); if (!isActive || angular.isDefined(attrs.uncheckable)) { scope.$apply(function() { ngModelCtrl.$setViewValue(isActive ? null : scope.$eval(attrs.btnRadio)); ngModelCtrl.$render(); }); } }); } }; }]) .directive('btnCheckbox', ['$document', '$log', '$buttonsSuppressWarning', function($document, $log, $buttonsSuppressWarning) { return { require: ['btnCheckbox', 'ngModel'], controller: 'ButtonsController', controllerAs: 'button', link: function(scope, element, attrs, ctrls) { if (!$buttonsSuppressWarning) { $log.warn('btn-checkbox is now deprecated. Use uib-btn-checkbox instead.'); } var buttonsCtrl = ctrls[0], ngModelCtrl = ctrls[1]; element.find('input').css({display: 'none'}); function getTrueValue() { return getCheckboxValue(attrs.btnCheckboxTrue, true); } function getFalseValue() { return getCheckboxValue(attrs.btnCheckboxFalse, false); } function getCheckboxValue(attributeValue, defaultValue) { var val = scope.$eval(attributeValue); return angular.isDefined(val) ? val : defaultValue; } //model -> UI ngModelCtrl.$render = function() { element.toggleClass(buttonsCtrl.activeClass, angular.equals(ngModelCtrl.$modelValue, getTrueValue())); }; //ui->model element.bind(buttonsCtrl.toggleEvent, function() { if (attrs.disabled) { return; } scope.$apply(function() { ngModelCtrl.$setViewValue(element.hasClass(buttonsCtrl.activeClass) ? getFalseValue() : getTrueValue()); ngModelCtrl.$render(); }); }); //accessibility element.on('keypress', function(e) { if (attrs.disabled || e.which !== 32 || $document[0].activeElement !== element[0]) { return; } scope.$apply(function() { ngModelCtrl.$setViewValue(element.hasClass(buttonsCtrl.activeClass) ? getFalseValue() : getTrueValue()); ngModelCtrl.$render(); }); }); } }; }]); /** * @ngdoc overview * @name ui.bootstrap.carousel * * @description * AngularJS version of an image carousel. * */ angular.module('ui.bootstrap.carousel', []) .controller('UibCarouselController', ['$scope', '$element', '$interval', '$animate', function($scope, $element, $interval, $animate) { var self = this, slides = self.slides = $scope.slides = [], NEW_ANIMATE = angular.version.minor >= 4, NO_TRANSITION = 'uib-noTransition', SLIDE_DIRECTION = 'uib-slideDirection', currentIndex = -1, currentInterval, isPlaying; self.currentSlide = null; var destroyed = false; /* direction: "prev" or "next" */ self.select = $scope.select = function(nextSlide, direction) { var nextIndex = $scope.indexOfSlide(nextSlide); //Decide direction if it's not given if (direction === undefined) { direction = nextIndex > self.getCurrentIndex() ? 'next' : 'prev'; } //Prevent this user-triggered transition from occurring if there is already one in progress if (nextSlide && nextSlide !== self.currentSlide && !$scope.$currentTransition) { goNext(nextSlide, nextIndex, direction); } }; function goNext(slide, index, direction) { // Scope has been destroyed, stop here. if (destroyed) { return; } angular.extend(slide, {direction: direction, active: true}); angular.extend(self.currentSlide || {}, {direction: direction, active: false}); if ($animate.enabled() && !$scope.noTransition && !$scope.$currentTransition && slide.$element && self.slides.length > 1) { slide.$element.data(SLIDE_DIRECTION, slide.direction); if (self.currentSlide && self.currentSlide.$element) { self.currentSlide.$element.data(SLIDE_DIRECTION, slide.direction); } $scope.$currentTransition = true; if (NEW_ANIMATE) { $animate.on('addClass', slide.$element, function(element, phase) { if (phase === 'close') { $scope.$currentTransition = null; $animate.off('addClass', element); } }); } else { slide.$element.one('$animate:close', function closeFn() { $scope.$currentTransition = null; }); } } self.currentSlide = slide; currentIndex = index; //every time you change slides, reset the timer restartTimer(); } $scope.$on('$destroy', function() { destroyed = true; }); function getSlideByIndex(index) { if (angular.isUndefined(slides[index].index)) { return slides[index]; } var i, len = slides.length; for (i = 0; i < slides.length; ++i) { if (slides[i].index == index) { return slides[i]; } } } self.getCurrentIndex = function() { if (self.currentSlide && angular.isDefined(self.currentSlide.index)) { return +self.currentSlide.index; } return currentIndex; }; /* Allow outside people to call indexOf on slides array */ $scope.indexOfSlide = function(slide) { return angular.isDefined(slide.index) ? +slide.index : slides.indexOf(slide); }; $scope.next = function() { var newIndex = (self.getCurrentIndex() + 1) % slides.length; if (newIndex === 0 && $scope.noWrap()) { $scope.pause(); return; } return self.select(getSlideByIndex(newIndex), 'next'); }; $scope.prev = function() { var newIndex = self.getCurrentIndex() - 1 < 0 ? slides.length - 1 : self.getCurrentIndex() - 1; if ($scope.noWrap() && newIndex === slides.length - 1) { $scope.pause(); return; } return self.select(getSlideByIndex(newIndex), 'prev'); }; $scope.isActive = function(slide) { return self.currentSlide === slide; }; $scope.$watch('interval', restartTimer); $scope.$watchCollection('slides', resetTransition); $scope.$on('$destroy', resetTimer); function restartTimer() { resetTimer(); var interval = +$scope.interval; if (!isNaN(interval) && interval > 0) { currentInterval = $interval(timerFn, interval); } } function resetTimer() { if (currentInterval) { $interval.cancel(currentInterval); currentInterval = null; } } function timerFn() { var interval = +$scope.interval; if (isPlaying && !isNaN(interval) && interval > 0 && slides.length) { $scope.next(); } else { $scope.pause(); } } function resetTransition(slides) { if (!slides.length) { $scope.$currentTransition = null; } } $scope.play = function() { if (!isPlaying) { isPlaying = true; restartTimer(); } }; $scope.pause = function() { if (!$scope.noPause) { isPlaying = false; resetTimer(); } }; self.addSlide = function(slide, element) { slide.$element = element; slides.push(slide); //if this is the first slide or the slide is set to active, select it if (slides.length === 1 || slide.active) { self.select(slides[slides.length - 1]); if (slides.length === 1) { $scope.play(); } } else { slide.active = false; } }; self.removeSlide = function(slide) { if (angular.isDefined(slide.index)) { slides.sort(function(a, b) { return +a.index > +b.index; }); } //get the index of the slide inside the carousel var index = slides.indexOf(slide); slides.splice(index, 1); if (slides.length > 0 && slide.active) { if (index >= slides.length) { self.select(slides[index - 1]); } else { self.select(slides[index]); } } else if (currentIndex > index) { currentIndex--; } //clean the currentSlide when no more slide if (slides.length === 0) { self.currentSlide = null; } }; $scope.$watch('noTransition', function(noTransition) { $element.data(NO_TRANSITION, noTransition); }); }]) /** * @ngdoc directive * @name ui.bootstrap.carousel.directive:carousel * @restrict EA * * @description * Carousel is the outer container for a set of image 'slides' to showcase. * * @param {number=} interval The time, in milliseconds, that it will take the carousel to go to the next slide. * @param {boolean=} noTransition Whether to disable transitions on the carousel. * @param {boolean=} noPause Whether to disable pausing on the carousel (by default, the carousel interval pauses on hover). * * @example <example module="ui.bootstrap"> <file name="index.html"> <uib-carousel> <uib-slide> <img src="http://placekitten.com/150/150" style="margin:auto;"> <div class="carousel-caption"> <p>Beautiful!</p> </div> </uib-slide> <uib-slide> <img src="http://placekitten.com/100/150" style="margin:auto;"> <div class="carousel-caption"> <p>D'aww!</p> </div> </uib-slide> </uib-carousel> </file> <file name="demo.css"> .carousel-indicators { top: auto; bottom: 15px; } </file> </example> */ .directive('uibCarousel', [function() { return { transclude: true, replace: true, controller: 'UibCarouselController', controllerAs: 'carousel', require: 'carousel', templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/carousel/carousel.html'; }, scope: { interval: '=', noTransition: '=', noPause: '=', noWrap: '&' } }; }]) /** * @ngdoc directive * @name ui.bootstrap.carousel.directive:slide * @restrict EA * * @description * Creates a slide inside a {@link ui.bootstrap.carousel.directive:carousel carousel}. Must be placed as a child of a carousel element. * * @param {boolean=} active Model binding, whether or not this slide is currently active. * @param {number=} index The index of the slide. The slides will be sorted by this parameter. * * @example <example module="ui.bootstrap"> <file name="index.html"> <div ng-controller="CarouselDemoCtrl"> <uib-carousel> <uib-slide ng-repeat="slide in slides" active="slide.active" index="$index"> <img ng-src="{{slide.image}}" style="margin:auto;"> <div class="carousel-caption"> <h4>Slide {{$index}}</h4> <p>{{slide.text}}</p> </div> </uib-slide> </uib-carousel> Interval, in milliseconds: <input type="number" ng-model="myInterval"> <br />Enter a negative number to stop the interval. </div> </file> <file name="script.js"> function CarouselDemoCtrl($scope) { $scope.myInterval = 5000; } </file> <file name="demo.css"> .carousel-indicators { top: auto; bottom: 15px; } </file> </example> */ .directive('uibSlide', function() { return { require: '^uibCarousel', restrict: 'EA', transclude: true, replace: true, templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/carousel/slide.html'; }, scope: { active: '=?', actual: '=?', index: '=?' }, link: function (scope, element, attrs, carouselCtrl) { carouselCtrl.addSlide(scope, element); //when the scope is destroyed then remove the slide from the current slides array scope.$on('$destroy', function() { carouselCtrl.removeSlide(scope); }); scope.$watch('active', function(active) { if (active) { carouselCtrl.select(scope); } }); } }; }) .animation('.item', [ '$injector', '$animate', function ($injector, $animate) { var NO_TRANSITION = 'uib-noTransition', SLIDE_DIRECTION = 'uib-slideDirection', $animateCss = null; if ($injector.has('$animateCss')) { $animateCss = $injector.get('$animateCss'); } function removeClass(element, className, callback) { element.removeClass(className); if (callback) { callback(); } } return { beforeAddClass: function(element, className, done) { // Due to transclusion, noTransition property is on parent's scope if (className == 'active' && element.parent() && element.parent().parent() && !element.parent().parent().data(NO_TRANSITION)) { var stopped = false; var direction = element.data(SLIDE_DIRECTION); var directionClass = direction == 'next' ? 'left' : 'right'; var removeClassFn = removeClass.bind(this, element, directionClass + ' ' + direction, done); element.addClass(direction); if ($animateCss) { $animateCss(element, {addClass: directionClass}) .start() .done(removeClassFn); } else { $animate.addClass(element, directionClass).then(function () { if (!stopped) { removeClassFn(); } done(); }); } return function () { stopped = true; }; } done(); }, beforeRemoveClass: function (element, className, done) { // Due to transclusion, noTransition property is on parent's scope if (className === 'active' && element.parent() && element.parent().parent() && !element.parent().parent().data(NO_TRANSITION)) { var stopped = false; var direction = element.data(SLIDE_DIRECTION); var directionClass = direction == 'next' ? 'left' : 'right'; var removeClassFn = removeClass.bind(this, element, directionClass, done); if ($animateCss) { $animateCss(element, {addClass: directionClass}) .start() .done(removeClassFn); } else { $animate.addClass(element, directionClass).then(function() { if (!stopped) { removeClassFn(); } done(); }); } return function() { stopped = true; }; } done(); } }; }]); /* deprecated carousel below */ angular.module('ui.bootstrap.carousel') .value('$carouselSuppressWarning', false) .controller('CarouselController', ['$scope', '$element', '$controller', '$log', '$carouselSuppressWarning', function($scope, $element, $controller, $log, $carouselSuppressWarning) { if (!$carouselSuppressWarning) { $log.warn('CarouselController is now deprecated. Use UibCarouselController instead.'); } angular.extend(this, $controller('UibCarouselController', { $scope: $scope, $element: $element })); }]) .directive('carousel', ['$log', '$carouselSuppressWarning', function($log, $carouselSuppressWarning) { return { transclude: true, replace: true, controller: 'CarouselController', controllerAs: 'carousel', require: 'carousel', templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/carousel/carousel.html'; }, scope: { interval: '=', noTransition: '=', noPause: '=', noWrap: '&' }, link: function() { if (!$carouselSuppressWarning) { $log.warn('carousel is now deprecated. Use uib-carousel instead.'); } } }; }]) .directive('slide', ['$log', '$carouselSuppressWarning', function($log, $carouselSuppressWarning) { return { require: '^carousel', transclude: true, replace: true, templateUrl: function(element, attrs) { return attrs.templateUrl || 'template/carousel/slide.html'; }, scope: { active: '=?', actual: '=?', index: '=?' }, link: function (scope, element, attrs, carouselCtrl) { if (!$carouselSuppressWarning) { $log.warn('slide is now deprecated. Use uib-slide instead.'); } carouselCtrl.addSlide(scope, element); //when the scope is destroyed then remove the slide from the current slides array scope.$on('$destroy', function() { carouselCtrl.removeSlide(scope); }); scope.$watch('active', function(active) { if (active) { carouselCtrl.select(scope); } }); } }; }]); angular.module('ui.bootstrap.dateparser', []) .service('uibDateParser', ['$log', '$locale', 'orderByFilter', function($log, $locale, orderByFilter) { // Pulled from https://github.com/mbostock/d3/blob/master/src/format/requote.js var SPECIAL_CHARACTERS_REGEXP = /[\\\^\$\*\+\?\|\[\]\(\)\.\{\}]/g; var localeId; var formatCodeToRegex; this.init = function() { localeId = $locale.id; this.parsers = {}; formatCodeToRegex = { 'yyyy': { regex: '\\d{4}', apply: function(value) { this.year = +value; } }, 'yy': { regex: '\\d{2}', apply: function(value) { this.year = +value + 2000; } }, 'y': { regex: '\\d{1,4}', apply: function(value) { this.year = +value; } }, 'MMMM': { regex: $locale.DATETIME_FORMATS.MONTH.join('|'), apply: function(value) { this.month = $locale.DATETIME_FORMATS.MONTH.indexOf(value); } }, 'MMM': { regex: $locale.DATETIME_FORMATS.SHORTMONTH.join('|'), apply: function(value) { this.month = $locale.DATETIME_FORMATS.SHORTMONTH.indexOf(value); } }, 'MM': { regex: '0[1-9]|1[0-2]', apply: function(value) { this.month = value - 1; } }, 'M': { regex: '[1-9]|1[0-2]', apply: function(value) { this.month = value - 1; } }, 'dd': { regex: '[0-2][0-9]{1}|3[0-1]{1}', apply: function(value) { this.date = +value; } }, 'd': { regex: '[1-2]?[0-9]{1}|3[0-1]{1}', apply: function(value) { this.date = +value; } }, 'EEEE': { regex: $locale.DATETIME_FORMATS.DAY.join('|') }, 'EEE': { regex: $locale.DATETIME_FORMATS.SHORTDAY.join('|') }, 'HH': { regex: '(?:0|1)[0-9]|2[0-3]', apply: function(value) { this.hours = +value; } }, 'hh': { regex: '0[0-9]|1[0-2]', apply: function(value) { this.hours = +value; } }, 'H': { regex: '1?[0-9]|2[0-3]', apply: function(value) { this.hours = +value; } }, 'h': { regex: '[0-9]|1[0-2]', apply: function(value) { this.hours = +value; } }, 'mm': { regex: '[0-5][0-9]', apply: function(value) { this.minutes = +value; } }, 'm': { regex: '[0-9]|[1-5][0-9]', apply: function(value) { this.minutes = +value; } }, 'sss': { regex: '[0-9][0-9][0-9]', apply: function(value) { this.milliseconds = +value; } }, 'ss': { regex: '[0-5][0-9]', apply: function(value) { this.seconds = +value; } }, 's': { regex: '[0-9]|[1-5][0-9]', apply: function(value) { this.seconds = +value; } }, 'a': { regex: $locale.DATETIME_FORMATS.AMPMS.join('|'), apply: function(value) { if (this.hours === 12) { this.hours = 0; } if (value === 'PM') { this.hours += 12; } } } }; }; this.init(); function createParser(format) { var map = [], regex = format.split(''); angular.forEach(formatCodeToRegex, function(data, code) { var index = format.indexOf(code); if (index > -1) { format = format.split(''); regex[index] = '(' + data.regex + ')'; format[index] = '$'; // Custom symbol to define consumed part of format for (var i = index + 1, n = index + code.length; i < n; i++) { regex[i] = ''; format[i] = '$'; } format = format.join(''); map.push({ index: index, apply: data.apply }); } }); return { regex: new RegExp('^' + regex.join('') + '$'), map: orderByFilter(map, 'index') }; } this.parse = function(input, format, baseDate) { if (!angular.isString(input) || !format) { return input; } format = $locale.DATETIME_FORMATS[format] || format; format = format.replace(SPECIAL_CHARACTERS_REGEXP, '\\$&'); if ($locale.id !== localeId) { this.init(); } if (!this.parsers[format]) { this.parsers[format] = createParser(format); } var parser = this.parsers[format], regex = parser.regex, map = parser.map, results = input.match(regex); if (results && results.length) { var fields, dt; if (angular.isDate(baseDate) && !isNaN(baseDate.getTime())) { fields = { year: baseDate.getFullYear(), month: baseDate.getMonth(), date: baseDate.getDate(), hours: baseDate.getHours(), minutes: baseDate.getMinutes(), seconds: baseDate.getSeconds(), milliseconds: baseDate.getMilliseconds() }; } else { if (baseDate) { $log.warn('dateparser:', 'baseDate is not a valid date'); } fields = { year: 1900, month: 0, date: 1, hours: 0, minutes: 0, seconds: 0, milliseconds: 0 }; } for (var i = 1, n = results.length; i < n; i++) { var mapper = map[i-1]; if (mapper.apply) { mapper.apply.call(fields, results[i]); } } if (isValid(fields.year, fields.month, fields.date)) { if (angular.isDate(baseDate) && !isNaN(baseDate.getTime())) { dt = new Date(baseDate); dt.setFullYear(fields.year, fields.month, fields.date, fields.hours, fields.minutes, fields.seconds, fields.milliseconds || 0); } else { dt = new Date(fields.year, fields.month, fields.date, fields.hours, fields.minutes, fields.seconds, fields.milliseconds || 0); } } return dt; } }; // Check if date is valid for specific month (and year for February). // Month: 0 = Jan, 1 = Feb, etc function isValid(year, month, date) { if (date < 1) { return false; } if (month === 1 && date > 28) { return date === 29 && ((year % 4 === 0 && year % 100 !== 0) || year % 400 === 0); } if (month === 3 || month === 5 || month === 8 || month === 10) { return date < 31; } return true; } }]); /* Deprecated dateparser below */ angular.module('ui.bootstrap.dateparser') .value('$dateParserSuppressWarning', false) .service('dateParser', ['$log', '$dateParserSuppressWarning', 'uibDateParser', function($log, $dateParserSuppressWarning, uibDateParser) { if (!$dateParserSuppressWarning) { $log.warn('dateParser is now deprecated. Use uibDateParser instead.'); } angular.extend(this, uibDateParser); }]); angular.module('ui.bootstrap.position', []) /** * A set of utility methods that can be use to retrieve position of DOM elements. * It is meant to be used where we need to absolute-position DOM elements in * relation to other, existing elements (this is the case for tooltips, popovers, * typeahead suggestions etc.). */ .factory('$uibPosition', ['$document', '$window', function($document, $window) { function getStyle(el, cssprop) { if (el.currentStyle) { //IE return el.currentStyle[cssprop]; } else if ($window.getComputedStyle) { return $window.getComputedStyle(el)[cssprop]; } // finally try and get inline style return el.style[cssprop]; } /** * Checks if a given element is statically positioned * @param element - raw DOM element */ function isStaticPositioned(element) { return (getStyle(element, 'position') || 'static' ) === 'static'; } /** * returns the closest, non-statically positioned parentOffset of a given element * @param element */ var parentOffsetEl = function(element) { var docDomEl = $document[0]; var offsetParent = element.offsetParent || docDomEl; while (offsetParent && offsetParent !== docDomEl && isStaticPositioned(offsetParent) ) { offsetParent = offsetParent.offsetParent; } return offsetParent || docDomEl; }; return { /** * Provides read-only equivalent of jQuery's position function: * http://api.jquery.com/position/ */ position: function(element) { var elBCR = this.offset(element); var offsetParentBCR = { top: 0, left: 0 }; var offsetParentEl = parentOffsetEl(element[0]); if (offsetParentEl != $document[0]) { offsetParentBCR = this.offset(angular.element(offsetParentEl)); offsetParentBCR.top += offsetParentEl.clientTop - offsetParentEl.scrollTop; offsetParentBCR.left += offsetParentEl.clientLeft - offsetParentEl.scrollLeft; } var boundingClientRect = element[0].getBoundingClientRect(); return { width: boundingClientRect.width || element.prop('offsetWidth'), height: boundingClientRect.height || element.prop('offsetHeight'), top: elBCR.top - offsetParentBCR.top, left: elBCR.left - offsetParentBCR.left }; }, /** * Provides read-only equivalent of jQuery's offset function: * http://api.jquery.com/offset/ */ offset: function(element) { var boundingClientRect = element[0].getBoundingClientRect(); return { width: boundingClientRect.width || element.prop('offsetWidth'), height: boundingClientRect.height || element.prop('offsetHeight'), top: boundingClientRect.top + ($window.pageYOffset || $document[0].documentElement.scrollTop), left: boundingClientRect.left + ($window.pageXOffset || $document[0].documentElement.scrollLeft) }; }, /** * Provides coordinates for the targetEl in relation to hostEl */ positionElements: function(hostEl, targetEl, positionStr, appendToBody) { var positionStrParts = positionStr.split('-'); var pos0 = positionStrParts[0], pos1 = positionStrParts[1] || 'center'; var hostElPos, targetElWidth, targetElHeight, targetElPos; hostElPos = appendToBody ? this.offset(hostEl) : this.position(hostEl); targetElWidth = targetEl.prop('offsetWidth'); targetElHeight = targetEl.prop('offsetHeight'); var shiftWidth = { center: function() { return hostElPos.left + hostElPos.width / 2 - targetElWidth / 2; }, left: function() { return hostElPos.left; }, right