view bootstrap-year-calendar/bootstrap-year-calendar.js @ 107:24a967efbf3e

add dmd
author paulo
date Fri, 03 Apr 2020 23:58:24 -0700
parents
children
line source
1 /* =========================================================
2 * Bootstrap year calendar v1.1.0
3 * Repo: https://github.com/Paul-DS/bootstrap-year-calendar
4 * =========================================================
5 * Created by Paul David-Sivelle
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 * ========================================================= */
20 (function($) {
21 var Calendar = function(element, options) {
22 this.element = element;
23 this.element.addClass('calendar');
25 this._initializeEvents(options);
26 this._initializeOptions(options);
27 this._render();
28 };
30 Calendar.prototype = {
31 constructor: Calendar,
32 _initializeOptions: function(opt) {
33 if(opt == null) {
34 opt = [];
35 }
37 this.options = {
38 startYear: !isNaN(parseInt(opt.startYear)) ? parseInt(opt.startYear) : new Date().getFullYear(),
39 minDate: opt.minDate instanceof Date ? opt.minDate : null,
40 maxDate: opt.maxDate instanceof Date ? opt.maxDate : null,
41 language: (opt.language != null && dates[opt.language] != null) ? opt.language : 'en',
42 allowOverlap: opt.allowOverlap != null ? opt.allowOverlap : true,
43 displayWeekNumber: opt.displayWeekNumber != null ? opt.displayWeekNumber : false,
44 alwaysHalfDay: opt.alwaysHalfDay != null ? opt.alwaysHalfDay : false,
45 enableRangeSelection: opt.enableRangeSelection != null ? opt.enableRangeSelection : false,
46 disabledDays: opt.disabledDays instanceof Array ? opt.disabledDays : [],
47 roundRangeLimits: opt.roundRangeLimits != null ? opt.roundRangeLimits : false,
48 dataSource: opt.dataSource instanceof Array != null ? opt.dataSource : [],
49 style: opt.style == 'background' || opt.style == 'border' || opt.style == 'custom' ? opt.style : 'border',
50 enableContextMenu: opt.enableContextMenu != null ? opt.enableContextMenu : false,
51 contextMenuItems: opt.contextMenuItems instanceof Array ? opt.contextMenuItems : [],
52 customDayRenderer : $.isFunction(opt.customDayRenderer) ? opt.customDayRenderer : null,
53 customDataSourceRenderer : $.isFunction(opt.customDataSourceRenderer) ? opt.customDataSourceRenderer : null
54 };
56 this._initializeDatasourceColors();
57 },
58 _initializeEvents: function(opt) {
59 if(opt == null) {
60 opt = [];
61 }
63 if(opt.renderEnd) { this.element.bind('renderEnd', opt.renderEnd); }
64 if(opt.clickDay) { this.element.bind('clickDay', opt.clickDay); }
65 if(opt.dayContextMenu) { this.element.bind('dayContextMenu', opt.dayContextMenu); }
66 if(opt.selectRange) { this.element.bind('selectRange', opt.selectRange); }
67 if(opt.mouseOnDay) { this.element.bind('mouseOnDay', opt.mouseOnDay); }
68 if(opt.mouseOutDay) { this.element.bind('mouseOutDay', opt.mouseOutDay); }
69 },
70 _initializeDatasourceColors: function() {
71 for(var i in this.options.dataSource) {
72 if(this.options.dataSource[i].color == null) {
73 this.options.dataSource[i].color = colors[i % colors.length];
74 }
75 }
76 },
77 _render: function() {
78 this.element.empty();
80 this._renderHeader();
81 this._renderBody();
82 this._renderDataSource();
84 this._applyEvents();
85 this.element.find('.months-container').fadeIn(500);
87 this._triggerEvent('renderEnd', { currentYear: this.options.startYear });
88 },
89 _renderHeader: function() {
90 var header = $(document.createElement('div'));
91 header.addClass('calendar-header panel panel-default');
93 var headerTable = $(document.createElement('table'));
95 var prevDiv = $(document.createElement('th'));
96 prevDiv.addClass('prev');
98 if(this.options.minDate != null && this.options.minDate > new Date(this.options.startYear - 1, 11, 31)) {
99 prevDiv.addClass('disabled');
100 }
102 var prevIcon = $(document.createElement('span'));
103 prevIcon.addClass('glyphicon glyphicon-chevron-left');
105 prevDiv.append(prevIcon);
107 headerTable.append(prevDiv);
109 var prev2YearDiv = $(document.createElement('th'));
110 prev2YearDiv.addClass('year-title year-neighbor2 hidden-sm hidden-xs');
111 prev2YearDiv.text(this.options.startYear - 2);
113 if(this.options.minDate != null && this.options.minDate > new Date(this.options.startYear - 2, 11, 31)) {
114 prev2YearDiv.addClass('disabled');
115 }
117 headerTable.append(prev2YearDiv);
119 var prevYearDiv = $(document.createElement('th'));
120 prevYearDiv.addClass('year-title year-neighbor hidden-xs');
121 prevYearDiv.text(this.options.startYear - 1);
123 if(this.options.minDate != null && this.options.minDate > new Date(this.options.startYear - 1, 11, 31)) {
124 prevYearDiv.addClass('disabled');
125 }
127 headerTable.append(prevYearDiv);
129 var yearDiv = $(document.createElement('th'));
130 yearDiv.addClass('year-title');
131 yearDiv.text(this.options.startYear);
133 headerTable.append(yearDiv);
135 var nextYearDiv = $(document.createElement('th'));
136 nextYearDiv.addClass('year-title year-neighbor hidden-xs');
137 nextYearDiv.text(this.options.startYear + 1);
139 if(this.options.maxDate != null && this.options.maxDate < new Date(this.options.startYear + 1, 0, 1)) {
140 nextYearDiv.addClass('disabled');
141 }
143 headerTable.append(nextYearDiv);
145 var next2YearDiv = $(document.createElement('th'));
146 next2YearDiv.addClass('year-title year-neighbor2 hidden-sm hidden-xs');
147 next2YearDiv.text(this.options.startYear + 2);
149 if(this.options.maxDate != null && this.options.maxDate < new Date(this.options.startYear + 2, 0, 1)) {
150 next2YearDiv.addClass('disabled');
151 }
153 headerTable.append(next2YearDiv);
155 var nextDiv = $(document.createElement('th'));
156 nextDiv.addClass('next');
158 if(this.options.maxDate != null && this.options.maxDate < new Date(this.options.startYear + 1, 0, 1)) {
159 nextDiv.addClass('disabled');
160 }
162 var nextIcon = $(document.createElement('span'));
163 nextIcon.addClass('glyphicon glyphicon-chevron-right');
165 nextDiv.append(nextIcon);
167 headerTable.append(nextDiv);
169 header.append(headerTable);
171 this.element.append(header);
172 },
173 _renderBody: function() {
174 var monthsDiv = $(document.createElement('div'));
175 monthsDiv.addClass('months-container');
177 for(var m = 0; m < 12; m++) {
178 /* Container */
179 var monthDiv = $(document.createElement('div'));
180 monthDiv.addClass('month-container');
181 monthDiv.data('month-id', m);
183 var firstDate = new Date(this.options.startYear, m, 1);
185 var table = $(document.createElement('table'));
186 table.addClass('month');
188 /* Month header */
189 var thead = $(document.createElement('thead'));
191 var titleRow = $(document.createElement('tr'));
193 var titleCell = $(document.createElement('th'));
194 titleCell.addClass('month-title');
195 titleCell.attr('colspan', this.options.displayWeekNumber ? 8 : 7);
196 titleCell.text(dates[this.options.language].months[m]);
198 titleRow.append(titleCell);
199 thead.append(titleRow);
201 var headerRow = $(document.createElement('tr'));
203 if(this.options.displayWeekNumber) {
204 var weekNumberCell = $(document.createElement('th'));
205 weekNumberCell.addClass('week-number');
206 weekNumberCell.text(dates[this.options.language].weekShort);
207 headerRow.append(weekNumberCell);
208 }
210 var d = dates[this.options.language].weekStart;
211 do
212 {
213 var headerCell = $(document.createElement('th'));
214 headerCell.addClass('day-header');
215 headerCell.text(dates[this.options.language].daysMin[d]);
217 headerRow.append(headerCell);
219 d++;
220 if(d >= 7)
221 d = 0;
222 }
223 while(d != dates[this.options.language].weekStart)
225 thead.append(headerRow);
226 table.append(thead);
228 /* Days */
229 var currentDate = new Date(firstDate.getTime());
230 var lastDate = new Date(this.options.startYear, m + 1, 0);
232 var weekStart = dates[this.options.language].weekStart
234 while(currentDate.getDay() != weekStart)
235 {
236 currentDate.setDate(currentDate.getDate() - 1);
237 }
239 while(currentDate <= lastDate)
240 {
241 var row = $(document.createElement('tr'));
243 if(this.options.displayWeekNumber) {
244 var weekNumberCell = $(document.createElement('td'));
245 weekNumberCell.addClass('week-number');
246 weekNumberCell.text(this.getWeekNumber(currentDate));
247 row.append(weekNumberCell);
248 }
250 do
251 {
252 var cell = $(document.createElement('td'));
253 cell.addClass('day');
255 if(currentDate < firstDate) {
256 cell.addClass('old');
257 }
258 else if(currentDate > lastDate) {
259 cell.addClass('new');
260 }
261 else {
262 if((this.options.minDate != null && currentDate < this.options.minDate) || (this.options.maxDate != null && currentDate > this.options.maxDate))
263 {
264 cell.addClass('disabled');
265 }
266 else if(this.options.disabledDays.length > 0) {
267 for(var d in this.options.disabledDays){
268 if(currentDate.getTime() == this.options.disabledDays[d].getTime()) {
269 cell.addClass('disabled');
270 break;
271 }
272 }
273 }
275 var cellContent = $(document.createElement('div'));
276 cellContent.addClass('day-content');
277 cellContent.text(currentDate.getDate());
278 cell.append(cellContent);
280 if(this.options.customDayRenderer) {
281 this.options.customDayRenderer(cellContent, currentDate);
282 }
283 }
285 row.append(cell);
287 currentDate.setDate(currentDate.getDate() + 1);
288 }
289 while(currentDate.getDay() != weekStart)
291 table.append(row);
292 }
294 monthDiv.append(table);
296 monthsDiv.append(monthDiv);
297 }
299 this.element.append(monthsDiv);
300 },
301 _renderDataSource: function() {
302 var _this = this;
303 if(this.options.dataSource != null && this.options.dataSource.length > 0) {
304 this.element.find('.month-container').each(function() {
305 var month = $(this).data('month-id');
307 var firstDate = new Date(_this.options.startYear, month, 1);
308 var lastDate = new Date(_this.options.startYear, month + 1, 0);
310 if((_this.options.minDate == null || lastDate >= _this.options.minDate) && (_this.options.maxDate == null || firstDate <= _this.options.maxDate))
311 {
312 var monthData = [];
314 for(var i in _this.options.dataSource) {
315 if(!(_this.options.dataSource[i].startDate > lastDate) || (_this.options.dataSource[i].endDate < firstDate)) {
316 monthData.push(_this.options.dataSource[i]);
317 }
318 }
320 if(monthData.length > 0) {
321 $(this).find('.day-content').each(function() {
322 var currentDate = new Date(_this.options.startYear, month, $(this).text());
324 var dayData = [];
326 if((_this.options.minDate == null || currentDate >= _this.options.minDate) && (_this.options.maxDate == null || currentDate <= _this.options.maxDate))
327 {
328 for(var i in monthData) {
329 if(monthData[i].startDate <= currentDate && monthData[i].endDate >= currentDate) {
330 dayData.push(monthData[i]);
331 }
332 }
334 if(dayData.length > 0)
335 {
336 _this._renderDataSourceDay($(this), currentDate, dayData);
337 }
338 }
339 });
340 }
341 }
342 });
343 }
344 },
345 _renderDataSourceDay: function(elt, currentDate, events) {
346 switch(this.options.style)
347 {
348 case 'border':
349 var weight = 0;
351 if(events.length == 1) {
352 weight = 4;
353 }
354 else if(events.length <= 3) {
355 weight = 2;
356 }
357 else {
358 elt.parent().css('box-shadow', 'inset 0 -4px 0 0 black');
359 }
361 if(weight > 0)
362 {
363 var boxShadow = '';
365 for(var i in events)
366 {
367 if(boxShadow != '') {
368 boxShadow += ",";
369 }
371 boxShadow += 'inset 0 -' + (parseInt(i) + 1) * weight + 'px 0 0 ' + events[i].color;
372 }
374 elt.parent().css('box-shadow', boxShadow);
375 }
376 break;
378 case 'background':
379 elt.parent().css('background-color', events[events.length - 1].color);
381 var currentTime = currentDate.getTime();
383 if(events[events.length - 1].startDate.getTime() == currentTime)
384 {
385 elt.parent().addClass('day-start');
387 if(events[events.length - 1].startHalfDay || this.options.alwaysHalfDay) {
388 elt.parent().addClass('day-half');
390 // Find color for other half
391 var otherColor = 'transparent';
392 for(var i = events.length - 2; i >= 0; i--) {
393 if(events[i].startDate.getTime() != currentTime || (!events[i].startHalfDay && !this.options.alwaysHalfDay)) {
394 otherColor = events[i].color;
395 break;
396 }
397 }
399 elt.parent().css('background', 'linear-gradient(-45deg, ' + events[events.length - 1].color + ', ' + events[events.length - 1].color + ' 49%, ' + otherColor + ' 51%, ' + otherColor + ')');
400 }
401 else if(this.options.roundRangeLimits) {
402 elt.parent().addClass('round-left');
403 }
404 }
405 else if(events[events.length - 1].endDate.getTime() == currentTime)
406 {
407 elt.parent().addClass('day-end');
409 if(events[events.length - 1].endHalfDay || this.options.alwaysHalfDay) {
410 elt.parent().addClass('day-half');
412 // Find color for other half
413 var otherColor = 'transparent';
414 for(var i = events.length - 2; i >= 0; i--) {
415 if(events[i].endDate.getTime() != currentTime || (!events[i].endHalfDay && !this.options.alwaysHalfDay)) {
416 otherColor = events[i].color;
417 break;
418 }
419 }
421 elt.parent().css('background', 'linear-gradient(135deg, ' + events[events.length - 1].color + ', ' + events[events.length - 1].color + ' 49%, ' + otherColor + ' 51%, ' + otherColor + ')');
422 }
423 else if(this.options.roundRangeLimits) {
424 elt.parent().addClass('round-right');
425 }
426 }
427 break;
429 case 'custom':
430 if(this.options.customDataSourceRenderer) {
431 this.options.customDataSourceRenderer.call(this, elt, currentDate, events);
432 }
433 break;
434 }
435 },
436 _applyEvents: function () {
437 var _this = this;
439 /* Header buttons */
440 this.element.find('.year-neighbor, .year-neighbor2').click(function() {
441 if(!$(this).hasClass('disabled')) {
442 _this.setYear(parseInt($(this).text()));
443 }
444 });
446 this.element.find('.calendar-header .prev').click(function() {
447 if(!$(this).hasClass('disabled')) {
448 _this.element.find('.months-container').animate({'margin-left':'100%'},100, function() {
449 _this.element.find('.months-container').hide();
450 _this.element.find('.months-container').css('margin-left', '0');
451 setTimeout(function() { _this.setYear(_this.options.startYear - 1) }, 50);
452 });
453 }
454 });
456 this.element.find('.calendar-header .next').click(function() {
457 if(!$(this).hasClass('disabled')) {
458 _this.element.find('.months-container').animate({'margin-left':'-100%'},100, function() {
459 _this.element.find('.months-container').hide();
460 _this.element.find('.months-container').css('margin-left', '0');
461 setTimeout(function() { _this.setYear(_this.options.startYear + 1) }, 50);
462 });
463 }
464 });
466 var cells = this.element.find('.day:not(.old, .new, .disabled)');
468 /* Click on date */
469 cells.click(function(e) {
470 e.stopPropagation();
471 var date = _this._getDate($(this));
472 _this._triggerEvent('clickDay', {
473 element: $(this),
474 which: e.which,
475 date: date,
476 events: _this.getEvents(date)
477 });
478 });
480 /* Click right on date */
482 cells.bind('contextmenu', function(e) {
483 if(_this.options.enableContextMenu)
484 {
485 e.preventDefault();
486 if(_this.options.contextMenuItems.length > 0)
487 {
488 _this._openContextMenu($(this));
489 }
490 }
492 var date = _this._getDate($(this));
493 _this._triggerEvent('dayContextMenu', {
494 element: $(this),
495 date: date,
496 events: _this.getEvents(date)
497 });
498 });
500 /* Range selection */
501 if(this.options.enableRangeSelection) {
502 cells.mousedown(function (e) {
503 if(e.which == 1) {
504 var currentDate = _this._getDate($(this));
506 if(_this.options.allowOverlap || _this.getEvents(currentDate).length == 0)
507 {
508 _this._mouseDown = true;
509 _this._rangeStart = _this._rangeEnd = currentDate;
510 _this._refreshRange();
511 }
512 }
513 });
515 cells.mouseenter(function (e) {
516 if (_this._mouseDown) {
517 var currentDate = _this._getDate($(this));
519 if(!_this.options.allowOverlap)
520 {
521 var newDate = new Date(_this._rangeStart.getTime());
523 if(newDate < currentDate) {
524 var nextDate = new Date(newDate.getFullYear(), newDate.getMonth(), newDate.getDate() + 1);
525 while(newDate < currentDate) {
526 if(_this.getEvents(nextDate).length > 0)
527 {
528 break;
529 }
531 newDate.setDate(newDate.getDate() + 1);
532 nextDate.setDate(nextDate.getDate() + 1);
533 }
534 }
535 else {
536 var nextDate = new Date(newDate.getFullYear(), newDate.getMonth(), newDate.getDate() - 1);
537 while(newDate > currentDate) {
538 if(_this.getEvents(nextDate).length > 0)
539 {
540 break;
541 }
543 newDate.setDate(newDate.getDate() - 1);
544 nextDate.setDate(nextDate.getDate() - 1);
545 }
546 }
548 currentDate = newDate;
549 }
551 var oldValue = _this._rangeEnd;
552 _this._rangeEnd = currentDate;
554 if (oldValue.getTime() != _this._rangeEnd.getTime()) {
555 _this._refreshRange();
556 }
557 }
558 });
560 $(window).mouseup(function (e) {
561 if (_this._mouseDown) {
562 _this._mouseDown = false;
563 _this._refreshRange();
565 var minDate = _this._rangeStart < _this._rangeEnd ? _this._rangeStart : _this._rangeEnd;
566 var maxDate = _this._rangeEnd > _this._rangeStart ? _this._rangeEnd : _this._rangeStart;
568 _this._triggerEvent('selectRange', { startDate: minDate, endDate: maxDate });
569 }
570 });
571 }
573 /* Hover date */
574 cells.mouseenter(function(e) {
575 if(!_this._mouseDown)
576 {
577 var date = _this._getDate($(this));
578 _this._triggerEvent('mouseOnDay', {
579 element: $(this),
580 date: date,
581 events: _this.getEvents(date)
582 });
583 }
584 });
586 cells.mouseleave(function(e) {
587 var date = _this._getDate($(this));
588 _this._triggerEvent('mouseOutDay', {
589 element: $(this),
590 date: date,
591 events: _this.getEvents(date)
592 });
593 });
595 /* Responsive management */
597 setInterval(function() {
598 var calendarSize = $(_this.element).width();
599 var monthSize = $(_this.element).find('.month').first().width() + 10;
600 var monthContainerClass = 'month-container';
602 if(monthSize * 6 < calendarSize) {
603 monthContainerClass += ' col-xs-2';
604 }
605 else if(monthSize * 4 < calendarSize) {
606 monthContainerClass += ' col-xs-3';
607 }
608 else if(monthSize * 3 < calendarSize) {
609 monthContainerClass += ' col-xs-4';
610 }
611 else if(monthSize * 2 < calendarSize) {
612 monthContainerClass += ' col-xs-6';
613 }
614 else {
615 monthContainerClass += ' col-xs-12';
616 }
618 $(_this.element).find('.month-container').attr('class', monthContainerClass);
619 }, 300);
620 },
621 _refreshRange: function () {
622 var _this = this;
624 this.element.find('td.day.range').removeClass('range')
625 this.element.find('td.day.range-start').removeClass('range-start');
626 this.element.find('td.day.range-end').removeClass('range-end');
628 if (this._mouseDown) {
629 var beforeRange = true;
630 var afterRange = false;
631 var minDate = _this._rangeStart < _this._rangeEnd ? _this._rangeStart : _this._rangeEnd;
632 var maxDate = _this._rangeEnd > _this._rangeStart ? _this._rangeEnd : _this._rangeStart;
634 this.element.find('.month-container').each(function () {
635 var monthId = $(this).data('month-id');
636 if (minDate.getMonth() <= monthId && maxDate.getMonth() >= monthId) {
637 $(this).find('td.day:not(.old, .new)').each(function () {
638 var date = _this._getDate($(this));
639 if (date >= minDate && date <= maxDate) {
640 $(this).addClass('range');
642 if (date.getTime() == minDate.getTime()) {
643 $(this).addClass('range-start');
644 }
646 if (date.getTime() == maxDate.getTime()) {
647 $(this).addClass('range-end');
648 }
649 }
650 });
651 }
652 });
653 }
654 },
655 _openContextMenu: function(elt) {
656 var contextMenu = $('.calendar-context-menu');
658 if(contextMenu.length > 0) {
659 contextMenu.hide();
660 contextMenu.empty();
661 }
662 else {
663 contextMenu = $(document.createElement('div'));
664 contextMenu.addClass('calendar-context-menu');
665 $('body').append(contextMenu);
666 }
668 var date = this._getDate(elt);
669 var events = this.getEvents(date);
671 for(var i in events) {
672 var eventItem = $(document.createElement('div'));
673 eventItem.addClass('item');
674 eventItem.css('border-left', '4px solid ' + events[i].color);
676 var eventItemContent = $(document.createElement('div'));
677 eventItemContent.addClass('content');
678 eventItemContent.text(events[i].name);
680 eventItem.append(eventItemContent);
682 var icon = $(document.createElement('span'));
683 icon.addClass('glyphicon glyphicon-chevron-right');
685 eventItem.append(icon);
687 this._renderContextMenuItems(eventItem, this.options.contextMenuItems, events[i]);
689 contextMenu.append(eventItem);
690 }
692 if(contextMenu.children().length > 0)
693 {
694 contextMenu.css('left', elt.offset().left + 25 + 'px');
695 contextMenu.css('top', elt.offset().top + 25 + 'px');
696 contextMenu.show();
698 $(window).one('mouseup', function() {
699 contextMenu.hide();
700 });
701 }
702 },
703 _renderContextMenuItems: function(parent, items, evt) {
704 var subMenu = $(document.createElement('div'));
705 subMenu.addClass('submenu');
707 for(var i in items) {
708 if(!items[i].visible || items[i].visible(evt)) {
709 var menuItem = $(document.createElement('div'));
710 menuItem.addClass('item');
712 var menuItemContent = $(document.createElement('div'));
713 menuItemContent.addClass('content');
714 menuItemContent.text(items[i].text);
716 menuItem.append(menuItemContent);
718 if(items[i].click) {
719 (function(index) {
720 menuItem.click(function() {
721 items[index].click(evt);
722 });
723 })(i);
724 }
726 var icon = $(document.createElement('span'));
727 icon.addClass('glyphicon glyphicon-chevron-right');
729 menuItem.append(icon);
731 if(items[i].items && items[i].items.length > 0) {
732 this._renderContextMenuItems(menuItem, items[i].items, evt);
733 }
735 subMenu.append(menuItem);
736 }
737 }
739 if(subMenu.children().length > 0)
740 {
741 parent.append(subMenu);
742 }
743 },
744 _getColor: function(colorString) {
745 var div = $('<div />');
746 div.css('color', colorString);
748 },
749 _getDate: function(elt) {
750 var day = elt.children('.day-content').text();
751 var month = elt.closest('.month-container').data('month-id');
752 var year = this.options.startYear;
754 return new Date(year, month, day);
755 },
756 _triggerEvent: function(eventName, parameters) {
757 var event = $.Event(eventName);
759 for(var i in parameters) {
760 event[i] = parameters[i];
761 }
763 this.element.trigger(event);
764 },
765 getWeekNumber: function(date) {
766 var tempDate = new Date(date.getTime());
767 tempDate.setHours(0, 0, 0, 0);
768 tempDate.setDate(tempDate.getDate() + 3 - (tempDate.getDay() + 6) % 7);
769 var week1 = new Date(tempDate.getFullYear(), 0, 4);
770 return 1 + Math.round(((tempDate.getTime() - week1.getTime()) / 86400000 - 3 + (week1.getDay() + 6) % 7) / 7);
771 },
772 getEvents: function(date) {
773 var events = [];
775 if(this.options.dataSource && date) {
776 for(var i in this.options.dataSource) {
777 if(this.options.dataSource[i].startDate <= date && this.options.dataSource[i].endDate >= date) {
778 events.push(this.options.dataSource[i]);
779 }
780 }
781 }
783 return events;
784 },
785 getYear: function() {
786 return this.options.startYear;
787 },
788 setYear: function(year) {
789 var parsedYear = parseInt(year);
790 if(!isNaN(parsedYear)) {
791 this.options.startYear = parsedYear;
792 this._render();
793 }
794 },
795 getMinDate: function() {
796 return this.options.minDate;
797 },
798 setMinDate: function(date) {
799 if(date instanceof Date) {
800 this.options.minDate = date;
801 this._render();
802 }
803 },
804 getMaxDate: function() {
805 return this.options.maxDate;
806 },
807 setMaxDate: function(date) {
808 if(date instanceof Date) {
809 this.options.maxDate = date;
810 this._render();
811 }
812 },
813 getStyle: function() {
814 return this.options.style;
815 },
816 setStyle: function(style) {
817 this.options.style = style == 'background' || style == 'border' || style == 'custom' ? style : 'border';
818 this._render();
819 },
820 getAllowOverlap: function() {
821 return this.options.allowOverlap;
822 },
823 setAllowOverlap: function(allowOverlap) {
824 this.options.allowOverlap = allowOverlap;
825 },
826 getDisplayWeekNumber: function() {
827 return this.options.displayWeekNumber;
828 },
829 setDisplayWeekNumber: function(displayWeekNumber) {
830 this.options.displayWeekNumber = displayWeekNumber;
831 this._render();
832 },
833 getAlwaysHalfDay: function() {
834 return this.options.alwaysHalfDay;
835 },
836 setAlwaysHalfDay: function(alwaysHalfDay) {
837 this.options.alwaysHalfDay = alwaysHalfDay;
838 this._render();
839 },
840 getEnableRangeSelection: function() {
841 return this.options.enableRangeSelection;
842 },
843 setEnableRangeSelection: function(enableRangeSelection) {
844 this.options.enableRangeSelection = enableRangeSelection;
845 this._render();
846 },
847 getDisabledDays: function() {
848 return this.options.disabledDays;
849 },
850 setDisabledDays: function(disabledDays) {
851 this.options.disabledDays = disabledDays instanceof Array ? disabledDays : [];
852 this._render();
853 },
854 getRoundRangeLimits: function() {
855 return this.options.roundRangeLimits;
856 },
857 setRoundRangeLimits: function(roundRangeLimits) {
858 this.options.roundRangeLimits = roundRangeLimits;
859 this._render();
860 },
861 getEnableContextMenu: function() {
862 return this.options.enableContextMenu;
863 },
864 setEnableContextMenu: function(enableContextMenu) {
865 this.options.enableContextMenu = enableContextMenu;
866 this._render();
867 },
868 getContextMenuItems: function() {
869 return this.options.contextMenuItems;
870 },
871 setContextMenuItems: function(contextMenuItems) {
872 this.options.contextMenuItems = contextMenuItems instanceof Array ? contextMenuItems : [];
873 this._render();
874 },
875 getCustomDayRenderer: function() {
876 return this.options.customDayRenderer;
877 },
878 setCustomDayRenderer: function(customDayRenderer) {
879 this.options.customDayRenderer = $.isFunction(customDayRenderer) ? customDayRenderer : null;
880 this._render();
881 },
882 getCustomDataSourceRenderer: function() {
883 return this.options.customDataSourceRenderer;
884 },
885 setCustomDataSourceRenderer: function(customDataSourceRenderer) {
886 this.options.customDataSourceRenderer = $.isFunction(customDataSourceRenderer) ? customDataSourceRenderer : null;
887 this._render();
888 },
889 getLanguage: function() {
890 return this.options.language;
891 },
892 setLanguage: function(language) {
893 if(language != null && dates[language] != null) {
894 this.options.language = language;
895 this._render();
896 }
897 },
898 getDataSource: function() {
899 return this.options.dataSource;
900 },
901 setDataSource: function(dataSource) {
902 this.options.dataSource = dataSource instanceof Array ? dataSource : [];
903 this._initializeDatasourceColors();
904 this._render();
905 },
906 addEvent: function(evt) {
907 this.options.dataSource.push(evt);
908 this._render();
909 }
910 }
912 $.fn.calendar = function (options) {
913 var calendar = new Calendar($(this) ,options);
914 $(this).data('calendar', calendar);
915 return calendar;
916 }
918 /* Events binding management */
919 $.fn.renderEnd = function(fct) { $(this).bind('renderEnd', fct); }
920 $.fn.clickDay = function(fct) { $(this).bind('clickDay', fct); }
921 $.fn.dayContextMenu = function(fct) { $(this).bind('dayContextMenu', fct); }
922 $.fn.selectRange = function(fct) { $(this).bind('selectRange', fct); }
923 $.fn.mouseOnDay = function(fct) { $(this).bind('mouseOnDay', fct); }
924 $.fn.mouseOutDay = function(fct) { $(this).bind('mouseOutDay', fct); }
926 var dates = $.fn.calendar.dates = {
927 en: {
928 days: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"],
929 daysShort: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"],
930 daysMin: ["Su", "Mo", "Tu", "We", "Th", "Fr", "Sa", "Su"],
931 months: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
932 monthsShort: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"],
933 weekShort: 'W',
934 weekStart:0
935 }
936 };
938 var colors = $.fn.calendar.colors = ['#2C8FC9', '#9CB703', '#F5BB00', '#FF4A32', '#B56CE2', '#45A597'];
940 $(function(){
941 $('[data-provide="calendar"]').each(function() {
942 $(this).calendar();
943 });
944 });
945 }(window.jQuery));