rails-angularstrap 2.2.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.
- checksums.yaml +7 -0
- data/README.md +89 -0
- data/Rakefile +2 -0
- data/lib/rails/angularstrap.rb +8 -0
- data/lib/rails/angularstrap/version.rb +5 -0
- data/vendor/assets/javascripts/angular-strap/LICENSE.md +21 -0
- data/vendor/assets/javascripts/angular-strap/README.md +112 -0
- data/vendor/assets/javascripts/angular-strap/angular-strap.nuspec +23 -0
- data/vendor/assets/javascripts/angular-strap/bower.json +53 -0
- data/vendor/assets/javascripts/angular-strap/dist/angular-strap.js +5014 -0
- data/vendor/assets/javascripts/angular-strap/dist/angular-strap.min.js +11 -0
- data/vendor/assets/javascripts/angular-strap/dist/angular-strap.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/angular-strap.tpl.js +89 -0
- data/vendor/assets/javascripts/angular-strap/dist/angular-strap.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/affix.js +249 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/affix.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/affix.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/alert.js +120 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/alert.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/alert.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/alert.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/alert.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/aside.js +96 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/aside.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/aside.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/aside.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/aside.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/button.js +177 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/button.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/button.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/collapse.js +273 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/collapse.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/collapse.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/date-formatter.js +61 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/date-formatter.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/date-formatter.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/date-parser.js +273 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/date-parser.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/date-parser.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/datepicker.js +640 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/datepicker.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/datepicker.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/datepicker.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/datepicker.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/debounce.js +62 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/debounce.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/debounce.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dimensions.js +156 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dimensions.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dimensions.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dropdown.js +149 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dropdown.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dropdown.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dropdown.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/dropdown.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/modal.js +349 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/modal.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/modal.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/modal.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/modal.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/navbar.js +72 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/navbar.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/navbar.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/parse-options.js +76 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/parse-options.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/parse-options.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/popover.js +112 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/popover.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/popover.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/popover.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/popover.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/raf.js +61 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/raf.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/raf.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/scrollspy.js +261 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/scrollspy.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/scrollspy.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/select.js +325 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/select.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/select.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/select.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/select.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tab.js +186 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tab.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tab.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tab.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tab.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/timepicker.js +485 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/timepicker.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/timepicker.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/timepicker.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/timepicker.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tooltip.js +690 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tooltip.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tooltip.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tooltip.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/tooltip.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/typeahead.js +266 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/typeahead.min.js +9 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/typeahead.min.js.map +1 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/typeahead.tpl.js +14 -0
- data/vendor/assets/javascripts/angular-strap/dist/modules/typeahead.tpl.min.js +8 -0
- data/vendor/assets/javascripts/angular-strap/gulpfile.js +489 -0
- data/vendor/assets/javascripts/angular-strap/package.json +73 -0
- data/vendor/assets/javascripts/angular-strap/src/affix/affix.js +258 -0
- data/vendor/assets/javascripts/angular-strap/src/alert/alert.js +113 -0
- data/vendor/assets/javascripts/angular-strap/src/alert/alert.tpl.html +4 -0
- data/vendor/assets/javascripts/angular-strap/src/aside/aside.js +89 -0
- data/vendor/assets/javascripts/angular-strap/src/aside/aside.tpl.html +14 -0
- data/vendor/assets/javascripts/angular-strap/src/button/button.js +174 -0
- data/vendor/assets/javascripts/angular-strap/src/collapse/collapse.js +266 -0
- data/vendor/assets/javascripts/angular-strap/src/datepicker/datepicker.js +633 -0
- data/vendor/assets/javascripts/angular-strap/src/datepicker/datepicker.tpl.html +33 -0
- data/vendor/assets/javascripts/angular-strap/src/dropdown/dropdown.js +143 -0
- data/vendor/assets/javascripts/angular-strap/src/dropdown/dropdown.tpl.html +6 -0
- data/vendor/assets/javascripts/angular-strap/src/helpers/date-formatter.js +54 -0
- data/vendor/assets/javascripts/angular-strap/src/helpers/date-parser.js +266 -0
- data/vendor/assets/javascripts/angular-strap/src/helpers/debounce.js +55 -0
- data/vendor/assets/javascripts/angular-strap/src/helpers/dimensions.js +212 -0
- data/vendor/assets/javascripts/angular-strap/src/helpers/parse-options.js +69 -0
- data/vendor/assets/javascripts/angular-strap/src/helpers/raf.js +54 -0
- data/vendor/assets/javascripts/angular-strap/src/modal/modal.js +348 -0
- data/vendor/assets/javascripts/angular-strap/src/modal/modal.tpl.html +14 -0
- data/vendor/assets/javascripts/angular-strap/src/module.js +19 -0
- data/vendor/assets/javascripts/angular-strap/src/navbar/navbar.js +65 -0
- data/vendor/assets/javascripts/angular-strap/src/popover/popover.js +111 -0
- data/vendor/assets/javascripts/angular-strap/src/popover/popover.tpl.html +5 -0
- data/vendor/assets/javascripts/angular-strap/src/scrollspy/scrollspy.js +254 -0
- data/vendor/assets/javascripts/angular-strap/src/select/select.js +321 -0
- data/vendor/assets/javascripts/angular-strap/src/select/select.tpl.html +14 -0
- data/vendor/assets/javascripts/angular-strap/src/tab/tab.js +183 -0
- data/vendor/assets/javascripts/angular-strap/src/tab/tab.tpl.html +7 -0
- data/vendor/assets/javascripts/angular-strap/src/timepicker/timepicker.js +493 -0
- data/vendor/assets/javascripts/angular-strap/src/timepicker/timepicker.tpl.html +62 -0
- data/vendor/assets/javascripts/angular-strap/src/tooltip/tooltip.js +806 -0
- data/vendor/assets/javascripts/angular-strap/src/tooltip/tooltip.tpl.html +4 -0
- data/vendor/assets/javascripts/angular-strap/src/typeahead/typeahead.js +262 -0
- data/vendor/assets/javascripts/angular-strap/src/typeahead/typeahead.tpl.html +5 -0
- data/vendor/assets/javascripts/angular/README.md +64 -0
- data/vendor/assets/javascripts/angular/angular-csp.css +13 -0
- data/vendor/assets/javascripts/angular/angular.js +26181 -0
- data/vendor/assets/javascripts/angular/angular.min.js +250 -0
- data/vendor/assets/javascripts/angular/angular.min.js.gzip +0 -0
- data/vendor/assets/javascripts/angular/angular.min.js.map +8 -0
- data/vendor/assets/javascripts/angular/bower.json +8 -0
- data/vendor/assets/javascripts/angular/index.js +2 -0
- data/vendor/assets/javascripts/angular/package.json +25 -0
- metadata +237 -0
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
<div class="dropdown-menu datepicker" ng-class="'datepicker-mode-' + $mode" style="max-width: 320px;">
|
|
2
|
+
<table style="table-layout: fixed; height: 100%; width: 100%;">
|
|
3
|
+
<thead>
|
|
4
|
+
<tr class="text-center">
|
|
5
|
+
<th>
|
|
6
|
+
<button tabindex="-1" type="button" class="btn btn-default pull-left" ng-click="$selectPane(-1)">
|
|
7
|
+
<i class="{{$iconLeft}}"></i>
|
|
8
|
+
</button>
|
|
9
|
+
</th>
|
|
10
|
+
<th colspan="{{ rows[0].length - 2 }}">
|
|
11
|
+
<button tabindex="-1" type="button" class="btn btn-default btn-block text-strong" ng-click="$toggleMode()">
|
|
12
|
+
<strong style="text-transform: capitalize;" ng-bind="title"></strong>
|
|
13
|
+
</button>
|
|
14
|
+
</th>
|
|
15
|
+
<th>
|
|
16
|
+
<button tabindex="-1" type="button" class="btn btn-default pull-right" ng-click="$selectPane(+1)">
|
|
17
|
+
<i class="{{$iconRight}}"></i>
|
|
18
|
+
</button>
|
|
19
|
+
</th>
|
|
20
|
+
</tr>
|
|
21
|
+
<tr ng-show="showLabels" ng-bind-html="labels"></tr>
|
|
22
|
+
</thead>
|
|
23
|
+
<tbody>
|
|
24
|
+
<tr ng-repeat="(i, row) in rows" height="{{ 100 / rows.length }}%">
|
|
25
|
+
<td class="text-center" ng-repeat="(j, el) in row">
|
|
26
|
+
<button tabindex="-1" type="button" class="btn btn-default" style="width: 100%" ng-class="{'btn-primary': el.selected, 'btn-info btn-today': el.isToday && !el.selected}" ng-click="$select(el.date)" ng-disabled="el.disabled">
|
|
27
|
+
<span ng-class="{'text-muted': el.muted}" ng-bind="el.label"></span>
|
|
28
|
+
</button>
|
|
29
|
+
</td>
|
|
30
|
+
</tr>
|
|
31
|
+
</tbody>
|
|
32
|
+
</table>
|
|
33
|
+
</div>
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
angular.module('mgcrea.ngStrap.dropdown', ['mgcrea.ngStrap.tooltip'])
|
|
4
|
+
|
|
5
|
+
.provider('$dropdown', function() {
|
|
6
|
+
|
|
7
|
+
var defaults = this.defaults = {
|
|
8
|
+
animation: 'am-fade',
|
|
9
|
+
prefixClass: 'dropdown',
|
|
10
|
+
prefixEvent: 'dropdown',
|
|
11
|
+
placement: 'bottom-left',
|
|
12
|
+
template: 'dropdown/dropdown.tpl.html',
|
|
13
|
+
trigger: 'click',
|
|
14
|
+
container: false,
|
|
15
|
+
keyboard: true,
|
|
16
|
+
html: false,
|
|
17
|
+
delay: 0
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
this.$get = function($window, $rootScope, $tooltip, $timeout) {
|
|
21
|
+
|
|
22
|
+
var bodyEl = angular.element($window.document.body);
|
|
23
|
+
var matchesSelector = Element.prototype.matchesSelector || Element.prototype.webkitMatchesSelector || Element.prototype.mozMatchesSelector || Element.prototype.msMatchesSelector || Element.prototype.oMatchesSelector;
|
|
24
|
+
|
|
25
|
+
function DropdownFactory(element, config) {
|
|
26
|
+
|
|
27
|
+
var $dropdown = {};
|
|
28
|
+
|
|
29
|
+
// Common vars
|
|
30
|
+
var options = angular.extend({}, defaults, config);
|
|
31
|
+
var scope = $dropdown.$scope = options.scope && options.scope.$new() || $rootScope.$new();
|
|
32
|
+
|
|
33
|
+
$dropdown = $tooltip(element, options);
|
|
34
|
+
var parentEl = element.parent();
|
|
35
|
+
|
|
36
|
+
// Protected methods
|
|
37
|
+
|
|
38
|
+
$dropdown.$onKeyDown = function(evt) {
|
|
39
|
+
if (!/(38|40)/.test(evt.keyCode)) return;
|
|
40
|
+
evt.preventDefault();
|
|
41
|
+
evt.stopPropagation();
|
|
42
|
+
|
|
43
|
+
// Retrieve focused index
|
|
44
|
+
var items = angular.element($dropdown.$element[0].querySelectorAll('li:not(.divider) a'));
|
|
45
|
+
if(!items.length) return;
|
|
46
|
+
var index;
|
|
47
|
+
angular.forEach(items, function(el, i) {
|
|
48
|
+
if(matchesSelector && matchesSelector.call(el, ':focus')) index = i;
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
// Navigate with keyboard
|
|
52
|
+
if(evt.keyCode === 38 && index > 0) index--;
|
|
53
|
+
else if(evt.keyCode === 40 && index < items.length - 1) index++;
|
|
54
|
+
else if(angular.isUndefined(index)) index = 0;
|
|
55
|
+
items.eq(index)[0].focus();
|
|
56
|
+
|
|
57
|
+
};
|
|
58
|
+
|
|
59
|
+
// Overrides
|
|
60
|
+
|
|
61
|
+
var show = $dropdown.show;
|
|
62
|
+
$dropdown.show = function() {
|
|
63
|
+
show();
|
|
64
|
+
// use timeout to hookup the events to prevent
|
|
65
|
+
// event bubbling from being processed imediately.
|
|
66
|
+
$timeout(function() {
|
|
67
|
+
options.keyboard && $dropdown.$element.on('keydown', $dropdown.$onKeyDown);
|
|
68
|
+
bodyEl.on('click', onBodyClick);
|
|
69
|
+
}, 0, false);
|
|
70
|
+
parentEl.hasClass('dropdown') && parentEl.addClass('open');
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
var hide = $dropdown.hide;
|
|
74
|
+
$dropdown.hide = function() {
|
|
75
|
+
if(!$dropdown.$isShown) return;
|
|
76
|
+
options.keyboard && $dropdown.$element.off('keydown', $dropdown.$onKeyDown);
|
|
77
|
+
bodyEl.off('click', onBodyClick);
|
|
78
|
+
parentEl.hasClass('dropdown') && parentEl.removeClass('open');
|
|
79
|
+
hide();
|
|
80
|
+
};
|
|
81
|
+
|
|
82
|
+
var destroy = $dropdown.destroy;
|
|
83
|
+
$dropdown.destroy = function() {
|
|
84
|
+
bodyEl.off('click', onBodyClick);
|
|
85
|
+
destroy();
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
// Private functions
|
|
89
|
+
|
|
90
|
+
function onBodyClick(evt) {
|
|
91
|
+
if(evt.target === element[0]) return;
|
|
92
|
+
return evt.target !== element[0] && $dropdown.hide();
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
return $dropdown;
|
|
96
|
+
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
return DropdownFactory;
|
|
100
|
+
|
|
101
|
+
};
|
|
102
|
+
|
|
103
|
+
})
|
|
104
|
+
|
|
105
|
+
.directive('bsDropdown', function($window, $sce, $dropdown) {
|
|
106
|
+
|
|
107
|
+
return {
|
|
108
|
+
restrict: 'EAC',
|
|
109
|
+
scope: true,
|
|
110
|
+
link: function postLink(scope, element, attr, transclusion) {
|
|
111
|
+
|
|
112
|
+
// Directive options
|
|
113
|
+
var options = {scope: scope};
|
|
114
|
+
angular.forEach(['placement', 'container', 'delay', 'trigger', 'keyboard', 'html', 'animation', 'template', 'id'], function(key) {
|
|
115
|
+
if(angular.isDefined(attr[key])) options[key] = attr[key];
|
|
116
|
+
});
|
|
117
|
+
|
|
118
|
+
// Support scope as an object
|
|
119
|
+
attr.bsDropdown && scope.$watch(attr.bsDropdown, function(newValue, oldValue) {
|
|
120
|
+
scope.content = newValue;
|
|
121
|
+
}, true);
|
|
122
|
+
|
|
123
|
+
// Visibility binding support
|
|
124
|
+
attr.bsShow && scope.$watch(attr.bsShow, function(newValue, oldValue) {
|
|
125
|
+
if(!dropdown || !angular.isDefined(newValue)) return;
|
|
126
|
+
if(angular.isString(newValue)) newValue = !!newValue.match(/true|,?(dropdown),?/i);
|
|
127
|
+
newValue === true ? dropdown.show() : dropdown.hide();
|
|
128
|
+
});
|
|
129
|
+
|
|
130
|
+
// Initialize dropdown
|
|
131
|
+
var dropdown = $dropdown(element, options);
|
|
132
|
+
|
|
133
|
+
// Garbage collection
|
|
134
|
+
scope.$on('$destroy', function() {
|
|
135
|
+
if (dropdown) dropdown.destroy();
|
|
136
|
+
options = null;
|
|
137
|
+
dropdown = null;
|
|
138
|
+
});
|
|
139
|
+
|
|
140
|
+
}
|
|
141
|
+
};
|
|
142
|
+
|
|
143
|
+
});
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
<ul tabindex="-1" class="dropdown-menu" role="menu">
|
|
2
|
+
<li role="presentation" ng-class="{divider: item.divider}" ng-repeat="item in content" >
|
|
3
|
+
<a role="menuitem" tabindex="-1" ng-href="{{item.href}}" ng-if="!item.divider && item.href" target="{{item.target || ''}}" ng-bind="item.text"></a>
|
|
4
|
+
<a role="menuitem" tabindex="-1" href="javascript:void(0)" ng-if="!item.divider && item.click" ng-click="$eval(item.click);$hide()" ng-bind="item.text"></a>
|
|
5
|
+
</li>
|
|
6
|
+
</ul>
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
angular.module('mgcrea.ngStrap.helpers.dateFormatter', [])
|
|
4
|
+
|
|
5
|
+
.service('$dateFormatter', function($locale, dateFilter) {
|
|
6
|
+
|
|
7
|
+
// The unused `lang` arguments are on purpose. The default implementation does not
|
|
8
|
+
// use them and it always uses the locale loaded into the `$locale` service.
|
|
9
|
+
// Custom implementations might use it, thus allowing different directives to
|
|
10
|
+
// have different languages.
|
|
11
|
+
|
|
12
|
+
this.getDefaultLocale = function() {
|
|
13
|
+
return $locale.id;
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
// Format is either a data format name, e.g. "shortTime" or "fullDate", or a date format
|
|
17
|
+
// Return either the corresponding date format or the given date format.
|
|
18
|
+
this.getDatetimeFormat = function(format, lang) {
|
|
19
|
+
return $locale.DATETIME_FORMATS[format] || format;
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
this.weekdaysShort = function(lang) {
|
|
23
|
+
return $locale.DATETIME_FORMATS.SHORTDAY;
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
function splitTimeFormat(format) {
|
|
27
|
+
return /(h+)([:\.])?(m+)[ ]?(a?)/i.exec(format).slice(1);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
// h:mm a => h
|
|
31
|
+
this.hoursFormat = function(timeFormat) {
|
|
32
|
+
return splitTimeFormat(timeFormat)[0];
|
|
33
|
+
};
|
|
34
|
+
|
|
35
|
+
// h:mm a => mm
|
|
36
|
+
this.minutesFormat = function(timeFormat) {
|
|
37
|
+
return splitTimeFormat(timeFormat)[2];
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
// h:mm a => :
|
|
41
|
+
this.timeSeparator = function(timeFormat) {
|
|
42
|
+
return splitTimeFormat(timeFormat)[1];
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
// h:mm a => true, H.mm => false
|
|
46
|
+
this.showAM = function(timeFormat) {
|
|
47
|
+
return !!splitTimeFormat(timeFormat)[3];
|
|
48
|
+
};
|
|
49
|
+
|
|
50
|
+
this.formatDate = function(date, format, lang){
|
|
51
|
+
return dateFilter(date, format);
|
|
52
|
+
};
|
|
53
|
+
|
|
54
|
+
});
|
|
@@ -0,0 +1,266 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
angular.module('mgcrea.ngStrap.helpers.dateParser', [])
|
|
4
|
+
|
|
5
|
+
.provider('$dateParser', function($localeProvider) {
|
|
6
|
+
|
|
7
|
+
// define a custom ParseDate object to use instead of native Date
|
|
8
|
+
// to avoid date values wrapping when setting date component values
|
|
9
|
+
function ParseDate() {
|
|
10
|
+
this.year = 1970;
|
|
11
|
+
this.month = 0;
|
|
12
|
+
this.day = 1;
|
|
13
|
+
this.hours = 0;
|
|
14
|
+
this.minutes = 0;
|
|
15
|
+
this.seconds = 0;
|
|
16
|
+
this.milliseconds = 0;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
ParseDate.prototype.setMilliseconds = function(value) { this.milliseconds = value; };
|
|
20
|
+
ParseDate.prototype.setSeconds = function(value) { this.seconds = value; };
|
|
21
|
+
ParseDate.prototype.setMinutes = function(value) { this.minutes = value; };
|
|
22
|
+
ParseDate.prototype.setHours = function(value) { this.hours = value; };
|
|
23
|
+
ParseDate.prototype.getHours = function() { return this.hours; };
|
|
24
|
+
ParseDate.prototype.setDate = function(value) { this.day = value; };
|
|
25
|
+
ParseDate.prototype.setMonth = function(value) { this.month = value; };
|
|
26
|
+
ParseDate.prototype.setFullYear = function(value) { this.year = value; };
|
|
27
|
+
ParseDate.prototype.fromDate = function(value) {
|
|
28
|
+
this.year = value.getFullYear();
|
|
29
|
+
this.month = value.getMonth();
|
|
30
|
+
this.day = value.getDate();
|
|
31
|
+
this.hours = value.getHours();
|
|
32
|
+
this.minutes = value.getMinutes();
|
|
33
|
+
this.seconds = value.getSeconds();
|
|
34
|
+
this.milliseconds = value.getMilliseconds();
|
|
35
|
+
return this;
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
ParseDate.prototype.toDate = function() {
|
|
39
|
+
return new Date(this.year, this.month, this.day, this.hours, this.minutes, this.seconds, this.milliseconds);
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
var proto = ParseDate.prototype;
|
|
43
|
+
|
|
44
|
+
function noop() {
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
function isNumeric(n) {
|
|
48
|
+
return !isNaN(parseFloat(n)) && isFinite(n);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
function indexOfCaseInsensitive(array, value) {
|
|
52
|
+
var len = array.length, str=value.toString().toLowerCase();
|
|
53
|
+
for (var i=0; i<len; i++) {
|
|
54
|
+
if (array[i].toLowerCase() === str) { return i; }
|
|
55
|
+
}
|
|
56
|
+
return -1; // Return -1 per the "Array.indexOf()" method.
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
var defaults = this.defaults = {
|
|
60
|
+
format: 'shortDate',
|
|
61
|
+
strict: false
|
|
62
|
+
};
|
|
63
|
+
|
|
64
|
+
this.$get = function($locale, dateFilter) {
|
|
65
|
+
|
|
66
|
+
var DateParserFactory = function(config) {
|
|
67
|
+
|
|
68
|
+
var options = angular.extend({}, defaults, config);
|
|
69
|
+
|
|
70
|
+
var $dateParser = {};
|
|
71
|
+
|
|
72
|
+
var regExpMap = {
|
|
73
|
+
'sss' : '[0-9]{3}',
|
|
74
|
+
'ss' : '[0-5][0-9]',
|
|
75
|
+
's' : options.strict ? '[1-5]?[0-9]' : '[0-9]|[0-5][0-9]',
|
|
76
|
+
'mm' : '[0-5][0-9]',
|
|
77
|
+
'm' : options.strict ? '[1-5]?[0-9]' : '[0-9]|[0-5][0-9]',
|
|
78
|
+
'HH' : '[01][0-9]|2[0-3]',
|
|
79
|
+
'H' : options.strict ? '1?[0-9]|2[0-3]' : '[01]?[0-9]|2[0-3]',
|
|
80
|
+
'hh' : '[0][1-9]|[1][012]',
|
|
81
|
+
'h' : options.strict ? '[1-9]|1[012]' : '0?[1-9]|1[012]',
|
|
82
|
+
'a' : 'AM|PM',
|
|
83
|
+
'EEEE' : $locale.DATETIME_FORMATS.DAY.join('|'),
|
|
84
|
+
'EEE' : $locale.DATETIME_FORMATS.SHORTDAY.join('|'),
|
|
85
|
+
'dd' : '0[1-9]|[12][0-9]|3[01]',
|
|
86
|
+
'd' : options.strict ? '[1-9]|[1-2][0-9]|3[01]' : '0?[1-9]|[1-2][0-9]|3[01]',
|
|
87
|
+
'MMMM' : $locale.DATETIME_FORMATS.MONTH.join('|'),
|
|
88
|
+
'MMM' : $locale.DATETIME_FORMATS.SHORTMONTH.join('|'),
|
|
89
|
+
'MM' : '0[1-9]|1[012]',
|
|
90
|
+
'M' : options.strict ? '[1-9]|1[012]' : '0?[1-9]|1[012]',
|
|
91
|
+
'yyyy' : '[1]{1}[0-9]{3}|[2]{1}[0-9]{3}',
|
|
92
|
+
'yy' : '[0-9]{2}',
|
|
93
|
+
'y' : options.strict ? '-?(0|[1-9][0-9]{0,3})' : '-?0*[0-9]{1,4}',
|
|
94
|
+
};
|
|
95
|
+
|
|
96
|
+
var setFnMap = {
|
|
97
|
+
'sss' : proto.setMilliseconds,
|
|
98
|
+
'ss' : proto.setSeconds,
|
|
99
|
+
's' : proto.setSeconds,
|
|
100
|
+
'mm' : proto.setMinutes,
|
|
101
|
+
'm' : proto.setMinutes,
|
|
102
|
+
'HH' : proto.setHours,
|
|
103
|
+
'H' : proto.setHours,
|
|
104
|
+
'hh' : proto.setHours,
|
|
105
|
+
'h' : proto.setHours,
|
|
106
|
+
'EEEE' : noop,
|
|
107
|
+
'EEE' : noop,
|
|
108
|
+
'dd' : proto.setDate,
|
|
109
|
+
'd' : proto.setDate,
|
|
110
|
+
'a' : function(value) { var hours = this.getHours() % 12; return this.setHours(value.match(/pm/i) ? hours + 12 : hours); },
|
|
111
|
+
'MMMM' : function(value) { return this.setMonth(indexOfCaseInsensitive($locale.DATETIME_FORMATS.MONTH, value)); },
|
|
112
|
+
'MMM' : function(value) { return this.setMonth(indexOfCaseInsensitive($locale.DATETIME_FORMATS.SHORTMONTH, value)); },
|
|
113
|
+
'MM' : function(value) { return this.setMonth(1 * value - 1); },
|
|
114
|
+
'M' : function(value) { return this.setMonth(1 * value - 1); },
|
|
115
|
+
'yyyy' : proto.setFullYear,
|
|
116
|
+
'yy' : function(value) { return this.setFullYear(2000 + 1 * value); },
|
|
117
|
+
'y' : proto.setFullYear
|
|
118
|
+
};
|
|
119
|
+
|
|
120
|
+
var regex, setMap;
|
|
121
|
+
|
|
122
|
+
$dateParser.init = function() {
|
|
123
|
+
$dateParser.$format = $locale.DATETIME_FORMATS[options.format] || options.format;
|
|
124
|
+
regex = regExpForFormat($dateParser.$format);
|
|
125
|
+
setMap = setMapForFormat($dateParser.$format);
|
|
126
|
+
};
|
|
127
|
+
|
|
128
|
+
$dateParser.isValid = function(date) {
|
|
129
|
+
if(angular.isDate(date)) return !isNaN(date.getTime());
|
|
130
|
+
return regex.test(date);
|
|
131
|
+
};
|
|
132
|
+
|
|
133
|
+
$dateParser.parse = function(value, baseDate, format) {
|
|
134
|
+
// check for date format special names
|
|
135
|
+
if(format) format = $locale.DATETIME_FORMATS[format] || format;
|
|
136
|
+
if(angular.isDate(value)) value = dateFilter(value, format || $dateParser.$format);
|
|
137
|
+
var formatRegex = format ? regExpForFormat(format) : regex;
|
|
138
|
+
var formatSetMap = format ? setMapForFormat(format) : setMap;
|
|
139
|
+
var matches = formatRegex.exec(value);
|
|
140
|
+
if(!matches) return false;
|
|
141
|
+
// use custom ParseDate object to set parsed values
|
|
142
|
+
var date = baseDate && !isNaN(baseDate.getTime()) ? new ParseDate().fromDate(baseDate) : new ParseDate().fromDate(new Date(1970, 0, 1, 0));
|
|
143
|
+
for(var i = 0; i < matches.length - 1; i++) {
|
|
144
|
+
formatSetMap[i] && formatSetMap[i].call(date, matches[i+1]);
|
|
145
|
+
}
|
|
146
|
+
// convert back to native Date object
|
|
147
|
+
var newDate = date.toDate();
|
|
148
|
+
|
|
149
|
+
// check new native Date object for day values overflow
|
|
150
|
+
if (parseInt(date.day, 10) !== newDate.getDate()) {
|
|
151
|
+
return false;
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
return newDate;
|
|
155
|
+
};
|
|
156
|
+
|
|
157
|
+
$dateParser.getDateForAttribute = function(key, value) {
|
|
158
|
+
var date;
|
|
159
|
+
|
|
160
|
+
if(value === 'today') {
|
|
161
|
+
var today = new Date();
|
|
162
|
+
date = new Date(today.getFullYear(), today.getMonth(), today.getDate() + (key === 'maxDate' ? 1 : 0), 0, 0, 0, (key === 'minDate' ? 0 : -1));
|
|
163
|
+
} else if(angular.isString(value) && value.match(/^".+"$/)) { // Support {{ dateObj }}
|
|
164
|
+
date = new Date(value.substr(1, value.length - 2));
|
|
165
|
+
} else if(isNumeric(value)) {
|
|
166
|
+
date = new Date(parseInt(value, 10));
|
|
167
|
+
} else if (angular.isString(value) && 0 === value.length) { // Reset date
|
|
168
|
+
date = key === 'minDate' ? -Infinity : +Infinity;
|
|
169
|
+
} else {
|
|
170
|
+
date = new Date(value);
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
return date;
|
|
174
|
+
};
|
|
175
|
+
|
|
176
|
+
$dateParser.getTimeForAttribute = function(key, value) {
|
|
177
|
+
var time;
|
|
178
|
+
|
|
179
|
+
if(value === 'now') {
|
|
180
|
+
time = new Date().setFullYear(1970, 0, 1);
|
|
181
|
+
} else if(angular.isString(value) && value.match(/^".+"$/)) {
|
|
182
|
+
time = new Date(value.substr(1, value.length - 2)).setFullYear(1970, 0, 1);
|
|
183
|
+
} else if(isNumeric(value)) {
|
|
184
|
+
time = new Date(parseInt(value, 10)).setFullYear(1970, 0, 1);
|
|
185
|
+
} else if (angular.isString(value) && 0 === value.length) { // Reset time
|
|
186
|
+
time = key === 'minTime' ? -Infinity : +Infinity;
|
|
187
|
+
} else {
|
|
188
|
+
time = $dateParser.parse(value, new Date(1970, 0, 1, 0));
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
return time;
|
|
192
|
+
};
|
|
193
|
+
|
|
194
|
+
/* Handle switch to/from daylight saving.
|
|
195
|
+
* Hours may be non-zero on daylight saving cut-over:
|
|
196
|
+
* > 12 when midnight changeover, but then cannot generate
|
|
197
|
+
* midnight datetime, so jump to 1AM, otherwise reset.
|
|
198
|
+
* @param date (Date) the date to check
|
|
199
|
+
* @return (Date) the corrected date
|
|
200
|
+
*
|
|
201
|
+
* __ copied from jquery ui datepicker __
|
|
202
|
+
*/
|
|
203
|
+
$dateParser.daylightSavingAdjust = function(date) {
|
|
204
|
+
if (!date) {
|
|
205
|
+
return null;
|
|
206
|
+
}
|
|
207
|
+
date.setHours(date.getHours() > 12 ? date.getHours() + 2 : 0);
|
|
208
|
+
return date;
|
|
209
|
+
};
|
|
210
|
+
|
|
211
|
+
// Private functions
|
|
212
|
+
|
|
213
|
+
function setMapForFormat(format) {
|
|
214
|
+
var keys = Object.keys(setFnMap), i;
|
|
215
|
+
var map = [], sortedMap = [];
|
|
216
|
+
// Map to setFn
|
|
217
|
+
var clonedFormat = format;
|
|
218
|
+
for(i = 0; i < keys.length; i++) {
|
|
219
|
+
if(format.split(keys[i]).length > 1) {
|
|
220
|
+
var index = clonedFormat.search(keys[i]);
|
|
221
|
+
format = format.split(keys[i]).join('');
|
|
222
|
+
if(setFnMap[keys[i]]) {
|
|
223
|
+
map[index] = setFnMap[keys[i]];
|
|
224
|
+
}
|
|
225
|
+
}
|
|
226
|
+
}
|
|
227
|
+
// Sort result map
|
|
228
|
+
angular.forEach(map, function(v) {
|
|
229
|
+
// conditional required since angular.forEach broke around v1.2.21
|
|
230
|
+
// related pr: https://github.com/angular/angular.js/pull/8525
|
|
231
|
+
if(v) sortedMap.push(v);
|
|
232
|
+
});
|
|
233
|
+
return sortedMap;
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
function escapeReservedSymbols(text) {
|
|
237
|
+
return text.replace(/\//g, '[\\/]').replace('/-/g', '[-]').replace(/\./g, '[.]').replace(/\\s/g, '[\\s]');
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
function regExpForFormat(format) {
|
|
241
|
+
var keys = Object.keys(regExpMap), i;
|
|
242
|
+
|
|
243
|
+
var re = format;
|
|
244
|
+
// Abstract replaces to avoid collisions
|
|
245
|
+
for(i = 0; i < keys.length; i++) {
|
|
246
|
+
re = re.split(keys[i]).join('${' + i + '}');
|
|
247
|
+
}
|
|
248
|
+
// Replace abstracted values
|
|
249
|
+
for(i = 0; i < keys.length; i++) {
|
|
250
|
+
re = re.split('${' + i + '}').join('(' + regExpMap[keys[i]] + ')');
|
|
251
|
+
}
|
|
252
|
+
format = escapeReservedSymbols(format);
|
|
253
|
+
|
|
254
|
+
return new RegExp('^' + re + '$', ['i']);
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
$dateParser.init();
|
|
258
|
+
return $dateParser;
|
|
259
|
+
|
|
260
|
+
};
|
|
261
|
+
|
|
262
|
+
return DateParserFactory;
|
|
263
|
+
|
|
264
|
+
};
|
|
265
|
+
|
|
266
|
+
});
|