UNPKG

21.4 kBJavaScriptView Raw
1/**
2 * color-calendar
3 * v1.0.4
4 * by Pawan Kolhe <contact@pawankolhe.com> (https://pawankolhe.com/)
5 */
6
7"use strict";function e(){this.prevButton.addEventListener("click",this.handlePrevMonthButtonClick.bind(this)),this.nextButton.addEventListener("click",this.handleNextMonthButtonClick.bind(this)),this.monthyearDisplay.addEventListener("click",this.handleMonthYearDisplayClick.bind(this)),this.calendarDays.addEventListener("click",this.handleCalendarDayClick.bind(this)),this.pickerMonthContainer.addEventListener("click",this.handleMonthPickerClick.bind(this)),this.pickerYearContainer.addEventListener("click",this.handleYearPickerClick.bind(this)),this.yearPickerChevronLeft.addEventListener("click",this.handleYearChevronLeftClick.bind(this)),this.yearPickerChevronRight.addEventListener("click",this.handleYearChevronRightClick.bind(this))}function t(){let e=this.calendarRoot;this.primaryColor&&e.style.setProperty("--cal-color-primary",this.primaryColor),this.fontFamilyHeader&&e.style.setProperty("--cal-font-family-header",this.fontFamilyHeader),this.fontFamilyWeekdays&&e.style.setProperty("--cal-font-family-weekdays",this.fontFamilyWeekdays),this.fontFamilyBody&&e.style.setProperty("--cal-font-family-body",this.fontFamilyBody),this.dropShadow&&e.style.setProperty("--cal-drop-shadow",this.dropShadow),this.border&&e.style.setProperty("--cal-border",this.border),this.borderRadius&&e.style.setProperty("--cal-border-radius",this.borderRadius),this.headerColor&&e.style.setProperty("--cal-header-color",this.headerColor),this.headerBackgroundColor&&e.style.setProperty("--cal-header-background-color",this.headerBackgroundColor),this.weekdaysColor&&e.style.setProperty("--cal-weekdays-color",this.weekdaysColor)}function a(e){!0===e?(this.pickerContainer.style.visibility="visible",this.pickerContainer.style.opacity="1","year"===this.pickerType&&this.generatePickerYears(),this.removeYearPickerSelection(),this.updateYearPickerSelection(this.currentDate.getFullYear())):!1===e?(this.pickerContainer.style.visibility="hidden",this.pickerContainer.style.opacity="0",this.monthDisplay&&this.yearDisplay&&(this.monthDisplay.style.opacity="1",this.yearDisplay.style.opacity="1"),this.yearPickerOffsetTemporary=0):"hidden"===this.pickerContainer.style.visibility?(this.pickerContainer.style.visibility="visible",this.pickerContainer.style.opacity="1","year"===this.pickerType&&this.generatePickerYears(),this.removeYearPickerSelection(),this.updateYearPickerSelection(this.currentDate.getFullYear())):(this.pickerContainer.style.visibility="hidden",this.pickerContainer.style.opacity="0",this.monthDisplay&&this.yearDisplay&&(this.monthDisplay.style.opacity="1",this.yearDisplay.style.opacity="1"),this.yearPickerOffsetTemporary=0)}function i(e){if(!e.target.classList.contains("calendar__picker-month-option"))return;const t=parseInt(e.target.dataset.value);this.updateMonthPickerSelection(t),this.updateCurrentDate(0,void 0,t),this.togglePicker(!1)}function r(e){e<0?e=11:e%=12,this.removeMonthPickerSelection(),this.pickerMonthContainer.children[e].classList.add("calendar__picker-month-selected")}function n(){for(let e=0;e<12;e++)this.pickerMonthContainer.children[e].classList.contains("calendar__picker-month-selected")&&this.pickerMonthContainer.children[e].classList.remove("calendar__picker-month-selected")}function s(e){if(!e.target.classList.contains("calendar__picker-year-option"))return;this.yearPickerOffset+=this.yearPickerOffsetTemporary;const t=parseInt(e.target.innerText),a=parseInt(e.target.dataset.value);this.updateYearPickerSelection(t,a),this.updateCurrentDate(0,void 0,void 0,t),this.togglePicker(!1)}function d(e,t){if(void 0===t){for(let a=0;a<12;a++){let i=this.pickerYearContainer.children[a];if(parseInt(i.innerHTML)===e&&i.dataset.value){t=parseInt(i.dataset.value);break}}if(void 0===t)return}this.removeYearPickerSelection(),this.pickerYearContainer.children[t].classList.add("calendar__picker-year-selected")}function l(){parseInt(this.pickerYearContainer.children[4].innerHTML)===this.today.getFullYear()?this.pickerYearContainer.children[4].classList.add("calendar__picker-year-today"):this.pickerYearContainer.children[4].classList.remove("calendar__picker-year-today")}function c(){for(let e=0;e<12;e++)this.pickerYearContainer.children[e].classList.contains("calendar__picker-year-selected")&&this.pickerYearContainer.children[e].classList.remove("calendar__picker-year-selected")}function o(){const e=this.today.getFullYear()+this.yearPickerOffset+this.yearPickerOffsetTemporary;let t=0;for(let a=e-4;a<=e+7;a++){this.pickerYearContainer.children[t].innerText=a.toString(),t++}this.updateYearPickerTodaySelection()}function h(){this.yearPickerOffsetTemporary-=12,this.generatePickerYears(),this.removeYearPickerSelection(),this.updateYearPickerSelection(this.currentDate.getFullYear()),this.updateYearPickerTodaySelection()}function y(){this.yearPickerOffsetTemporary+=12,this.generatePickerYears(),this.removeYearPickerSelection(),this.updateYearPickerSelection(this.currentDate.getFullYear()),this.updateYearPickerTodaySelection()}function u(e){this.monthDisplayType=e,this.updateMonthYear()}function p(e){if(!e.target.classList.contains("calendar__month")&&!e.target.classList.contains("calendar__year"))return;if(this.disableMonthYearPickers)return;const t=this.pickerType,a=e.target.classList;a.contains("calendar__month")?(this.pickerType="month",this.monthDisplay.style.opacity="1",this.yearDisplay.style.opacity="0.7",this.pickerMonthContainer.style.display="grid",this.pickerYearContainer.style.display="none"):a.contains("calendar__year")&&(this.pickerType="year",this.monthDisplay.style.opacity="0.7",this.yearDisplay.style.opacity="1",this.pickerMonthContainer.style.display="none",this.pickerYearContainer.style.display="grid"),t===this.pickerType?this.togglePicker():this.togglePicker(!0)}function _(){if(this.disableMonthArrowClick)return;const e=this.currentDate.getMonth()-1;this.currentDate.getFullYear()<=this.today.getFullYear()+this.yearPickerOffset-4&&e<0&&(this.yearPickerOffset-=12,this.generatePickerYears()),e<0&&this.updateYearPickerSelection(this.currentDate.getFullYear()-1),this.updateMonthPickerSelection(e),this.updateCurrentDate(-1),this.togglePicker(!1)}function v(){if(this.disableMonthArrowClick)return;const e=this.currentDate.getMonth()+1;this.currentDate.getFullYear()>=this.today.getFullYear()+this.yearPickerOffset+7&&e>11&&(this.yearPickerOffset+=12,this.generatePickerYears()),e>11&&this.updateYearPickerSelection(this.currentDate.getFullYear()+1),this.updateMonthPickerSelection(e),this.updateCurrentDate(1),this.togglePicker(!1)}function k(){this.oldSelectedNode=null,this.monthDisplay.innerHTML=new Intl.DateTimeFormat("default",{month:this.monthDisplayType}).format(this.currentDate),this.yearDisplay.innerHTML=this.currentDate.getFullYear().toString()}function D(e){var t;this.weekdayDisplayType=e,this.weekdays=null!==(t=this.weekdayDisplayTypeOptions[this.weekdayDisplayType])&&void 0!==t?t:this.weekdayDisplayTypeOptions.short,this.generateWeekdays()}function f(){let e="";for(let t=0;t<7;t++)e+=`\n <div class="calendar__weekday">${this.weekdays[(t+this.startWeekday)%7]}</div>\n `;this.calendarWeekdays.innerHTML=e}function g(e){e&&(e instanceof Date?this.reset(e):this.reset(new Date(e)))}function m(){return this.currentDate}function C(){this.daysIn_PrevMonth=[],this.daysIn_CurrentMonth=[],this.daysIn_NextMonth=[]}function M(e){e&&(this.updateMonthYear(),this.clearCalendarDays(),this.generateDays(),this.selectDayInitial()),this.renderDays(),e&&this.setOldSelectedNode()}function P(){if(!this.oldSelectedNode){let e=void 0;for(let t=1;t<this.calendarDays.childNodes.length;t+=2){let a=this.calendarDays.childNodes[t];if(a.classList&&a.classList.contains("calendar__day-active")&&a.innerText===this.currentDate.getDate().toString()){e=a;break}}e&&(this.oldSelectedNode=[e,parseInt(e.innerText)])}}function S(e){if(e)this.daysIn_CurrentMonth[this.currentDate.getDate()-1].selected=!0;else{let e=this.today.getMonth()===this.currentDate.getMonth(),t=this.today.getDate()===this.currentDate.getDate();e&&t?this.daysIn_CurrentMonth[this.today.getDate()-1].selected=!0:this.daysIn_CurrentMonth[0].selected=!0}}function Y(e){if(!(e.target.classList.contains("calendar__day-box")||e.target.classList.contains("calendar__day-text")||e.target.classList.contains("calendar__day-box-today")||e.target.classList.contains("calendar__day-bullet"))||e.target.parentElement.classList.contains("calendar__day-selected"))return;if(this.disableDayClick)return;if(this.oldSelectedNode&&!this.oldSelectedNode[0])return;let t,a;t=e.target.parentElement.innerText,a=parseInt(t,10),this.removeOldDaySelection(),t&&(this.updateCurrentDate(0,a),Object.assign(this.daysIn_CurrentMonth[a-1],{selected:!0}),this.rerenderSelectedDay(e.target.parentElement,a,!0))}function w(){this.oldSelectedNode&&(Object.assign(this.daysIn_CurrentMonth[this.oldSelectedNode[1]-1],{selected:!1}),this.rerenderSelectedDay(this.oldSelectedNode[0],this.oldSelectedNode[1]))}function T(e,t,a,i){this.currentDate=new Date(i||this.currentDate.getFullYear(),null!=a?a:this.currentDate.getMonth()+e,0===e&&t?t:1),(0!==e||null!=a||i)&&(this.updateCalendar(!0),this.monthChanged&&this.monthChanged(this.currentDate,this.getMonthEvents())),this.dateChanged&&this.dateChanged(this.currentDate,this.getDateEvents(this.currentDate))}function b(){this.numOfDays_PrevMonth=new Date(this.currentDate.getFullYear(),this.currentDate.getMonth(),0).getDate(),this.firstDay_CurrentMonth=new Date(this.currentDate.getFullYear(),this.currentDate.getMonth(),1).getDay(),this.numOfDays_CurrentMonth=new Date(this.currentDate.getFullYear(),this.currentDate.getMonth()+1,0).getDate();for(let e=0;e<this.numOfDays_CurrentMonth;e++)this.daysIn_CurrentMonth.push({day:e+1,selected:!1})}function L(){let e=0;const t=this.currentDate.getFullYear(),a=this.currentDate.getMonth();let i;this.filteredEventsThisMonth=this.eventsData.filter(e=>{const i=new Date(e.start);return i.getFullYear()===t&&i.getMonth()===a}),this.eventDayMap={},this.filteredEventsThisMonth.forEach(e=>{const t=new Date(e.start).getDate(),a=new Date(e.end).getDate();for(let e=t;e<=a;e++)this.eventDayMap[e]=!0}),i=this.firstDay_CurrentMonth<this.startWeekday?7+this.firstDay_CurrentMonth-this.startWeekday:this.firstDay_CurrentMonth-this.startWeekday;let r="";for(let t=0;t<i;t++)r+=`\n <div class="calendar__day calendar__day-other">${this.numOfDays_PrevMonth+1-i+t}</div>\n `,e++;let n=this.today.getFullYear()===this.currentDate.getFullYear(),s=this.today.getMonth()===this.currentDate.getMonth()&&n;this.daysIn_CurrentMonth.forEach(t=>{let a=s&&t.day===this.today.getDate();r+=`\n <div class="calendar__day calendar__day-active${a?" calendar__day-today":""}${this.eventDayMap[t.day]?" calendar__day-event":" calendar__day-no-event"}${t.selected?" calendar__day-selected":""}">\n <span class="calendar__day-text">${t.day}</span>\n <div class="calendar__day-bullet"></div>\n <div class="calendar__day-box"></div>\n </div>\n `,e++});for(let t=0;t<this.DAYS_TO_DISPLAY-e;t++)r+=`\n <div class="calendar__day calendar__day-other">${t+1}</div>\n `;this.calendarDays.innerHTML=r}function O(e,t,a){let i=e.previousElementSibling,r=this.today.getFullYear()===this.currentDate.getFullYear(),n=this.today.getMonth()===this.currentDate.getMonth()&&r&&t===this.today.getDate(),s=document.createElement("div");s.className+=`calendar__day calendar__day-active${n?" calendar__day-today":""}${this.eventDayMap[t]?" calendar__day-event":" calendar__day-no-event"}${this.daysIn_CurrentMonth[t-1].selected?" calendar__day-selected":""}`,s.innerHTML=`\n <span class="calendar__day-text">${t}</span>\n <div class="calendar__day-bullet"></div>\n <div class="calendar__day-box"></div>\n `,i?i.parentElement?i.parentElement.insertBefore(s,i.nextSibling):console.log("Previous element does not have parent"):this.calendarDays.insertBefore(s,e),a&&(this.oldSelectedNode=[s,t]),e.remove()}function E(){return JSON.parse(JSON.stringify(this.eventsData))}function F(e){return this.eventsData=JSON.parse(JSON.stringify(e)),this.setDate(this.currentDate),this.eventsData.length}function N(e=[]){const t=this.eventsData.push(...e);return this.setDate(this.currentDate),t}function I(e){return this.filteredEventsThisMonth.filter(t=>{const a=new Date(t.start).getDate(),i=new Date(t.end).getDate();return e.getDate()>=a&&e.getDate()<=i})}function x(){return this.filteredEventsThisMonth}module.exports=class{constructor(A={}){var W,B,$,H,q,R,J,z,U,j,G,K;if(this.CAL_NAME="color-calendar",this.DAYS_TO_DISPLAY=42,this.weekdayDisplayTypeOptions={short:["S","M","T","W","T","F","S"],"long-lower":["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],"long-upper":["SUN","MON","TUE","WED","THU","FRI","SAT"]},this.id=null!==(W=A.id)&&void 0!==W?W:"#color-calendar",this.calendarSize=null!==(B=A.calendarSize)&&void 0!==B?B:"large",this.layoutModifiers=null!==($=A.layoutModifiers)&&void 0!==$?$:[],this.eventsData=null!==(H=A.eventsData)&&void 0!==H?H:[],this.monthDisplayType=null!==(q=A.monthDisplayType)&&void 0!==q?q:"long",this.startWeekday=null!==(R=A.startWeekday)&&void 0!==R?R:0,this.theme=null!==(J=A.theme)&&void 0!==J?J:"basic",this.primaryColor=A.primaryColor,this.fontFamilyHeader=A.fontFamilyHeader,this.fontFamilyWeekdays=A.fontFamilyWeekdays,this.fontFamilyBody=A.fontFamilyBody,this.dropShadow=A.dropShadow,this.border=A.border,this.borderRadius=A.borderRadius,this.headerColor=A.headerColor,this.headerBackgroundColor=A.headerBackgroundColor,this.weekdaysColor=A.weekdaysColor,this.disableMonthYearPickers=null!==(z=A.disableMonthYearPickers)&&void 0!==z&&z,this.disableDayClick=null!==(U=A.disableDayClick)&&void 0!==U&&U,this.disableMonthArrowClick=null!==(j=A.disableMonthArrowClick)&&void 0!==j&&j,this.monthChanged=A.monthChanged,this.dateChanged=A.dateChanged,this.weekdayDisplayType=null!==(G=A.weekdayDisplayType)&&void 0!==G?G:"long",this.weekdays=null!==(K=this.weekdayDisplayTypeOptions[this.weekdayDisplayType])&&void 0!==K?K:this.weekdayDisplayTypeOptions.short,this.today=new Date,this.currentDate=new Date,this.pickerType="month",this.eventDayMap={},this.oldSelectedNode=null,this.filteredEventsThisMonth=[],this.daysIn_PrevMonth=[],this.daysIn_CurrentMonth=[],this.daysIn_NextMonth=[],this.firstDay_PrevMonth=0,this.firstDay_CurrentMonth=0,this.firstDay_NextMonth=0,this.numOfDays_PrevMonth=0,this.numOfDays_CurrentMonth=0,this.numOfDays_NextMonth=0,this.yearPickerOffset=0,this.yearPickerOffsetTemporary=0,this.addEventListeners=e,this.configureStylePreferences=t,this.togglePicker=a,this.handleMonthPickerClick=i,this.updateMonthPickerSelection=r,this.removeMonthPickerSelection=n,this.handleYearPickerClick=s,this.updateYearPickerSelection=d,this.updateYearPickerTodaySelection=l,this.removeYearPickerSelection=c,this.generatePickerYears=o,this.handleYearChevronLeftClick=h,this.handleYearChevronRightClick=y,this.setMonthDisplayType=u,this.handleMonthYearDisplayClick=p,this.handlePrevMonthButtonClick=_,this.handleNextMonthButtonClick=v,this.updateMonthYear=k,this.setWeekdayDisplayType=D,this.generateWeekdays=f,this.setDate=g,this.getSelectedDate=m,this.clearCalendarDays=C,this.updateCalendar=M,this.setOldSelectedNode=P,this.selectDayInitial=S,this.handleCalendarDayClick=Y,this.removeOldDaySelection=w,this.updateCurrentDate=T,this.generateDays=b,this.renderDays=L,this.rerenderSelectedDay=O,this.getEventsData=E,this.setEventsData=F,this.addEventsData=N,this.getDateEvents=I,this.getMonthEvents=x,this.calendar=document.querySelector(this.id),!this.calendar)throw new Error(`[COLOR-CALENDAR] Element with selector '${this.id}' not found`);this.calendar.innerHTML=`\n <div class="${this.CAL_NAME} ${this.theme} color-calendar--${this.calendarSize}">\n <div class="calendar__header">\n <div class="calendar__arrow calendar__arrow-prev"><div class="calendar__arrow-inner"></div></div>\n <div class="calendar__monthyear">\n <span class="calendar__month"></span>&nbsp;\n <span class="calendar__year"></span>\n </div>\n <div class="calendar__arrow calendar__arrow-next"><div class="calendar__arrow-inner"></div></div>\n </div>\n <div class="calendar__body">\n <div class="calendar__weekdays"></div>\n <div class="calendar__days"></div>\n <div class="calendar__picker">\n <div class="calendar__picker-month">\n <div class="calendar__picker-month-option" data-value="0">Jan</div>\n <div class="calendar__picker-month-option" data-value="1">Feb</div>\n <div class="calendar__picker-month-option" data-value="2">Mar</div>\n <div class="calendar__picker-month-option" data-value="3">Apr</div>\n <div class="calendar__picker-month-option" data-value="4">May</div>\n <div class="calendar__picker-month-option" data-value="5">Jun</div>\n <div class="calendar__picker-month-option" data-value="6">Jul</div>\n <div class="calendar__picker-month-option" data-value="7">Aug</div>\n <div class="calendar__picker-month-option" data-value="8">Sep</div>\n <div class="calendar__picker-month-option" data-value="9">Oct</div>\n <div class="calendar__picker-month-option" data-value="10">Nov</div>\n <div class="calendar__picker-month-option" data-value="11">Dec</div>\n </div>\n <div class="calendar__picker-year">\n <div class="calendar__picker-year-option" data-value="0"></div>\n <div class="calendar__picker-year-option" data-value="1"></div>\n <div class="calendar__picker-year-option" data-value="2"></div>\n <div class="calendar__picker-year-option" data-value="3"></div>\n <div class="calendar__picker-year-option" data-value="4"></div>\n <div class="calendar__picker-year-option" data-value="5"></div>\n <div class="calendar__picker-year-option" data-value="6"></div>\n <div class="calendar__picker-year-option" data-value="7"></div>\n <div class="calendar__picker-year-option" data-value="8"></div>\n <div class="calendar__picker-year-option" data-value="9"></div>\n <div class="calendar__picker-year-option" data-value="10"></div>\n <div class="calendar__picker-year-option" data-value="11"></div>\n <div class="calendar__picker-year-arrow calendar__picker-year-arrow-left">\n <div class="chevron-thin chevron-thin-left"></div>\n </div>\n <div class="calendar__picker-year-arrow calendar__picker-year-arrow-right">\n <div class="chevron-thin chevron-thin-right"></div>\n </div>\n </div>\n </div>\n </div>\n </div>\n `,this.calendarRoot=document.querySelector(`${this.id} .${this.CAL_NAME}`),this.calendarHeader=document.querySelector(this.id+" .calendar__header"),this.calendarWeekdays=document.querySelector(this.id+" .calendar__weekdays"),this.calendarDays=document.querySelector(this.id+" .calendar__days"),this.pickerContainer=document.querySelector(this.id+" .calendar__picker"),this.pickerMonthContainer=document.querySelector(this.id+" .calendar__picker-month"),this.pickerYearContainer=document.querySelector(this.id+" .calendar__picker-year"),this.yearPickerChevronLeft=document.querySelector(this.id+" .calendar__picker-year-arrow-left"),this.yearPickerChevronRight=document.querySelector(this.id+" .calendar__picker-year-arrow-right"),this.pickerMonthContainer.children[this.today.getMonth()].classList.add("calendar__picker-month-today"),this.layoutModifiers.forEach(e=>{this.calendarRoot.classList.add(e)}),this.layoutModifiers.includes("month-left-align")&&(this.calendarHeader.innerHTML='\n <div class="calendar__monthyear">\n <span class="calendar__month"></span>&nbsp;\n <span class="calendar__year"></span>\n </div>\n <div class="calendar__arrow calendar__arrow-prev"><div class="calendar__arrow-inner"></div></div>\n <div class="calendar__arrow calendar__arrow-next"><div class="calendar__arrow-inner"></div></div>\n '),this.monthyearDisplay=document.querySelector(this.id+" .calendar__monthyear"),this.monthDisplay=document.querySelector(this.id+" .calendar__month"),this.yearDisplay=document.querySelector(this.id+" .calendar__year"),this.prevButton=document.querySelector(this.id+" .calendar__arrow-prev .calendar__arrow-inner"),this.nextButton=document.querySelector(this.id+" .calendar__arrow-next .calendar__arrow-inner"),this.togglePicker(!1),this.configureStylePreferences(),this.addEventListeners(),this.reset(new Date)}reset(e){this.currentDate=e||new Date,this.clearCalendarDays(),this.updateMonthYear(),this.updateMonthPickerSelection(this.currentDate.getMonth()),this.generatePickerYears(),this.updateYearPickerSelection(this.currentDate.getFullYear(),4),this.updateYearPickerTodaySelection(),this.generateWeekdays(),this.generateDays(),this.selectDayInitial(!!e),this.renderDays(),this.setOldSelectedNode(),this.dateChanged&&this.dateChanged(this.currentDate,this.getDateEvents(this.currentDate)),this.monthChanged&&this.monthChanged(this.currentDate,this.getMonthEvents())}};