Skip to content

Commit 79bda10

Browse files
committed
完成了day29的挑战,更新了主目录readme.md
1 parent 0ae297b commit 79bda10

File tree

6 files changed

+263
-2
lines changed

6 files changed

+263
-2
lines changed

29 - Countdown Timer/README.md

+89
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,89 @@
1+
# 29 Countdown Timer 中文指南
2+
3+
> 本篇作者:©[大史快跑Dashrun](https://github.com/dashrun)——Chinasoft Frontend Developer
4+
5+
> 简介:[JavaScript30](https://javascript30.com)[Wes Bos](https://github.com/wesbos) 推出的一个 30 天挑战。项目免费提供了 30 个视频教程、30 个挑战的起始文档和 30 个挑战解决方案源代码。目的是帮助人们用纯 JavaScript 来写东西,不借助框架和库,也不使用编译器和引用。现在你看到的是这系列指南的第 29 篇。完整指南在 [GitHub](https://github.com/soyaine/JavaScript30),喜欢请 Star 哦♪(^∇^*)
6+
7+
> 创建时间:2017-11-6
8+
最后更新:2017-11-12
9+
10+
## 挑战任务
11+
初始文档`index-start.html`中提供了一个倒计时控制器,从`html`文档的结构可以看出,顶部的按钮可以用来增加倒计时时间,常用的时间间隔已将参数绑定在`data-time`属性上;`display`类用来显示计时的结果。
12+
本次编程挑战的任务是通过javascript代码基于当前时间生成一个倒计时,将`结束时间``剩余时间`分别显示在`diaplay__time-left`类标签和`display__end-time`类标签上。
13+
14+
## 实现效果
15+
![结果展示](https://github.com/dashrun/vanilla-javascript-30/blob/master/29%20-%20Countdown%20Timer/effect.png)
16+
17+
## 编程思路
18+
监听按点击事件`click`来为倒计时增加时间,使用`setInterval`函数每秒执行判断函数,若倒计时事件到,则清除当前计时器,若时间未到,则计算并刷新页面上应该显示的时间。
19+
20+
## 过程指南
21+
1.定义变量及获取需要操作的DOM元素的引用。
22+
```js
23+
const endTime = document.querySelector(".display__end-time");
24+
const leftTime = document.querySelector(".display__time-left");
25+
const buttons = document.querySelectorAll("button");
26+
const date = new Date();
27+
var left = 0;//剩余时间
28+
var end = 0;//结束时间
29+
var timer;//interval计时器
30+
leftTime.innerHTML = left;//未操作时,剩余时间显示0
31+
```
32+
2.为button绑定点击事件,当按钮点击时执行对应的回调函数。
33+
```js
34+
const arr = Array.from(buttons);
35+
arr.map(function(item){
36+
item.addEventListener('click',clickAction);
37+
});
38+
```
39+
3.监听表单的提交事件,注意表单的调用方式。
40+
```js
41+
document.customForm.addEventListener('submit',function(e){
42+
e.preventDefault();
43+
updateTime(this.minutes.value*60);
44+
updateTimer();
45+
});
46+
```
47+
4.点击后的回调函数中取得点击按钮传递的秒数,调用`updateTime()`函数更新页面显示结果,并调用`updateTimer()`来更新计时器相关动作.
48+
```js
49+
function clickAction(e){
50+
let deltaTime;
51+
deltaTime = this.dataset.time;//取得data-time属性的值
52+
updateTime(deltaTime);
53+
54+
//点击后更新计时器
55+
updateTimer();
56+
}
57+
```
58+
5.`updateTime()`函数用来更新和页面相关的显示信息。
59+
```js
60+
function updateTime(delta){
61+
left = left + parseInt(delta,0);
62+
end = date.getTime() + left*1000;
63+
leftTime.innerHTML = left;
64+
endTime.innerHTML =new Date(end).toLocaleTimeString();
65+
}
66+
```
67+
6.`updateTimer()`函数用来执行和设定每秒检查计时器是否需要继续工作的逻辑判断。
68+
```js
69+
function updateTimer(){
70+
//清除以前的timer,如果不清除,新生成的定时器会和以前的定时器叠加在一起,均会生效。
71+
if(timer){
72+
clearInterval(timer);
73+
}
74+
75+
// 设置新的Timer
76+
timer = setInterval(function(){
77+
if(left == 0){
78+
endTime.innerHTML = 'End';
79+
clearInterval(timer);
80+
}else{
81+
left -= 1;
82+
leftTime.innerHTML = left;
83+
}
84+
},1000);
85+
}
86+
```
87+
88+
## 延伸思考
89+
本次代码中前后会定义定时器和清除定时器,另一种做法是定时器一直工作不清除,对应的按钮和表单只修改时间,不用调整定时器,当值发生变化后,下一秒定时器检测时就会开始倒计时,这样代码逻辑上会有所简化,感兴趣的朋友可以自行练习。

29 - Countdown Timer/effect.png

240 KB
Loading

29 - Countdown Timer/index-start.html

+29
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
<!DOCTYPE html>
2+
<html lang="en">
3+
<head>
4+
<meta charset="UTF-8">
5+
<title>Countdown Timer</title>
6+
<link href='https://fonts.googleapis.com/css?family=Inconsolata' rel='stylesheet' type='text/css'>
7+
<link rel="stylesheet" href="style.css">
8+
</head>
9+
<body>
10+
<div class="timer">
11+
<div class="timer__controls">
12+
<button data-time="20" class="timer__button">20 Secs</button>
13+
<button data-time="300" class="timer__button">Work 5</button>
14+
<button data-time="900" class="timer__button">Quick 15</button>
15+
<button data-time="1200" class="timer__button">Snack 20</button>
16+
<button data-time="3600" class="timer__button">Lunch Break</button>
17+
<form name="customForm" id="custom">
18+
<input type="text" name="minutes" placeholder="Enter Minutes">
19+
</form>
20+
</div>
21+
<div class="display">
22+
<h1 class="display__time-left"></h1>
23+
<p class="display__end-time"></p>
24+
</div>
25+
</div>
26+
27+
<script src="scripts-START.js"></script>
28+
</body>
29+
</html>

29 - Countdown Timer/scripts-START.js

+61
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
const endTime = document.querySelector(".display__end-time");
2+
const leftTime = document.querySelector(".display__time-left");
3+
const buttons = document.querySelectorAll("button");
4+
const date = new Date();
5+
var left = 0;//剩余时间
6+
var end = 0;//结束时间
7+
var timer;//interval计时器
8+
leftTime.innerHTML = left;//未操作时,剩余时间显示0
9+
10+
//为button绑定点击事件
11+
const arr = Array.from(buttons);
12+
arr.map(function(item){
13+
item.addEventListener('click',clickAction);
14+
});
15+
16+
//监听自定义输入
17+
document.customForm.addEventListener('submit',function(e){
18+
e.preventDefault();
19+
updateTime(this.minutes.value*60);
20+
updateTimer();
21+
});
22+
23+
//定义点击后的回调
24+
function clickAction(e){
25+
let deltaTime;
26+
deltaTime = this.dataset.time;
27+
updateTime(deltaTime);
28+
29+
//点击后更新计时器
30+
updateTimer();
31+
}
32+
33+
34+
35+
//updateTime
36+
function updateTime(delta){
37+
left = left + parseInt(delta,0);
38+
end = date.getTime() + left*1000;
39+
leftTime.innerHTML = left;
40+
endTime.innerHTML =new Date(end).toLocaleTimeString();
41+
}
42+
43+
//每秒刷新时间
44+
function updateTimer(){
45+
//清除以前的timer
46+
if(timer){
47+
clearInterval(timer);
48+
}
49+
50+
// 设置新的Timer
51+
timer = setInterval(function(){
52+
if(left == 0){
53+
endTime.innerHTML = 'End';
54+
clearInterval(timer);
55+
}else{
56+
left -= 1;
57+
leftTime.innerHTML = left;
58+
}
59+
},1000);
60+
}
61+

29 - Countdown Timer/style.css

+82
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
html {
2+
box-sizing: border-box;
3+
font-size: 10px;
4+
background: #8E24AA;
5+
background: linear-gradient(45deg, #42a5f5 0%,#478ed1 50%,#0d47a1 100%);
6+
}
7+
8+
*, *:before, *:after {
9+
box-sizing: inherit;
10+
}
11+
12+
body {
13+
margin:0;
14+
text-align: center;
15+
font-family: 'Inconsolata', monospace;
16+
}
17+
18+
.display__time-left {
19+
font-weight: 100;
20+
font-size: 20rem;
21+
margin: 0;
22+
color:white;
23+
text-shadow:4px 4px 0 rgba(0,0,0,0.05);
24+
}
25+
26+
.timer {
27+
display:flex;
28+
min-height: 100vh;
29+
flex-direction:column;
30+
}
31+
32+
.timer__controls {
33+
display: flex;
34+
}
35+
36+
.timer__controls > * {
37+
flex:1;
38+
}
39+
40+
.timer__controls form {
41+
flex:1;
42+
display:flex;
43+
}
44+
45+
.timer__controls input {
46+
flex:1;
47+
border:0;
48+
padding:2rem;
49+
}
50+
51+
.timer__button {
52+
background:none;
53+
border:0;
54+
cursor: pointer;
55+
color:white;
56+
font-size: 2rem;
57+
text-transform: uppercase;
58+
background:rgba(0,0,0,0.1);
59+
border-bottom:3px solid rgba(0,0,0,0.2);
60+
border-right:1px solid rgba(0,0,0,0.2);
61+
padding:1rem;
62+
font-family: 'Inconsolata', monospace;
63+
}
64+
65+
.timer__button:hover,
66+
.timer__button:focus {
67+
background:rgba(0,0,0,0.2);
68+
outline:0;
69+
}
70+
71+
.display {
72+
flex:1;
73+
display:flex;
74+
flex-direction: column;
75+
align-items: center;
76+
justify-content: center;
77+
}
78+
79+
.display__end-time {
80+
font-size: 4rem;
81+
color:white;
82+
}

README.md

+2-2
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ No | Guide | Demo
6767
25 | [Event Related指南](https://github.com/soyaine/JavaScript30/blob/master/25%20-%20Event%20Related/README.md) | [Event Related效果](https://github.com/soyaine/JavaScript30/blob/master/25%20-%20Event%20Related/index-finished-Dashrun.html)
6868
26 | [Stripe Follow Along Nav指南](https://github.com/soyaine/JavaScript30/blob/master/26%20-%20Stripe%20Follow%20Along%20Nav/README.md) | [Strip Follow Along Nav效果](https://github.com/soyaine/JavaScript30/blob/master/26%20-%20Stripe%20Follow%20Along%20Nav/index-finished-Dashrun.html)
6969
27 | [Click and Drag指南](https://github.com/soyaine/JavaScript30/blob/master/27%20-%20Click%20and%20Drag/README.md) | [Click and Drag效果](https://github.com/soyaine/JavaScript30/blob/master/27%20-%20Click%20and%20Drag/index-finished-Dashrun.html)
70-
28 | Video Speed Controller | -
70+
28 | [Video Speed Controller指南](https://github.com/soyaine/JavaScript30/blob/master/28%20-%20Video%20Speed%20Controller/README.md) | [Video Speed Controller效果](https://github.com/soyaine/JavaScript30/blob/master/28%20-%20Video%20Speed%20Controller/index-finished-Dashrun.html)
7171
29 | Countdown Timer | -
7272
30 | Whack A Mole | -
7373

@@ -80,7 +80,7 @@ Name | Contribution
8080
[@DrakeXiang](https://github.com/DrakeXiang) | No.[11](https://github.com/soyaine/JavaScript30/tree/master/11%20-%20Custom%20Video%20Player)
8181
[@zzh466](http://github.com/zzh466) | Review
8282
[@Xing Liu](https://github.com/S1ngS1ng) | Review
83-
[@大史快跑Dashrun](https://github.com/dashrun) | No.[16](https://github.com/soyaine/JavaScript30/tree/master/16%20-%20Mouse%20Move%20Shadow).[17](https://github.com/soyaine/JavaScript30/tree/master/17%20-%20Sort%20Without%20Articles).[18](https://github.com/soyaine/JavaScript30/tree/master/18%20-%20AddingUpTimesWithReduce).[19](https://github.com/soyaine/JavaScript30/blob/master/19%20-%20Webcam%20Fun).[20](https://github.com/soyaine/JavaScript30/tree/master/20%20-%20Speech%20Detection).[21](https://github.com/soyaine/JavaScript30/tree/master/21%20-%20Geolocation).[22](https://github.com/soyaine/JavaScript30/tree/master/22%20-%20Follow%20Along%20Link%20Highlighter).[23](https://github.com/soyaine/JavaScript30/tree/master/23%20-%20Speech%20Synthesis).[24](https://github.com/soyaine/JavaScript30/tree/master/24%20-%20Sticky%20Nav).[25](https://github.com/soyaine/JavaScript30/tree/master/25%20-%20Event%20Related).[26](https://github.com/soyaine/JavaScript30/tree/master/26%20-%20Strip%20Follow%20Along%20Nav).[27](https://github.com/soyaine/JavaScript30/tree/master/27%20-%20Click%20and%20Drag)
83+
[@大史快跑Dashrun](https://github.com/dashrun) | No.[16](https://github.com/soyaine/JavaScript30/tree/master/16%20-%20Mouse%20Move%20Shadow).[17](https://github.com/soyaine/JavaScript30/tree/master/17%20-%20Sort%20Without%20Articles).[18](https://github.com/soyaine/JavaScript30/tree/master/18%20-%20AddingUpTimesWithReduce).[19](https://github.com/soyaine/JavaScript30/blob/master/19%20-%20Webcam%20Fun).[20](https://github.com/soyaine/JavaScript30/tree/master/20%20-%20Speech%20Detection).[21](https://github.com/soyaine/JavaScript30/tree/master/21%20-%20Geolocation).[22](https://github.com/soyaine/JavaScript30/tree/master/22%20-%20Follow%20Along%20Link%20Highlighter).[23](https://github.com/soyaine/JavaScript30/tree/master/23%20-%20Speech%20Synthesis).[24](https://github.com/soyaine/JavaScript30/tree/master/24%20-%20Sticky%20Nav).[25](https://github.com/soyaine/JavaScript30/tree/master/25%20-%20Event%20Related).[26](https://github.com/soyaine/JavaScript30/tree/master/26%20-%20Strip%20Follow%20Along%20Nav).[27](https://github.com/soyaine/JavaScript30/tree/master/27%20-%20Click%20and%20Drag).[28](https://github.com/soyaine/JavaScript30/tree/master/28%20-%20Video%20Speed%20Controller)
8484
[@缉熙Soyaine](https://github.com/soyaine) | No.[1](https://github.com/soyaine/JavaScript30/tree/master/01%20-%20JavaScript%20Drum%20Kit).[2](https://github.com/soyaine/JavaScript30/tree/master/02%20-%20JS%20%2B%20CSS%20Clock).[3](https://github.com/soyaine/JavaScript30/tree/master/03%20-%20CSS%20%Variables).[4](https://github.com/soyaine/JavaScript30/tree/master/04%20-%20Array%20Cardio%20Day%201).[5](https://github.com/soyaine/JavaScript30/blob/master/05%20-%20Flex%20Panel%20Gallery).[6](https://github.com/soyaine/JavaScript30/blob/master/06%20-%20Type%20Ahead).[7](https://github.com/soyaine/JavaScript30/tree/master/07%20-%20Array%20Cardio%20Day%202).[8](https://github.com/soyaine/JavaScript30/tree/master/08%20-%20Fun%20with%20HTML5%20Canvas).[9](https://github.com/soyaine/JavaScript30/blob/master/09%20-%20Dev%20Tools%20Domination).[10](https://github.com/soyaine/JavaScript30/blob/master/10%20-%20Hold%20Shift%20and%20Check%20Checkboxes/README.md).[12](https://github.com/soyaine/JavaScript30/tree/master/12%20-%20Key%20Sequence%20Detection/README.md).[13](https://github.com/soyaine/JavaScript30/blob/master/13%20-%20Slide%20in%20on%20Scroll/README.md).[14](https://github.com/soyaine/JavaScript30/tree/master/14%20-%20JavaScript%20References%20VS%20Copying)
8585

8686
## JOIN US

0 commit comments

Comments
 (0)