教你用原生CSS寫炫酷頁面切換效果,跟第三方元件說拜拜
因為專案需要,別人想讓我給他寫一個個人部落格,並且給了我一個其他人的網頁,可以點此檢視。有的同學可能說了,第三方部落格框架這麼多,為什麼還要去手寫的,你說這個有可能是沒有看到開啟這個部落格。
樣式介紹
給大家看一下這個網頁的大體樣式。
這個介面可以說是非常漂亮,整體也是一個響應式佈局,總體來說還算不錯。但是拋開頁面設計,這個網站有一個致命的缺點,就是沒有做懶載入,這麼多頁面其實就是一個HTML檔案,所有的資源圖片以及文字資訊等全部是一次性載入,所以你想開啟這個介面還是比較困難的,需要等待一些時間。
我們這次只看設計。其實用Vue的朋友們應該都聽過element-ui
這個元件庫,它裡面有一個抽屜元件可以用。其實用這種現成的元件的侷限性大家都很清楚,雖然說開發很快,但是定製化有很多限制,向上面GIF圖中的效果他就不能很好的實現。於是本著學習的態度我們來實現一下這個樣式。
實現方法
話不多說,我們先來看一下實現效果
我們大致實現了想要實現的效果:
- 點選不同標籤頁出現相應介面
- 切換動畫
- 點選蒙版收回頂層標籤頁
切換動畫
動畫的實現方法有很多,在CSS裡面寫動畫的話我比較常用keyframes,但是在這裡我是用js來控制動畫,沒有使用css動畫屬性。js實現動畫的話大家思考一下連環畫的生成原理,其實就是在很短的事件裡面對圖片的頻繁移動,只要移動速度合適,我們的眼睛就會認為我們看到了一個移動的物體。
我js實現動畫的原理和此類似,設定一個延時與起始位置,讓他在規定時間內按照liner均勻移動,當然你也可以不使用liner,比如說X2,這些也都是可以的。
關於實現方法,我是寫了一個animation類,這個類包括延時、函式(liner或者其他漸變函式)、completed等,可以很好地進行動畫生成與控制。下面來看一下這段程式碼
class Animator { // 建構函式 constructor() { this.durationTime = 0; this.easingFn = k => k; this.eventHandlers = new Map(); } // 動畫移動速度所用的函式 easing(fn) { if (typeof fn !== "function") { throw new Error("Easing must be a function, such as k => k"); } this.easingFn = fn; return this; } // 動畫時間 duration(time) { if (typeof time !== "number") { throw new Error("Duration must be a number"); } this.durationTime = time; return this; } // 響應函式 on(type, handler) { if (typeof handler !== "function") { throw new Error("Handler must be a function"); } this.eventHandlers.set(type, handler); return this; } // 動畫生成 animate() { const duration = this.durationTime; const easing = this.easingFn; const update = this.eventHandlers.get("update") || (t => t); const complete = this.eventHandlers.get("complete") || (() => {}); let timer = null; const startTime = +new Date(); function step() { const percent = Math.min(1, (+new Date() - startTime) / duration); if (percent < 1) { update(easing(percent)); timer = requestAnimationFrame(step); } else { cancelAnimationFrame(timer); update(easing(1)); complete(); } } timer = requestAnimationFrame(step); } } /* * 這裡是專門寫了一個產生動畫的函式 * 傳參: start:Number, step:Number, el:object(元素物件) * 傳入這些引數之後就可以產生相應的動畫效果 */ var move = function(start, step, el) { new Animator() .duration(200) .easing(k => k) .on("update", t => { el.style.right = String(start + t * step) + "%"; }) .animate(); };
網頁佈局
其實像這種抽屜式的網頁佈局大家應該都不陌生,大概就是設定position
為absolute
,然後再使用left
或者right
屬性進行佈局,我在文章下面會給出全部程式碼的下載連結,大家如果感興趣可以下載來看一下。
點選邏輯
通過我前面的介紹,大家應該是可以知道這個demo是可以通過按鈕點選觸發,也是可以通過點選蒙版來觸發的,當我的滑鼠移到蒙版的時候滑鼠會改變一個樣式,這個只要設定一個屬性就可以啦
.overlay {
cursor: url("你的圖示url"), pointer;
}
具體的邏輯大家可以參照這個思維導圖
其實當時這個邏輯搞了比較長時間,大家應該可以想到實現多個標籤頁的點選應該是使用棧來實現,始終把顯示出來的抽屜頁放在最頂層,這樣也方便我們進行後續操作。
網頁原始碼
需要原始碼的朋友可以點此下載