本文详细介绍如何使用JavaScript实现页面数值的动态递增效果。通过HTML5的data-*属性存储目标数值,结合CSS Flexbox布局与媒体查询适配屏幕,利用JavaScript的定时器(setTimeout)和递归调用实现平滑的数字滚动。文章提供完整的HTML、CSS及JS代码,并深入解析核心逻辑,包括类型转换、速率控制及边界判断,帮助开发者快速掌握前端交互技巧。
前言
大家好,今天分享一个有趣的JavaScript小案例,实现数值的动态递增效果。这个效果曾在清华大学官网出现过(现已移除),觉得很有趣,最近在复习JS时重新编写并整理出来,希望能与大家分享这份乐趣。
效果如下:

下面直接展示实现代码:
HTML结构:
<div class="outer">
<div class="counter-container">
<i class="iconfont icon-Basket-Ball" style="font-size:50px"></i>
<div class="counter" data-set="37062"></div>
<span>常规赛总得分</span>
</div>
<div class="counter-container">
<i class="iconfont icon-BasketballHoop" style="font-size:50px"></i>
<div class="counter" data-set="10210"></div>
<span>常规赛总篮板</span>
</div>
<div class="counter-container">
<i class="iconfont icon-assistant" style="font-size:50px"></i>
<div class="counter" data-set="10045"></div>
<span>常规赛总助攻</span>
</div>
</div>
代码解析:
这里构建了一个外层容器,内部包含三个子容器。每个子容器的数据显示使用了
data-*属性(注:data-*用于存储页面或应用程序的私有自定义数据,赋予我们在所有 HTML 元素上嵌入自定义 data 属性的能力,存储的(自定义)数据能够被页面的 JavaScript 中利用,以创建更好的用户体验(不进行 Ajax 调用或服务器端数据库查询))。我们将自定义数据(37062、10210、10045)通过该属性传入,以便在JavaScript中读取。
CSS样式:
* {
box-sizing: border-box;
}
.outer {
background-color: #8e44ad;
color: #fff;
font-family: 'Roboto Mono', sans-serif;
display: flex;
align-items: center;
justify-content: center;
height: 350px;
overflow: hidden;
margin: 0;
}
.counter-container {
display: flex;
flex-direction: column;
justify-content: center;
text-align: center;
margin: 30px 50px;
}
.counter {
font-size: 60px;
margin-top: 10px;
}
@media (max-width: 580px) {
.outer {
flex-direction: column;
}
}
代码解析:
CSS部分相对简单,主要使用了
flex布局来排列元素,并添加了一个媒体查询以适配不同屏幕尺寸,具体细节请查看代码。
JavaScript逻辑:
let counters = document.querySelectorAll('.counter') //获取到三个counter盒子
counters.forEach(item => {
item.innerText = '0' //记录分数变化的变量,初始值为0
const updateData = () => {
const data = +item.getAttribute('data-set') //获取到元素中绑定的数据
const tmp = +item.innerText //临时变量保存变化一次的数据量
const changeData = data / 200 //设置改变的速率
if(tmp < data) { //如果临时变量的值小于最终数据的值,那么就给元素进行数据相加
item.innerText = `${Math.ceil(tmp + changeData)}` //值数相加,然后进行取整
setTimeout(updateData,1) //定时器传入回调函数目的在于动态变化
} else {
item.innerText = data //不满足条件后,证明得到了最终数据,直接渲染
}
}
updateData() //调用函数,启动函数
})
代码解析:
数据动态变化的核心逻辑如下:
- 首先获取存储数据的三个div元素,通过forEach方法遍历这些元素。由于初始分数为0,我们将每个盒子的innerText设置为字符串'0'(注意:这里初始值为字符串类型)。
- 接着定义一个更新数据的方法updateData,获取之前绑定的自定义数据。这里可能有人对+item.getAttribute('data-set')感到疑惑,前面的+号代表将后续内容转换为正数,即告诉编译器即将赋值的数值类型为数字类型,避免将其作为字符串进行拼接。
- 然后定义一个临时变量tmp,用于保存item.innerText中变化后的数值。接下来设置数据变化的速率,这里通过除以200来实现。除数越大,变化速率越慢;反之则越快。
- 随后进行判断(比较临时量与总量):如果临时量小于总量,就让临时量tmp与数据变化量changeData相加并取整;如果不满足判断条件,直接渲染数据即可(此时数据已是最终数据,即我们的自定义数据)。
- 实现数据动态变化的核心在于定时器。在满足判断条件的代码块中启动定时器,传入回调函数updateData,实现每1ms调用一次,使数据变化看起来非常流畅。
写在最后:
JavaScript的实现逻辑应一步步来,会发现逻辑很清晰。希望大家在写JS代码时,也能一步步下手,否则很容易导致逻辑混乱。未来会不定期分享一些js小案例,一起探索有趣的前端效果,在娱乐的同时提升JS开发能力!
到此这篇关于JavaScript实现数值动态变化效果的文章就介绍到这了,更多相关JS实现数值动态变化内容请搜索本站以前的文章或继续浏览下面的相关文章,希望大家以后多多支持本站!