You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在HTML中实现数字滚动跳动(Tick Up)动画效果

实现数字滚动跳动(Tick Up)计数器效果

我想实现数字变化时的「滚动跳动(Tick Up)」效果,类似Twitter的点赞/转发/评论计数器以及Discord的反应计数器。原代码存在问题:新数字会显示在原数字旁边,向上滚动后只保留新数字向下回到原位,我想要的效果是新数字位于旧数字下方,动画结束后直接恢复到初始位置。

原代码问题分析

原JS代码里的_x.innerHTML += _x.innerHTML + "<br>" + num是核心错误——这会把当前计数器的内容重复一遍,再追加新数字,导致旧数字、重复的旧数字、新数字挤在一起,完全不符合“旧数字在上,新数字在下”的预期结构。

修正后的完整代码

HTML

<span id="counter" class="counter">0</span>
<button onclick="changeCounter('counter', Math.floor(Math.random()*100))">切换数字</button>

CSS

.counter {
    display: inline-block;
    height: 15px;
    font-size: 15px;
    line-height: 15px; /* 保证文字垂直居中,每行高度和容器一致 */
    overflow-y: hidden;
    transition: margin-top 0.2s ease; /* 把过渡效果写在CSS里,简化JS逻辑 */
}

JavaScript

function changeCounter(id, num) {
    const counter = document.getElementById(id);
    const oldValue = counter.textContent; // 用textContent获取纯文本,避免HTML干扰
    
    // 构建旧值在上、新值在下的结构
    counter.innerHTML = `${oldValue}<br>${num}`;
    
    // 等待DOM更新后触发滚动动画(16ms约为一帧时间)
    setTimeout(() => {
        counter.style.marginTop = "-15px";
    }, 16);
    
    // 动画结束后重置状态,为下一次动画做准备
    setTimeout(() => {
        counter.textContent = num;
        counter.style.marginTop = "0";
    }, 220); // 0.2s动画时长 + 16ms延迟,确保动画完全结束后再重置
}

关键修改说明

  • 结构修正:不再重复旧内容,直接用<br>分隔旧值和新值,形成标准的上下两行布局,新数字自然处于旧数字下方。
  • CSS优化:添加line-height消除滚动时的文字偏移,把过渡效果固化在CSS中,不用每次通过JS动态设置。
  • JS逻辑调整:
    • 用textContent读取旧值,避免HTML元素干扰;
    • 延迟16ms触发滚动,确保浏览器完成上下结构渲染后再执行动画;
    • 动画结束后直接重置为新数字并归位margin-top,保证下一次动画的初始状态正确。

内容的提问来源于stack exchange,提问作者wutadam

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.08 03:45:33