vpn.email
Version:
vpn.email client
655 lines (541 loc) • 23.1 kB
JavaScript
$.widget("metro.calendar", {
version: "3.0.0",
options: {
format: "yyyy-mm-dd",
multiSelect: false,
startMode: 'day', //year, month, day
weekStart: window.METRO_CALENDAR_WEEK_START, // 0 - Sunday, 1 - Monday
otherDays: true,
date: new Date(),
minDate: false,
maxDate: false,
preset: false,
exclude: false,
stored: false,
buttons: true,
buttonToday: true,
buttonClear: true,
syncCalenderToDateField: true,
locale: window.METRO_CURRENT_LOCALE,
actions: true,
condensedGrid: false,
scheme: 'default',
getDates: function (d) { },
dayClick: function (d, d0) { }
},
//_storage: [],
//_exclude: [],
_year: 0,
_month: 0,
_day: 0,
_today: new Date(),
_event: '',
_mode: 'day', // day, month, year
_distance: 0,
_events: [],
_create: function () {
var that = this, element = this.element, o = this.options;
$.each(element.data(), function (key, value) {
if (key in o) {
try {
o[key] = $.parseJSON(value);
} catch (e) {
o[key] = value;
}
}
});
if (typeof o.date === 'string') {
o.date = new Date(o.date);
}
if (o.minDate !== false && typeof o.minDate === 'string') {
o.minDate = new Date(o.minDate + 'T00:00:00Z') - 24 * 60 * 60 * 1000;
}
if (o.maxDate !== false && typeof o.maxDate === 'string') {
o.maxDate = new Date(o.maxDate + 'T00:00:00Z');
}
//console.log(window.METRO_LOCALES);
this.locales = window.METRO_LOCALES;
this._year = o.date.getFullYear();
this._distance = o.date.getFullYear() - 4;
this._month = o.date.getMonth();
this._day = o.date.getDate();
this._mode = o.startMode;
element.data("_storage", []);
element.data("_exclude", []);
element.data("_stored", []);
if (!element.hasClass('calendar')) { element.addClass('calendar'); }
var re, dates;
if (o.preset) {
re = /\s*,\s*/;
dates = o.preset.split(re);
$.each(dates, function () {
if (new Date(this) !== undefined) { that.setDate(this); }
});
}
if (o.exclude) {
re = /\s*,\s*/;
dates = o.exclude.split(re);
$.each(dates, function () {
if (new Date(this) !== undefined) { that.setDateExclude(this); }
});
}
if (o.stored) {
re = /\s*,\s*/;
dates = o.stored.split(re);
$.each(dates, function () {
if (new Date(this) !== undefined) { that.setDateStored(this); }
});
}
if (o.scheme !== 'default') {
element.addClass(o.scheme);
}
this._renderCalendar();
element.data('calendar', this);
},
_renderButtons: function (table) {
var tr, td, o = this.options;
if (this.options.buttons) {
var buttonToday = o.buttonToday ? "<button class='button calendar-btn-today small-button success'>" + this.locales[o.locale].buttons[0] + "</button>" : "";
var buttonClear = o.buttonClear ? "<button class='button calendar-btn-clear small-button warning'>" + this.locales[o.locale].buttons[1] + "</button>" : "";
tr = $("<div/>").addClass("calendar-row calendar-actions");
td = $("<div/>").addClass("align-center").html(
buttonToday + buttonClear
);
td.appendTo(tr);
tr.appendTo(table);
}
},
_renderMonth: function () {
var that = this, o = this.options,
year = this._year,
month = this._month,
day = this._day,
event = this._event,
feb = 28;
if (month === 1) {
if ((year % 100 !== 0) && (year % 4 === 0) || (year % 400 === 0)) {
feb = 29;
}
}
var totalDays = ["31", "" + feb + "", "31", "30", "31", "30", "31", "31", "30", "31", "30", "31"];
var daysInMonth = totalDays[month];
var first_week_day = this._dateFromNumbers(year, month + 1, 1).getDay();
var table, tr, td, i, div;
this.element.html("");
table = $("<div/>").addClass("calendar-grid");
if (o.condensedGrid) {
table.addClass('condensed no-border');
}
//console.log(this.locales);
// Add calendar header
tr = $("<div/>").addClass('calendar-row no-margin');
$("<div/>").addClass("calendar-cell align-center").html("<a class='btn-previous-year' href='#'>-</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell align-center").html("<a class='btn-previous-month' href='#'>〈</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell sel-month align-center").html("<a class='btn-select-month' href='#'>" + this.locales[o.locale].months[month] + ' ' + year + "</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell align-center").html("<a class='btn-next-month' href='#'>〉</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell align-center").html("<a class='btn-next-year' href='#'>+</a>").appendTo(tr);
tr.addClass("calendar-header").appendTo(table);
// Add day names
var j;
tr = $("<div/>").addClass('calendar-row week-days');
for (i = 0; i < 7; i++) {
if (!o.weekStart) {
td = $("<div/>").addClass("calendar-cell align-center day-of-week").appendTo(tr);
div = $("<div/>").html(this.locales[o.locale].days[i + 7]).appendTo(td);
} else {
j = i + 1;
if (j === 7) { j = 0; }
td = $("<div/>").addClass("calendar-cell align-center day-of-week").appendTo(tr);
div = $("<div/>").html(this.locales[o.locale].days[j + 7]).appendTo(td);
}
}
tr.addClass("calendar-subheader").appendTo(table);
// Add empty days for previos month
var prevMonth = this._month - 1; if (prevMonth < 0) { prevMonth = 11; } var daysInPrevMonth = totalDays[prevMonth];
var _first_week_day = ((o.weekStart) ? first_week_day + 6 : first_week_day) % 7;
var htmlPrevDay = "";
tr = $("<div/>").addClass('calendar-row');
for (i = 0; i < _first_week_day; i++) {
if (o.otherDays) { htmlPrevDay = daysInPrevMonth - (_first_week_day - i - 1); }
td = $("<div/>").addClass("calendar-cell empty").appendTo(tr);
div = $("<div/>").addClass('other-day').html(htmlPrevDay).appendTo(td);
if (!o.otherDays) {
div.css('visibility', 'hidden');
}
}
// Days for current month
var week_day = ((o.weekStart) ? first_week_day + 6 : first_week_day) % 7;
var d, a, d_html;
for (i = 1; i <= daysInMonth; i++) {
week_day %= 7;
if (week_day === 0) {
tr.appendTo(table);
tr = $("<div/>").addClass('calendar-row');
}
td = $("<div/>").addClass("calendar-cell align-center day");
div = $("<div/>").appendTo(td);
if (o.minDate !== false && (this._dateFromNumbers(year, month + 1, i) < o.minDate) || o.maxDate !== false && (this._dateFromNumbers(year, month + 1, i) > o.maxDate)) {
td.removeClass("day");
div.addClass("other-day");
d_html = i;
} else {
d_html = "<a href='#'>" + i + "</a>";
}
div.html(d_html);
//console.log(div);
if (year === this._today.getFullYear() && month === this._today.getMonth() && this._today.getDate() === i) {
td.addClass("today");
}
//console.log('xxx');
d = this._dateNumberStringyFy(this._year, this._month + 1, i);
if (this.element.data('_storage').indexOf(d) >= 0) {
a = td.find("a");
a.parent().parent().addClass("selected");
}
if (this.element.data('_exclude').indexOf(d) >= 0) {
a = td.find("a");
a.parent().parent().addClass("exclude");
}
if (this.element.data('_stored').indexOf(d) >= 0) {
a = td.find("a");
a.parent().parent().addClass("stored");
}
td.appendTo(tr);
week_day++;
}
// next month other days
var htmlOtherDays = "";
for (i = week_day + 1; i <= 7; i++) {
if (o.otherDays) { htmlOtherDays = i - week_day; }
td = $("<div/>").addClass("calendar-cell empty").appendTo(tr);
div = $("<div/>").addClass('other-day').html(htmlOtherDays).appendTo(td);
if (!o.otherDays) {
div.css('visibility', 'hidden');
}
}
tr.appendTo(table);
this._renderButtons(table);
table.appendTo(this.element);
},
_renderMonths: function () {
var table, tr, td, i, j;
this.element.html("");
table = $("<div/>").addClass("calendar-grid");
if (this.options.condensedGrid) {
table.addClass('condensed no-border');
}
// Add calendar header
tr = $("<div/>").addClass('calendar-row');
$("<div/>").addClass("calendar-cell sel-minus align-center").html("<a class='btn-previous-year' href='#'>-</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell sel-year align-center").html("<a class='btn-select-year' href='#'>" + this._year + "</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell sel-plus align-center").html("<a class='btn-next-year' href='#'>+</a>").appendTo(tr);
tr.addClass("calendar-header").appendTo(table);
tr = $("<div/>").addClass('calendar-row');
j = 0;
for (i = 0; i < 12; i++) {
//td = $("<td/>").addClass("text-center month").html("<a href='#' data-month='"+i+"'>"+this.options.monthsShort[i]+"</a>");
td = $("<div/>").addClass("calendar-cell month-cell align-center month").html("<a href='#' data-month='" + i + "'>" + this.locales[this.options.locale].months[i + 12] + "</a>");
if (this._month === i && (new Date()).getFullYear() === this._year) {
td.addClass("today");
}
td.appendTo(tr);
if ((j + 1) % 4 === 0) {
tr.appendTo(table);
tr = $("<div/>").addClass('calendar-row');
}
j += 1;
}
this._renderButtons(table);
table.appendTo(this.element);
},
_renderYears: function () {
var table, tr, td, i, j;
this.element.html("");
table = $("<div/>").addClass("calendar-grid");
if (this.options.condensedGrid) {
table.addClass('condensed no-border');
}
// Add calendar header
tr = $("<div/>").addClass('calendar-row cells4');
$("<div/>").addClass("calendar-cell sel-minus align-center").html("<a class='btn-previous-year' href='#'>-</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell sel-year align-center").html("<a class='btn-none-btn'>" + (this._distance) + "-" + (this._distance + 11) + "</a>").appendTo(tr);
$("<div/>").addClass("calendar-cell sel-plus align-center").html("<a class='btn-next-year' href='#'>+</a>").appendTo(tr);
tr.addClass("calendar-header").appendTo(table);
tr = $("<div/>").addClass('calendar-row');
j = 0;
for (i = this._distance; i < this._distance + 12; i++) {
td = $("<div/>").addClass("calendar-cell year-cell align-center year").html("<a href='#' data-year='" + i + "'>" + i + "</a>");
if ((new Date()).getFullYear() === i) {
td.addClass("today");
}
td.appendTo(tr);
if ((j + 1) % 4 === 0) {
tr.appendTo(table);
tr = $("<div/>").addClass('calendar-row');
}
j += 1;
}
this._renderButtons(table);
table.appendTo(this.element);
},
_renderCalendar: function () {
switch (this._mode) {
case 'year': this._renderYears(); break;
case 'month': this._renderMonths(); break;
default: this._renderMonth();
}
this._initButtons();
},
_initButtons: function () {
// Add actions
var that = this, o = this.options,
table = this.element.find('.calendar-grid');
if (this._mode === 'day') {
table.find('.btn-select-month').on('click', function (e) {
e.preventDefault();
e.stopPropagation();
that._mode = 'month';
that._renderCalendar();
});
table.find('.btn-previous-month').on('click', function (e) {
that._event = 'eventPrevious';
e.preventDefault();
e.stopPropagation();
that._month -= 1;
if (that._month < 0) {
that._year -= 1;
that._month = 11;
}
that._renderCalendar();
});
table.find('.btn-next-month').on('click', function (e) {
that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._month += 1;
if (that._month === 12) {
that._year += 1;
that._month = 0;
}
that._renderCalendar();
});
table.find('.btn-previous-year').on('click', function (e) {
that._event = 'eventPrevious';
e.preventDefault();
e.stopPropagation();
that._year -= 1;
that._renderCalendar();
});
table.find('.btn-next-year').on('click', function (e) {
that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._year += 1;
that._renderCalendar();
});
table.find('.day a').on('click', function (e) {
e.preventDefault();
e.stopPropagation();
if ($(this).parent().parent().hasClass('exclude')) {
return false;
}
var d = (new Date(that._paddy(that._year, 4), that._paddy(that._month, 2), that._paddy(parseInt($(this).html()), 2)).format(that.options.format, null));
var d0 = (new Date(that._paddy(that._year, 4), that._paddy(that._month, 2), that._paddy(parseInt($(this).html()), 2)));
if (that.options.multiSelect) {
$(this).parent().parent().toggleClass("selected");
if ($(this).parent().parent().hasClass("selected")) {
that._addDate(that._dateStringyFy(d0));
} else {
that._removeDate(that._dateStringyFy(d0));
}
} else {
table.find('.day a').parent().parent().removeClass('selected');
$(this).parent().parent().addClass("selected");
that.element.data('_storage', []);
that._addDate(that._dateStringyFy(d0));
}
if (typeof o.dayClick === 'function') {
o.dayClick(d, d0);
} else {
if (typeof window[o.dayClick] === 'function') {
window[o.dayClick](d, d0);
} else {
var result = eval("(function(){" + o.dayClick + "})");
result.call(d, d0);
}
}
});
} else if (this._mode === 'month') {
table.find('.month a').on('click', function (e) {
that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._month = parseInt($(this).data('month'));
that._mode = 'day';
that._renderCalendar();
});
table.find('.btn-previous-year').on('click', function (e) {
that._event = 'eventPrevious';
e.preventDefault();
e.stopPropagation();
that._year -= 1;
that._renderCalendar();
});
table.find('.btn-next-year').on('click', function (e) {
that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._year += 1;
that._renderCalendar();
});
table.find('.btn-select-year').on('click', function (e) {
that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._mode = 'year';
that._renderCalendar();
});
} else {
table.find('.year a').on('click', function (e) {
that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._year = parseInt($(this).data('year'));
that._mode = 'month';
that._renderCalendar();
});
table.find('.btn-previous-year').on('click', function (e) {
that._event = 'eventPrevious';
e.preventDefault();
e.stopPropagation();
that._distance -= 10;
that._renderCalendar();
});
table.find('.btn-next-year').on('click', function (e) {
that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._distance += 10;
that._renderCalendar();
});
}
table.find('.calendar-btn-today').on('click', function (e) {
//that._event = 'eventNext';
e.preventDefault();
e.stopPropagation();
that._mode = that.options.startMode;
that.options.date = new Date();
that._year = that.options.date.getFullYear();
that._month = that.options.date.getMonth();
that._day = that.options.date.getDate();
that._renderCalendar();
});
table.find('.calendar-btn-clear').on('click', function (e) {
e.preventDefault();
e.stopPropagation();
that.options.date = new Date();
that._year = that.options.date.getFullYear();
that._month = that.options.date.getMonth();
that._day = that.options.date.getDate();
that.element.data('_storage', []);
that._renderCalendar();
});
},
_addDate: function (d) {
var index = this.element.data('_storage').indexOf(d);
if (index < 0) { this.element.data('_storage').push(d); }
},
_removeDate: function (d) {
var index = this.element.data('_storage').indexOf(d);
this.element.data('_storage').splice(index, 1);
},
_addDateExclude: function (d) {
var index = this.element.data('_exclude').indexOf(d);
if (index < 0) { this.element.data('_exclude').push(d); }
},
_addDateStored: function (d) {
var index = this.element.data('_stored').indexOf(d);
if (index < 0) { this.element.data('_stored').push(d); }
},
_removeDateExclude: function (d) {
var index = this.element.data('_exclude').indexOf(d);
this.element.data('_exclude').splice(index, 1);
},
_removeDateStored: function (d) {
var index = this.element.data('_stored').indexOf(d);
this.element.data('_stored').splice(index, 1);
},
_paddy: function paddy(n, p, c) {
var pad_char = typeof c !== 'undefined' ? c : '0';
var pad = new Array(1 + p).join(pad_char);
return (pad + n).slice(-pad.length);
},
_dateFromNumbers: function dateFromNumbers(year, month, day){
return new Date(this._paddy(year, 4) + "/" + this._paddy(month, 2) + "/" + this._paddy(day, 2));
},
_dateNumberStringyFy: function dateNumberStringyFy(year, month, day) {
return (this._dateFromNumbers(year, month, day)).format('yyyy-mm-dd')
},
_dateStringyFy: function dateStringyFy(d) {
return this._dateNumberStringyFy(d.getFullYear(), d.getMonth() + 1, d.getDate());
},
setDate: function (d) {
var r;
d = new Date(d);
r = this._dateNumberStringyFy(d.getFullYear(), d.getMonth() + 1, d.getDate());
this._addDate(r);
if (this.options.syncCalenderToDateField) {
this._year = d.getFullYear();
this._month = d.getMonth();
this._day = d.getDate();
}
this._renderCalendar();
},
setDateExclude: function (d) {
var r;
d = new Date(d);
r = this._dateNumberStringyFy(d.getFullYear(), d.getMonth() + 1, d.getDate());
this._addDateExclude(r);
this._renderCalendar();
},
setDateStored: function (d) {
var r;
d = new Date(d);
r = this._dateNumberStringyFy(d.getFullYear(), d.getMonth() + 1, d.getDate());
this._addDateStored(r);
this._renderCalendar();
},
getDate: function (index) {
return new Date(index !== undefined ? this.element.data('_storage')[index] : this.element.data('_storage')[0]).format(this.options.format);
},
getDates: function () {
var res;
res = $.merge($.merge([], this.element.data('_storage')), this.element.data('_stored'));
return res.unique();
},
unsetDate: function (d) {
var r;
d = new Date(d);
r = this._dateNumberStringyFy(d.getFullYear(), d.getMonth() + 1, d.getDate());
this._removeDate(r);
this._renderCalendar();
},
unsetDateExclude: function (d) {
var r;
d = new Date(d);
r = this._dateNumberStringyFy(d.getFullYear(), d.getMonth() + 1, d.getDate());
this._removeDateExclude(r);
this._renderCalendar();
},
unsetDateStored: function (d) {
var r;
d = new Date(d);
r = this._dateNumberStringyFy(d.getFullYear(), d.getMonth() + 1, d.getDate());
this._removeDateStored(r);
this._renderCalendar();
},
_destroy: function () { },
_setOption: function (key, value) {
this._super('_setOption', key, value);
}
});