flashoff 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (73) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +17 -0
  3. data/Gemfile +4 -0
  4. data/LICENSE.txt +22 -0
  5. data/README.md +74 -0
  6. data/Rakefile +1 -0
  7. data/app/assets/fonts/gotham/gotham-bold.eot +0 -0
  8. data/app/assets/fonts/gotham/gotham-bold.svg +2066 -0
  9. data/app/assets/fonts/gotham/gotham-bold.ttf +0 -0
  10. data/app/assets/fonts/gotham/gotham-bold.woff +0 -0
  11. data/app/assets/fonts/gotham/gotham-book.eot +0 -0
  12. data/app/assets/fonts/gotham/gotham-book.svg +631 -0
  13. data/app/assets/fonts/gotham/gotham-book.ttf +0 -0
  14. data/app/assets/fonts/gotham/gotham-book.woff +0 -0
  15. data/app/assets/fonts/gotham/gotham-light.eot +0 -0
  16. data/app/assets/fonts/gotham/gotham-light.svg +635 -0
  17. data/app/assets/fonts/gotham/gotham-light.ttf +0 -0
  18. data/app/assets/fonts/gotham/gotham-light.woff +0 -0
  19. data/app/assets/fonts/gotham/gotham-medium.eot +0 -0
  20. data/app/assets/fonts/gotham/gotham-medium.svg +629 -0
  21. data/app/assets/fonts/gotham/gotham-medium.ttf +0 -0
  22. data/app/assets/fonts/gotham/gotham-medium.woff +0 -0
  23. data/app/assets/fonts/ionicons/ionicons.eot +0 -0
  24. data/app/assets/fonts/ionicons/ionicons.svg +1390 -0
  25. data/app/assets/fonts/ionicons/ionicons.ttf +0 -0
  26. data/app/assets/fonts/ionicons/ionicons.woff +0 -0
  27. data/flashoff.gemspec +23 -0
  28. data/lib/flashoff/version.rb +3 -0
  29. data/lib/flashoff.rb +5 -0
  30. data/vendor/assets/javascripts/alert.js +78 -0
  31. data/vendor/assets/javascripts/collapse.js +159 -0
  32. data/vendor/assets/javascripts/date_picker.js +1385 -0
  33. data/vendor/assets/javascripts/dropdown.js +134 -0
  34. data/vendor/assets/javascripts/file_input.js +88 -0
  35. data/vendor/assets/javascripts/map.js +2036 -0
  36. data/vendor/assets/javascripts/modal.js +226 -0
  37. data/vendor/assets/javascripts/popover.js +97 -0
  38. data/vendor/assets/javascripts/tab.js +115 -0
  39. data/vendor/assets/javascripts/time_picker.js +878 -0
  40. data/vendor/assets/javascripts/tooltip.js +365 -0
  41. data/vendor/assets/javascripts/transition.js +36 -0
  42. data/vendor/assets/stylesheets/ad.css.scss +72 -0
  43. data/vendor/assets/stylesheets/alert.css.scss +57 -0
  44. data/vendor/assets/stylesheets/breadcrumb.css.scss +26 -0
  45. data/vendor/assets/stylesheets/button.css.scss +183 -0
  46. data/vendor/assets/stylesheets/code.css.scss +49 -0
  47. data/vendor/assets/stylesheets/collapse.css.scss +15 -0
  48. data/vendor/assets/stylesheets/datepicker.css.scss +104 -0
  49. data/vendor/assets/stylesheets/dropdown.css.scss +84 -0
  50. data/vendor/assets/stylesheets/footer.css.scss +33 -0
  51. data/vendor/assets/stylesheets/form.css.scss +213 -0
  52. data/vendor/assets/stylesheets/grid.css.scss +291 -0
  53. data/vendor/assets/stylesheets/header.css.scss +134 -0
  54. data/vendor/assets/stylesheets/icon.css.scss +972 -0
  55. data/vendor/assets/stylesheets/image.css.scss +39 -0
  56. data/vendor/assets/stylesheets/label_and_badge.css.scss +53 -0
  57. data/vendor/assets/stylesheets/link.css.scss +19 -0
  58. data/vendor/assets/stylesheets/list.css.scss +38 -0
  59. data/vendor/assets/stylesheets/map.css.scss +13 -0
  60. data/vendor/assets/stylesheets/modal.css.scss +117 -0
  61. data/vendor/assets/stylesheets/pagination.css.scss +37 -0
  62. data/vendor/assets/stylesheets/placeholder.css.scss +11 -0
  63. data/vendor/assets/stylesheets/popover.css.scss +107 -0
  64. data/vendor/assets/stylesheets/progress.css.scss +25 -0
  65. data/vendor/assets/stylesheets/reset.css.scss +57 -0
  66. data/vendor/assets/stylesheets/tab.css.scss +165 -0
  67. data/vendor/assets/stylesheets/table.css.scss +70 -0
  68. data/vendor/assets/stylesheets/timepicker.css.scss +69 -0
  69. data/vendor/assets/stylesheets/tooltip.css.scss +81 -0
  70. data/vendor/assets/stylesheets/transition.css.scss +12 -0
  71. data/vendor/assets/stylesheets/trunk.css.scss +69 -0
  72. data/vendor/assets/stylesheets/typography.css.scss +147 -0
  73. metadata +144 -0
@@ -0,0 +1,878 @@
1
+ (function($, window, document, undefined) {
2
+ 'use strict';
3
+
4
+ // TIMEPICKER PUBLIC CLASS DEFINITION
5
+ var Timepicker = function(element, options) {
6
+ this.widget = '';
7
+ this.$element = $(element);
8
+ this.defaultTime = options.defaultTime;
9
+ this.disableFocus = options.disableFocus;
10
+ this.isOpen = options.isOpen;
11
+ this.minuteStep = options.minuteStep;
12
+ this.modalBackdrop = options.modalBackdrop;
13
+ this.secondStep = options.secondStep;
14
+ this.showInputs = options.showInputs;
15
+ this.showMeridian = options.showMeridian;
16
+ this.showSeconds = options.showSeconds;
17
+ this.template = options.template;
18
+ this.appendWidgetTo = options.appendWidgetTo;
19
+
20
+ this._init();
21
+ };
22
+
23
+ Timepicker.prototype = {
24
+
25
+ constructor: Timepicker,
26
+
27
+ _init: function() {
28
+ var self = this;
29
+
30
+ if (this.$element.parent().hasClass('input-append') || this.$element.parent().hasClass('input-prepend')) {
31
+ this.$element.parent('.input-append, .input-prepend').find('.add-on').on({
32
+ 'click.timepicker': $.proxy(this.showWidget, this)
33
+ });
34
+ this.$element.on({
35
+ 'focus.timepicker': $.proxy(this.highlightUnit, this),
36
+ 'click.timepicker': $.proxy(this.highlightUnit, this),
37
+ 'keydown.timepicker': $.proxy(this.elementKeydown, this),
38
+ 'blur.timepicker': $.proxy(this.blurElement, this)
39
+ });
40
+ } else {
41
+ if (this.template) {
42
+ this.$element.on({
43
+ 'focus.timepicker': $.proxy(this.showWidget, this),
44
+ 'click.timepicker': $.proxy(this.showWidget, this),
45
+ 'blur.timepicker': $.proxy(this.blurElement, this)
46
+ });
47
+ } else {
48
+ this.$element.on({
49
+ 'focus.timepicker': $.proxy(this.highlightUnit, this),
50
+ 'click.timepicker': $.proxy(this.highlightUnit, this),
51
+ 'keydown.timepicker': $.proxy(this.elementKeydown, this),
52
+ 'blur.timepicker': $.proxy(this.blurElement, this)
53
+ });
54
+ }
55
+ }
56
+
57
+ if (this.template !== false) {
58
+ this.$widget = $(this.getTemplate()).prependTo(this.$element.parents(this.appendWidgetTo)).on('click', $.proxy(this.widgetClick, this));
59
+ } else {
60
+ this.$widget = false;
61
+ }
62
+
63
+ if (this.showInputs && this.$widget !== false) {
64
+ this.$widget.find('input').each(function() {
65
+ $(this).on({
66
+ 'click.timepicker': function() { $(this).select(); },
67
+ 'keydown.timepicker': $.proxy(self.widgetKeydown, self)
68
+ });
69
+ });
70
+ }
71
+
72
+ this.setDefaultTime(this.defaultTime);
73
+ },
74
+
75
+ blurElement: function() {
76
+ this.highlightedUnit = undefined;
77
+ this.updateFromElementVal();
78
+ },
79
+
80
+ decrementHour: function() {
81
+ if (this.showMeridian) {
82
+ if (this.hour === 1) {
83
+ this.hour = 12;
84
+ } else if (this.hour === 12) {
85
+ this.hour--;
86
+
87
+ return this.toggleMeridian();
88
+ } else if (this.hour === 0) {
89
+ this.hour = 11;
90
+
91
+ return this.toggleMeridian();
92
+ } else {
93
+ this.hour--;
94
+ }
95
+ } else {
96
+ if (this.hour === 0) {
97
+ this.hour = 23;
98
+ } else {
99
+ this.hour--;
100
+ }
101
+ }
102
+ this.update();
103
+ },
104
+
105
+ decrementMinute: function(step) {
106
+ var newVal;
107
+
108
+ if (step) {
109
+ newVal = this.minute - step;
110
+ } else {
111
+ newVal = this.minute - this.minuteStep;
112
+ }
113
+
114
+ if (newVal < 0) {
115
+ this.decrementHour();
116
+ this.minute = newVal + 60;
117
+ } else {
118
+ this.minute = newVal;
119
+ }
120
+ this.update();
121
+ },
122
+
123
+ decrementSecond: function() {
124
+ var newVal = this.second - this.secondStep;
125
+
126
+ if (newVal < 0) {
127
+ this.decrementMinute(true);
128
+ this.second = newVal + 60;
129
+ } else {
130
+ this.second = newVal;
131
+ }
132
+ this.update();
133
+ },
134
+
135
+ elementKeydown: function(e) {
136
+ switch (e.keyCode) {
137
+ case 9: //tab
138
+ this.updateFromElementVal();
139
+
140
+ switch (this.highlightedUnit) {
141
+ case 'hour':
142
+ e.preventDefault();
143
+ this.highlightNextUnit();
144
+ break;
145
+ case 'minute':
146
+ if (this.showMeridian || this.showSeconds) {
147
+ e.preventDefault();
148
+ this.highlightNextUnit();
149
+ }
150
+ break;
151
+ case 'second':
152
+ if (this.showMeridian) {
153
+ e.preventDefault();
154
+ this.highlightNextUnit();
155
+ }
156
+ break;
157
+ }
158
+ break;
159
+ case 27: // escape
160
+ this.updateFromElementVal();
161
+ break;
162
+ case 37: // left arrow
163
+ e.preventDefault();
164
+ this.highlightPrevUnit();
165
+ this.updateFromElementVal();
166
+ break;
167
+ case 38: // up arrow
168
+ e.preventDefault();
169
+ switch (this.highlightedUnit) {
170
+ case 'hour':
171
+ this.incrementHour();
172
+ this.highlightHour();
173
+ break;
174
+ case 'minute':
175
+ this.incrementMinute();
176
+ this.highlightMinute();
177
+ break;
178
+ case 'second':
179
+ this.incrementSecond();
180
+ this.highlightSecond();
181
+ break;
182
+ case 'meridian':
183
+ this.toggleMeridian();
184
+ this.highlightMeridian();
185
+ break;
186
+ }
187
+ break;
188
+ case 39: // right arrow
189
+ e.preventDefault();
190
+ this.updateFromElementVal();
191
+ this.highlightNextUnit();
192
+ break;
193
+ case 40: // down arrow
194
+ e.preventDefault();
195
+ switch (this.highlightedUnit) {
196
+ case 'hour':
197
+ this.decrementHour();
198
+ this.highlightHour();
199
+ break;
200
+ case 'minute':
201
+ this.decrementMinute();
202
+ this.highlightMinute();
203
+ break;
204
+ case 'second':
205
+ this.decrementSecond();
206
+ this.highlightSecond();
207
+ break;
208
+ case 'meridian':
209
+ this.toggleMeridian();
210
+ this.highlightMeridian();
211
+ break;
212
+ }
213
+ break;
214
+ }
215
+ },
216
+
217
+ formatTime: function(hour, minute, second, meridian) {
218
+ hour = hour < 10 ? '0' + hour : hour;
219
+ minute = minute < 10 ? '0' + minute : minute;
220
+ second = second < 10 ? '0' + second : second;
221
+
222
+ return hour + ':' + minute + (this.showSeconds ? ':' + second : '') + (this.showMeridian ? ' ' + meridian : '');
223
+ },
224
+
225
+ getCursorPosition: function() {
226
+ var input = this.$element.get(0);
227
+
228
+ if ('selectionStart' in input) {// Standard-compliant browsers
229
+
230
+ return input.selectionStart;
231
+ } else if (document.selection) {// IE fix
232
+ input.focus();
233
+ var sel = document.selection.createRange(),
234
+ selLen = document.selection.createRange().text.length;
235
+
236
+ sel.moveStart('character', - input.value.length);
237
+
238
+ return sel.text.length - selLen;
239
+ }
240
+ },
241
+
242
+ getTemplate: function() {
243
+ var template,
244
+ hourTemplate,
245
+ minuteTemplate,
246
+ secondTemplate,
247
+ meridianTemplate,
248
+ templateContent;
249
+
250
+ if (this.showInputs) {
251
+ hourTemplate = '<input type="text" name="hour" class="timepicker-hour" maxlength="2"/>';
252
+ minuteTemplate = '<input type="text" name="minute" class="timepicker-minute" maxlength="2"/>';
253
+ secondTemplate = '<input type="text" name="second" class="timepicker-second" maxlength="2"/>';
254
+ meridianTemplate = '<input type="text" name="meridian" class="timepicker-meridian" maxlength="2"/>';
255
+ } else {
256
+ hourTemplate = '<span class="timepicker-hour"></span>';
257
+ minuteTemplate = '<span class="timepicker-minute"></span>';
258
+ secondTemplate = '<span class="timepicker-second"></span>';
259
+ meridianTemplate = '<span class="timepicker-meridian"></span>';
260
+ }
261
+
262
+ templateContent = '<table>'+
263
+ '<tr>'+
264
+ '<td><a href="#" data-action="incrementHour"><i class="icon-chevron-up"></i></a></td>'+
265
+ '<td class="separator">&nbsp;</td>'+
266
+ '<td><a href="#" data-action="incrementMinute"><i class="icon-chevron-up"></i></a></td>'+
267
+ (this.showSeconds ?
268
+ '<td class="separator">&nbsp;</td>'+
269
+ '<td><a href="#" data-action="incrementSecond"><i class="icon-chevron-up"></i></a></td>'
270
+ : '') +
271
+ (this.showMeridian ?
272
+ '<td class="separator">&nbsp;</td>'+
273
+ '<td class="meridian-column"><a href="#" data-action="toggleMeridian"><i class="icon-chevron-up"></i></a></td>'
274
+ : '') +
275
+ '</tr>'+
276
+ '<tr>'+
277
+ '<td>'+ hourTemplate +'</td> '+
278
+ '<td class="separator">:</td>'+
279
+ '<td>'+ minuteTemplate +'</td> '+
280
+ (this.showSeconds ?
281
+ '<td class="separator">:</td>'+
282
+ '<td>'+ secondTemplate +'</td>'
283
+ : '') +
284
+ (this.showMeridian ?
285
+ '<td class="separator">&nbsp;</td>'+
286
+ '<td>'+ meridianTemplate +'</td>'
287
+ : '') +
288
+ '</tr>'+
289
+ '<tr>'+
290
+ '<td><a href="#" data-action="decrementHour"><i class="icon-chevron-down"></i></a></td>'+
291
+ '<td class="separator"></td>'+
292
+ '<td><a href="#" data-action="decrementMinute"><i class="icon-chevron-down"></i></a></td>'+
293
+ (this.showSeconds ?
294
+ '<td class="separator">&nbsp;</td>'+
295
+ '<td><a href="#" data-action="decrementSecond"><i class="icon-chevron-down"></i></a></td>'
296
+ : '') +
297
+ (this.showMeridian ?
298
+ '<td class="separator">&nbsp;</td>'+
299
+ '<td><a href="#" data-action="toggleMeridian"><i class="icon-chevron-down"></i></a></td>'
300
+ : '') +
301
+ '</tr>'+
302
+ '</table>';
303
+
304
+ switch(this.template) {
305
+ case 'modal':
306
+ template = '<div class="timepicker-widget modal hide fade in" data-backdrop="'+ (this.modalBackdrop ? 'true' : 'false') +'">'+
307
+ '<div class="modal-header">'+
308
+ '<a href="#" class="close" data-dismiss="modal">×</a>'+
309
+ '<h3>Pick a Time</h3>'+
310
+ '</div>'+
311
+ '<div class="modal-content">'+
312
+ templateContent +
313
+ '</div>'+
314
+ '<div class="modal-footer">'+
315
+ '<a href="#" class="btn btn-primary" data-dismiss="modal">OK</a>'+
316
+ '</div>'+
317
+ '</div>';
318
+ break;
319
+ case 'dropdown':
320
+ template = '<div class="timepicker-widget dropdown-menu">'+ templateContent +'</div>';
321
+ break;
322
+ }
323
+
324
+ return template;
325
+ },
326
+
327
+ getTime: function() {
328
+ return this.formatTime(this.hour, this.minute, this.second, this.meridian);
329
+ },
330
+
331
+ hideWidget: function() {
332
+ if (this.isOpen === false) {
333
+ return;
334
+ }
335
+
336
+ if (this.showInputs) {
337
+ this.updateFromWidgetInputs();
338
+ }
339
+
340
+ this.$element.trigger({
341
+ 'type': 'hide.timepicker',
342
+ 'time': {
343
+ 'value': this.getTime(),
344
+ 'hours': this.hour,
345
+ 'minutes': this.minute,
346
+ 'seconds': this.second,
347
+ 'meridian': this.meridian
348
+ }
349
+ });
350
+
351
+ if (this.template === 'modal' && this.$widget.modal) {
352
+ this.$widget.modal('hide');
353
+ } else {
354
+ this.$widget.removeClass('open');
355
+ }
356
+
357
+ $(document).off('mousedown.timepicker');
358
+
359
+ this.isOpen = false;
360
+ },
361
+
362
+ highlightUnit: function() {
363
+ this.position = this.getCursorPosition();
364
+ if (this.position >= 0 && this.position <= 2) {
365
+ this.highlightHour();
366
+ } else if (this.position >= 3 && this.position <= 5) {
367
+ this.highlightMinute();
368
+ } else if (this.position >= 6 && this.position <= 8) {
369
+ if (this.showSeconds) {
370
+ this.highlightSecond();
371
+ } else {
372
+ this.highlightMeridian();
373
+ }
374
+ } else if (this.position >= 9 && this.position <= 11) {
375
+ this.highlightMeridian();
376
+ }
377
+ },
378
+
379
+ highlightNextUnit: function() {
380
+ switch (this.highlightedUnit) {
381
+ case 'hour':
382
+ this.highlightMinute();
383
+ break;
384
+ case 'minute':
385
+ if (this.showSeconds) {
386
+ this.highlightSecond();
387
+ } else if (this.showMeridian){
388
+ this.highlightMeridian();
389
+ } else {
390
+ this.highlightHour();
391
+ }
392
+ break;
393
+ case 'second':
394
+ if (this.showMeridian) {
395
+ this.highlightMeridian();
396
+ } else {
397
+ this.highlightHour();
398
+ }
399
+ break;
400
+ case 'meridian':
401
+ this.highlightHour();
402
+ break;
403
+ }
404
+ },
405
+
406
+ highlightPrevUnit: function() {
407
+ switch (this.highlightedUnit) {
408
+ case 'hour':
409
+ this.highlightMeridian();
410
+ break;
411
+ case 'minute':
412
+ this.highlightHour();
413
+ break;
414
+ case 'second':
415
+ this.highlightMinute();
416
+ break;
417
+ case 'meridian':
418
+ if (this.showSeconds) {
419
+ this.highlightSecond();
420
+ } else {
421
+ this.highlightMinute();
422
+ }
423
+ break;
424
+ }
425
+ },
426
+
427
+ highlightHour: function() {
428
+ var $element = this.$element.get(0);
429
+
430
+ this.highlightedUnit = 'hour';
431
+
432
+ if ($element.setSelectionRange) {
433
+ setTimeout(function() {
434
+ $element.setSelectionRange(0,2);
435
+ }, 0);
436
+ }
437
+ },
438
+
439
+ highlightMinute: function() {
440
+ var $element = this.$element.get(0);
441
+
442
+ this.highlightedUnit = 'minute';
443
+
444
+ if ($element.setSelectionRange) {
445
+ setTimeout(function() {
446
+ $element.setSelectionRange(3,5);
447
+ }, 0);
448
+ }
449
+ },
450
+
451
+ highlightSecond: function() {
452
+ var $element = this.$element.get(0);
453
+
454
+ this.highlightedUnit = 'second';
455
+
456
+ if ($element.setSelectionRange) {
457
+ setTimeout(function() {
458
+ $element.setSelectionRange(6,8);
459
+ }, 0);
460
+ }
461
+ },
462
+
463
+ highlightMeridian: function() {
464
+ var $element = this.$element.get(0);
465
+
466
+ this.highlightedUnit = 'meridian';
467
+
468
+ if ($element.setSelectionRange) {
469
+ if (this.showSeconds) {
470
+ setTimeout(function() {
471
+ $element.setSelectionRange(9,11);
472
+ }, 0);
473
+ } else {
474
+ setTimeout(function() {
475
+ $element.setSelectionRange(6,8);
476
+ }, 0);
477
+ }
478
+ }
479
+ },
480
+
481
+ incrementHour: function() {
482
+ if (this.showMeridian) {
483
+ if (this.hour === 11) {
484
+ this.hour++;
485
+ return this.toggleMeridian();
486
+ } else if (this.hour === 12) {
487
+ this.hour = 0;
488
+ }
489
+ }
490
+ if (this.hour === 23) {
491
+ this.hour = 0;
492
+
493
+ return;
494
+ }
495
+ this.hour++;
496
+ this.update();
497
+ },
498
+
499
+ incrementMinute: function(step) {
500
+ var newVal;
501
+
502
+ if (step) {
503
+ newVal = this.minute + step;
504
+ } else {
505
+ newVal = this.minute + this.minuteStep - (this.minute % this.minuteStep);
506
+ }
507
+
508
+ if (newVal > 59) {
509
+ this.incrementHour();
510
+ this.minute = newVal - 60;
511
+ } else {
512
+ this.minute = newVal;
513
+ }
514
+ this.update();
515
+ },
516
+
517
+ incrementSecond: function() {
518
+ var newVal = this.second + this.secondStep - (this.second % this.secondStep);
519
+
520
+ if (newVal > 59) {
521
+ this.incrementMinute(true);
522
+ this.second = newVal - 60;
523
+ } else {
524
+ this.second = newVal;
525
+ }
526
+ this.update();
527
+ },
528
+
529
+ remove: function() {
530
+ $('document').off('.timepicker');
531
+ if (this.$widget) {
532
+ this.$widget.remove();
533
+ }
534
+ delete this.$element.data().timepicker;
535
+ },
536
+
537
+ setDefaultTime: function(defaultTime){
538
+ if (!this.$element.val()) {
539
+ if (defaultTime === 'current') {
540
+ var dTime = new Date(),
541
+ hours = dTime.getHours(),
542
+ minutes = Math.floor(dTime.getMinutes() / this.minuteStep) * this.minuteStep,
543
+ seconds = Math.floor(dTime.getSeconds() / this.secondStep) * this.secondStep,
544
+ meridian = 'AM';
545
+
546
+ if (this.showMeridian) {
547
+ if (hours === 0) {
548
+ hours = 12;
549
+ } else if (hours >= 12) {
550
+ if (hours > 12) {
551
+ hours = hours - 12;
552
+ }
553
+ meridian = 'PM';
554
+ } else {
555
+ meridian = 'AM';
556
+ }
557
+ }
558
+
559
+ this.hour = hours;
560
+ this.minute = minutes;
561
+ this.second = seconds;
562
+ this.meridian = meridian;
563
+
564
+ this.update();
565
+
566
+ } else if (defaultTime === false) {
567
+ this.hour = 0;
568
+ this.minute = 0;
569
+ this.second = 0;
570
+ this.meridian = 'AM';
571
+ } else {
572
+ this.setTime(defaultTime);
573
+ }
574
+ } else {
575
+ this.updateFromElementVal();
576
+ }
577
+ },
578
+
579
+ setTime: function(time) {
580
+ var arr,
581
+ timeArray;
582
+
583
+ if (this.showMeridian) {
584
+ arr = time.split(' ');
585
+ timeArray = arr[0].split(':');
586
+ this.meridian = arr[1];
587
+ } else {
588
+ timeArray = time.split(':');
589
+ }
590
+
591
+ this.hour = parseInt(timeArray[0], 10);
592
+ this.minute = parseInt(timeArray[1], 10);
593
+ this.second = parseInt(timeArray[2], 10);
594
+
595
+ if (isNaN(this.hour)) {
596
+ this.hour = 0;
597
+ }
598
+ if (isNaN(this.minute)) {
599
+ this.minute = 0;
600
+ }
601
+
602
+ if (this.showMeridian) {
603
+ if (this.hour > 12) {
604
+ this.hour = 12;
605
+ } else if (this.hour < 1) {
606
+ this.hour = 12;
607
+ }
608
+
609
+ if (this.meridian === 'am' || this.meridian === 'a') {
610
+ this.meridian = 'AM';
611
+ } else if (this.meridian === 'pm' || this.meridian === 'p') {
612
+ this.meridian = 'PM';
613
+ }
614
+
615
+ if (this.meridian !== 'AM' && this.meridian !== 'PM') {
616
+ this.meridian = 'AM';
617
+ }
618
+ } else {
619
+ if (this.hour >= 24) {
620
+ this.hour = 23;
621
+ } else if (this.hour < 0) {
622
+ this.hour = 0;
623
+ }
624
+ }
625
+
626
+ if (this.minute < 0) {
627
+ this.minute = 0;
628
+ } else if (this.minute >= 60) {
629
+ this.minute = 59;
630
+ }
631
+
632
+ if (this.showSeconds) {
633
+ if (isNaN(this.second)) {
634
+ this.second = 0;
635
+ } else if (this.second < 0) {
636
+ this.second = 0;
637
+ } else if (this.second >= 60) {
638
+ this.second = 59;
639
+ }
640
+ }
641
+
642
+ this.update();
643
+ },
644
+
645
+ showWidget: function() {
646
+ if (this.isOpen) {
647
+ return;
648
+ }
649
+
650
+ if (this.$element.is(':disabled')) {
651
+ return;
652
+ }
653
+
654
+ var self = this;
655
+ $(document).on('mousedown.timepicker', function (e) {
656
+ // Clicked outside the timepicker, hide it
657
+ if ($(e.target).closest('.timepicker-widget').length === 0) {
658
+ self.hideWidget();
659
+ }
660
+ });
661
+
662
+ this.$element.trigger({
663
+ 'type': 'show.timepicker',
664
+ 'time': {
665
+ 'value': this.getTime(),
666
+ 'hours': this.hour,
667
+ 'minutes': this.minute,
668
+ 'seconds': this.second,
669
+ 'meridian': this.meridian
670
+ }
671
+ });
672
+
673
+ if (this.disableFocus) {
674
+ this.$element.blur();
675
+ }
676
+
677
+ this.updateFromElementVal();
678
+
679
+ if (this.template === 'modal' && this.$widget.modal) {
680
+ this.$widget.modal('show').on('hidden', $.proxy(this.hideWidget, this));
681
+ } else {
682
+ if (this.isOpen === false) {
683
+ this.$widget.addClass('open');
684
+ }
685
+ }
686
+
687
+ this.isOpen = true;
688
+ },
689
+
690
+ toggleMeridian: function() {
691
+ this.meridian = this.meridian === 'AM' ? 'PM' : 'AM';
692
+ this.update();
693
+ },
694
+
695
+ update: function() {
696
+ this.$element.trigger({
697
+ 'type': 'changeTime.timepicker',
698
+ 'time': {
699
+ 'value': this.getTime(),
700
+ 'hours': this.hour,
701
+ 'minutes': this.minute,
702
+ 'seconds': this.second,
703
+ 'meridian': this.meridian
704
+ }
705
+ });
706
+
707
+ this.updateElement();
708
+ this.updateWidget();
709
+ },
710
+
711
+ updateElement: function() {
712
+ this.$element.val(this.getTime()).change();
713
+ },
714
+
715
+ updateFromElementVal: function() {
716
+ var val = this.$element.val();
717
+
718
+ if (val) {
719
+ this.setTime(val);
720
+ }
721
+ },
722
+
723
+ updateWidget: function() {
724
+ if (this.$widget === false) {
725
+ return;
726
+ }
727
+
728
+ var hour = this.hour < 10 ? '0' + this.hour : this.hour,
729
+ minute = this.minute < 10 ? '0' + this.minute : this.minute,
730
+ second = this.second < 10 ? '0' + this.second : this.second;
731
+
732
+ if (this.showInputs) {
733
+ this.$widget.find('input.timepicker-hour').val(hour);
734
+ this.$widget.find('input.timepicker-minute').val(minute);
735
+
736
+ if (this.showSeconds) {
737
+ this.$widget.find('input.timepicker-second').val(second);
738
+ }
739
+ if (this.showMeridian) {
740
+ this.$widget.find('input.timepicker-meridian').val(this.meridian);
741
+ }
742
+ } else {
743
+ this.$widget.find('span.timepicker-hour').text(hour);
744
+ this.$widget.find('span.timepicker-minute').text(minute);
745
+
746
+ if (this.showSeconds) {
747
+ this.$widget.find('span.timepicker-second').text(second);
748
+ }
749
+ if (this.showMeridian) {
750
+ this.$widget.find('span.timepicker-meridian').text(this.meridian);
751
+ }
752
+ }
753
+ },
754
+
755
+ updateFromWidgetInputs: function() {
756
+ if (this.$widget === false) {
757
+ return;
758
+ }
759
+ var time = $('input.timepicker-hour', this.$widget).val() + ':' +
760
+ $('input.timepicker-minute', this.$widget).val() +
761
+ (this.showSeconds ? ':' + $('input.timepicker-second', this.$widget).val() : '') +
762
+ (this.showMeridian ? ' ' + $('input.timepicker-meridian', this.$widget).val() : '');
763
+
764
+ this.setTime(time);
765
+ },
766
+
767
+ widgetClick: function(e) {
768
+ e.stopPropagation();
769
+ e.preventDefault();
770
+
771
+ var action = $(e.target).closest('a').data('action');
772
+ if (action) {
773
+ this[action]();
774
+ }
775
+ },
776
+
777
+ widgetKeydown: function(e) {
778
+ var $input = $(e.target).closest('input'),
779
+ name = $input.attr('name');
780
+
781
+ switch (e.keyCode) {
782
+ case 9: //tab
783
+ if (this.showMeridian) {
784
+ if (name === 'meridian') {
785
+ return this.hideWidget();
786
+ }
787
+ } else {
788
+ if (this.showSeconds) {
789
+ if (name === 'second') {
790
+ return this.hideWidget();
791
+ }
792
+ } else {
793
+ if (name === 'minute') {
794
+ return this.hideWidget();
795
+ }
796
+ }
797
+ }
798
+
799
+ this.updateFromWidgetInputs();
800
+ break;
801
+ case 27: // escape
802
+ this.hideWidget();
803
+ break;
804
+ case 38: // up arrow
805
+ e.preventDefault();
806
+ switch (name) {
807
+ case 'hour':
808
+ this.incrementHour();
809
+ break;
810
+ case 'minute':
811
+ this.incrementMinute();
812
+ break;
813
+ case 'second':
814
+ this.incrementSecond();
815
+ break;
816
+ case 'meridian':
817
+ this.toggleMeridian();
818
+ break;
819
+ }
820
+ break;
821
+ case 40: // down arrow
822
+ e.preventDefault();
823
+ switch (name) {
824
+ case 'hour':
825
+ this.decrementHour();
826
+ break;
827
+ case 'minute':
828
+ this.decrementMinute();
829
+ break;
830
+ case 'second':
831
+ this.decrementSecond();
832
+ break;
833
+ case 'meridian':
834
+ this.toggleMeridian();
835
+ break;
836
+ }
837
+ break;
838
+ }
839
+ }
840
+ };
841
+
842
+
843
+ //TIMEPICKER PLUGIN DEFINITION
844
+ $.fn.timepicker = function(option) {
845
+ var args = Array.apply(null, arguments);
846
+ args.shift();
847
+ return this.each(function() {
848
+ var $this = $(this),
849
+ data = $this.data('timepicker'),
850
+ options = typeof option === 'object' && option;
851
+
852
+ if (!data) {
853
+ $this.data('timepicker', (data = new Timepicker(this, $.extend({}, $.fn.timepicker.defaults, options, $(this).data()))));
854
+ }
855
+
856
+ if (typeof option === 'string') {
857
+ data[option].apply(data, args);
858
+ }
859
+ });
860
+ };
861
+
862
+ $.fn.timepicker.defaults = {
863
+ defaultTime: 'current',
864
+ disableFocus: false,
865
+ isOpen: false,
866
+ minuteStep: 15,
867
+ modalBackdrop: false,
868
+ secondStep: 15,
869
+ showSeconds: false,
870
+ showInputs: true,
871
+ showMeridian: true,
872
+ template: 'dropdown',
873
+ appendWidgetTo: '.timepicker'
874
+ };
875
+
876
+ $.fn.timepicker.Constructor = Timepicker;
877
+
878
+ })(jQuery, window, document);