import ngModule from '../module'; import Component from 'core/lib/component'; import './style.scss'; class Controller extends Component { constructor($element, $, vnWeekDays) { super($element, $); this.vnWeekDays = vnWeekDays; this.nMonths = 4; let date = new Date(); date.setDate(1); date.setHours(0, 0, 0, 0); this.date = date; } get date() { return this._date; } set date(value) { this._date = value; let stamp = value.getTime(); let firstDay = new Date(stamp); firstDay.setDate(1); this.firstDay = firstDay; let lastDay = new Date(stamp); lastDay.setMonth(lastDay.getMonth() + this.nMonths); lastDay.setDate(0); this.lastDay = lastDay; this.months = []; for (let i = 0; i < this.nMonths; i++) { let monthDate = new Date(stamp); monthDate.setMonth(value.getMonth() + i); this.months.push(monthDate); } this.refreshEvents(); } step(direction) { let date = new Date(this.date.getTime()); date.setMonth(date.getMonth() + (this.nMonths * direction)); this.date = date; this.emit('step'); } get data() { return this._data; } set data(value) { this._data = value; value = value || {}; this.events = value.events; function toStamp(date) { return date && new Date(date).setHours(0, 0, 0, 0); } this.exclusions = {}; let exclusions = value.exclusions; if (exclusions) { for (let exclusion of exclusions) { let stamp = toStamp(exclusion.dated); if (!this.exclusions[stamp]) this.exclusions[stamp] = []; this.exclusions[stamp].push(exclusion); } } this.geoExclusions = {}; let geoExclusions = value.geoExclusions; if (geoExclusions) { for (let geoExclusion of geoExclusions) { let stamp = toStamp(geoExclusion.dated); if (!this.geoExclusions[stamp]) this.geoExclusions[stamp] = []; this.geoExclusions[stamp].push(geoExclusion); } } let events = value.events; if (events) { for (let event of events) { event.dated = toStamp(event.dated); event.ended = toStamp(event.ended); event.started = toStamp(event.started); event.wdays = this.vnWeekDays.fromSet(event.weekDays); } } this.refreshEvents(); let calendars = this.element.querySelectorAll('vn-calendar'); for (let calendar of calendars) calendar.$ctrl.repaint(); } refreshEvents() { this.days = {}; if (!this.data) return; let day = new Date(this.firstDay.getTime()); while (day <= this.lastDay) { let stamp = day.getTime(); let wday = day.getDay(); let dayEvents = []; let exclusions = this.exclusions[stamp] || []; if (this.events) { for (let event of this.events) { let match; switch (event.type) { case 'day': match = event.dated == stamp; break; default: match = event.wdays[wday] && (!event.started || stamp >= event.started) && (!event.ended || stamp <= event.ended); break; } if (match && !exclusions.find(e => e.zoneFk == event.zoneFk)) dayEvents.push(event); } } if (dayEvents.length) this.days[stamp] = dayEvents; day.setDate(day.getDate() + 1); } } onSelection($event, $days, $type, $weekday) { let $events = []; let $exclusions = []; let $geoExclusions = []; for (let day of $days) { let stamp = day.getTime(); $events = $events.concat(this.days[stamp] || []); $exclusions = $exclusions.concat(this.exclusions[stamp] || []); $geoExclusions = $geoExclusions.concat(this.geoExclusions[stamp] || []); } this.emit('selection', { $event, $days, $type, $weekday, $events, $exclusions, $geoExclusions }); } hasEvents(day) { let stamp = day.getTime(); return this.days[stamp] || this.exclusions[stamp] || this.geoExclusions[stamp]; } getClass(day) { let stamp = day.getTime(); if (this.geoExclusions[stamp]) return 'geoExcluded'; else if (this.exclusions[stamp]) return 'excluded'; else return ''; } } Controller.$inject = ['$element', '$scope', 'vnWeekDays']; ngModule.vnComponent('vnZoneCalendar', { template: require('./index.html'), controller: Controller, bindings: { data: '