應用場景是公司的一個每日推薦專題須要加入日曆功能,點擊日曆能夠跳轉到當日的推薦。vue
設計圖:框架
日曆實現的核心是利用js的Date對象(項目代碼環境是依賴在vue當中)。mvvm
咱們首先考慮咱們日曆的第一頁,當前月。函數
要展現咱們的當前月,首先咱們須要三個數據:this
這些數據的初始化(注意這裏只是初始化,由於在日曆的使用過程當中,他們是會隨着交互而變化的)狀態很好得到,前兩個數據咱們只須要經過:spa
this.curdate = new Date();
this.calendarMonth = this.curDate.getMonth() + 1; // 注意月份加1
this.calendarYear = this.curDate.getFullYear();
複製代碼
值得一提的是咱們的日期數據,由於這裏涉及到2個變量,第一個是每月份的天數是不同的。第二個是每月的1號是星期幾也是不固定的(而這個星期幾,則會影響到顯示上,1號應該從哪裏開始)。設計
直接貼上最終的獲取列表的代碼:code
/* 返回當月的日期表 */
getMonthList() {
// new Date()中的最後一個參數爲0,表示的是當月的最後一天,
// 所以咱們經過這一句得到的就是傳入的年月的當月最後一天。
let date = new Date(this.calendarYear, this.calendarMonth, 0);
// 得到當月的最後一天的日期號,就知道了當月有多少天
this.days = date.getDate();
// setDate(1)的做用是把日期變爲當月的第一天
date.setDate(1);
// 在經過getDay(),就能知道當月的第一天是星期幾
let day = date.getDay();
// 得到1號是星期幾後,在日曆上作一個偏移,這裏我採用的是補0
let delay = day - 1;
// 由於星期天在getDay的返回中是0,固特殊處理
if (day == 0) {
delay = 6;
}
let list = [];
for (let i = 0; i < this.days + delay; i++) {
if (i < delay) {
list.push(0);
} else {
list.push(i - delay + 1)
}
}
return list;
},
// 經過這個函數咱們就得到了當月的列表,格式相似於[0,0,0,1,2,3...31]
複製代碼
變化主要分爲兩個方面:點擊左右箭頭改變月份,點擊具體的日期。cdn
改變月份時咱們要作的主要工做是改變咱們用於記錄時間的變量(使用mvvm框架的好處是咱們不須要關注視圖層面的改變,只須要專一咱們的變量):對象
changeMonth(flag) {
// flag 記錄左右滑動,對應到月份就是加1和減1
this.curDate.setMonth(this.calendarMonth - 1 + flag);
// setNowDate() 函數裏面包括了咱們每次改變日期時所須要作的工做,好比刷新月份列表(即從新調用getMonthList函數等其餘一些功能)
//若是咱們要把日曆作成一個組件,那麼咱們的函數中確定須要觸發一個事件鉤子以反饋給外部例如:$emit('monthChange')
this.setNowDate();
},
複製代碼
changeDay(day, el) {
// 改變個人當前顯示日期
this.curDate.setDate(day);
// clickedMonth是用來記錄我當前點擊的月份,這個變量只隨點擊改變,而不隨頁面翻動改變,主要是用來判斷當前日期的樣式用的。
this.clickedMonth = this.calendarMonth;
this.clickedYear = this.calendarYear;
// 獲取當前日曆的推薦數據(具體邏輯不贅述,這裏能夠進行本身須要的操做)
this.getData(new Date(this.calendarYear, this.calendarMonth - 1, day), true)
this.setNowDate();
},
複製代碼
點擊了日期後,咱們的樣式也會隨之改變:
// 計算樣式的函數
calDayCls(day) {
let cls = "calendar-li";
/* 查看當前 */
if (day == this.calendarDay && this.calendarYear == this.clickedYear && this.calendarMonth == this.clickedMonth) {
cls += ' calendar-li-active';
}
return cls
}
複製代碼
至此,咱們的日曆的核心功能就完成了,核心函數以下:
setNowDate // 改變控制當前日曆顯示的變量
changeMonth // 改變月份
getMonthList // 獲取月份日期表
changeDay // 改變日期
calDayCls // 計算當前日期的樣式
複製代碼
有了這些核心部分,就基本實現了日曆的核心功能,而後就能夠在上面添加更多的自定義的功能了,由於不少是涉及到我本身項目中個性化的東西,不具有過多參考價值,固沒有在代碼體現。