做了兩天了,簡單的談一下感受,這個(gè)項(xiàng)目雖然推出了好幾年了(2016),前端圈發(fā)生了天翻地覆的變化,隨著三大框架的流行, jQuery和原生JS 開發(fā)在國內(nèi)逐漸失去主流地位,但是萬變不離其宗。原生JS至關(guān)重要。因?yàn)镴S是這一切的基礎(chǔ),就像高樓大廈的地基一樣,你總不能直接就開始四樓五樓吧,那是不現(xiàn)實(shí)的。
簡介:JavaScript30 是 Wes Bos 推出的一個(gè) 30 天挑戰(zhàn)。項(xiàng)目免費(fèi)提供了 30 個(gè)視頻教程、30 個(gè)挑戰(zhàn)的起始文檔和 30 個(gè)挑戰(zhàn)解決方案源代碼。目的是幫助人們用純 JavaScript 來寫東西,不借助框架和庫,也不使用編譯器和引用?,F(xiàn)在你看到的是這系列指南的第 2 篇。完整指南在 GitHub,喜歡請 Star 哦?(?*)
實(shí)現(xiàn)效果
[圖片上傳失敗...(image-5d82d1-1632934898764)]
文檔中已經(jīng)給出了 HTML 結(jié)構(gòu),表盤內(nèi)有三個(gè) div 對應(yīng)三個(gè)指針。只需要添加一些 CSS 效果,然后用 JavaScript 動態(tài)更新指針的狀態(tài)即可
關(guān)鍵要點(diǎn)
- 表盤上指針的樣式:旋轉(zhuǎn)的效果
- 獲取實(shí)時(shí)的時(shí)間
- 每一秒改變一次指針狀態(tài)
涉及到的特性:
transform: rotate()transitionsetInterval(callback, time)setTimeoutnew Date()Date().getSeconds()Date().getMinutes()-
Date().getHours()
Window.requestAnimationFrame()
過程指南
CSS 部分
在原作者的基礎(chǔ)上稍稍改進(jìn)了一下 增加了三個(gè)偽元素 指針旋轉(zhuǎn)軸與表盤中心重合
.second-hand::after {
position: absolute;
content: '';
display: block;
width: 5px;
height: 50%;
background-color: red;
left: 50%;
bottom: 50%;
transform: translate(-50%, 0);
}
.min-hand::after {
position: absolute;
content: '';
display: block;
width: 10px;
height: 40%;
background-color: white;
left: 50%;
bottom: 50%;
transform: translate(-50%, 0);
}
.hour-hand::after {
position: absolute;
content: '';
display: block;
width: 15px;
height: 20%;
background-color: white;
left: 50%;
bottom: 50%;
transform: translate(-50%, 0);
}
用偽元素 增加一個(gè)表盤的中心點(diǎn)
.clock-face:after {
content: '';
display: block;
width: 30px;
height: 30px;
border-radius: 100%;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
background: white;
}
JS部分
-
利用定時(shí)器自動更新時(shí)間 有三種方式實(shí)現(xiàn)這種方法
- 定時(shí)器
setInterval可以每隔一段固定的時(shí)間將操作放入執(zhí)行隊(duì)列,利用這個(gè)特性,加入頁面后每秒更新一次時(shí)間,以實(shí)現(xiàn)秒針轉(zhuǎn)動的效果。
setInterval(setDate, 1000); // setDate 為每 1000 毫秒觸發(fā)的 function- 定時(shí)器
setTimeout設(shè)定延時(shí) 執(zhí)行一次 配合回調(diào)函數(shù) 形式 ,加入頁面后每秒更新一次時(shí)間,以實(shí)現(xiàn)秒針轉(zhuǎn)動的效果。
- 定時(shí)器
function timeoutHandler() {
setClock(); //執(zhí)行 函數(shù)
setTimeout(timeoutHandler, 1000)
}
setTimeout(timeoutHandler, 1000)
function animationHandler() {
setClock();
window.requestAnimationFrame(animationHandler)
}
window.requestAnimationFrame(animationHandler)
- 獲取三個(gè)指針對應(yīng)的 HTML 元素,留待后續(xù)操作
const second = document.querySelector('.second-hand'); //秒針
const min = document.querySelector('.min-hand'); //分表
const hour = document.querySelector('.hour-hand'); //時(shí)針
- 編寫 setClock 方法
創(chuàng)建 Date 對象
獲取當(dāng)前時(shí)間的小時(shí)、分鐘、秒
-
利用此刻的數(shù)據(jù),計(jì)算每個(gè)指針對應(yīng)的角度
let secondDeg = data.getSeconds() * 6 //(360/60)以秒針為例,由于此頁面初始狀態(tài)中秒針為垂直的,所以零點(diǎn)時(shí)(時(shí)間起始位置)應(yīng)用到元素上的
rotate旋轉(zhuǎn)角度值應(yīng)該為 6°。秒針轉(zhuǎn)一圈為 60s,所以每一秒對應(yīng)表盤上的角度值即為 (...s / 60s) 。Wes Bos 給出的解決方案中,時(shí)針是和秒針一樣每一小時(shí)跳動一次,若要模擬更加真實(shí)的時(shí)鐘,要使時(shí)針在一小時(shí)內(nèi)緩慢的移動到下一個(gè)時(shí)間點(diǎn)。所以可以利用上分鐘,計(jì)算每一分鐘對時(shí)針的角度影響,將加到時(shí)針角度上即可。
let minDeg = data.getMinutes() * 6 + data.getSeconds() * 6 / 60 //(360/60) let hourDeg = data.getHours() * 30 + data.getMinutes() * 30 / 60 //(360/12) 將角度值賦值給 HTML 元素的
style中的transform屬性
//動態(tài)改變樣式 表盤時(shí)針旋轉(zhuǎn)的角度
second.style.transform = `rotate(${secondDeg}deg)`
min.style.transform = `rotate(${minDeg}deg)`
hour.style.transform = `rotate(${hourDeg}deg)`