纯js实现倒计时功能

发布时间 - 2026-01-10 22:21:07    点击率:

通过js实现页面的倒计时功能。

思路: 传入一个秒数c,c/60可以得到分钟m, c%60可以得到显示的秒数s,同理,再将m/60可是得到小时数, m/%可以得到分钟数。通过setInterval每次将总秒数-1,并将计算所得时间显示到页面上。

第一版的肮脏代码如下, 可以作为反面教材思考一下

<html> 
  <head> 
    <title>Tomato</title> 
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 
    <script type="text/javascript"> 
      var vTimeLength = 5; 
      var vHour; 
      var vMinutes; 
      var vSeconds; 
      var vRemainingTime; 
      function countDown(){ 
        vTimeLength = vTimeLength - 1; 
        vMinutes = Math.floor(vTimeLength/60); 
        vSeconds = Math.floor(vTimeLength%60); 
        if (vMinutes >= 60){ 
          vHour = Math.floor(vMinutes/60); 
          var vMinutesNew = Math.floor(vMinutes%60); 
          vRemainingTime = vHour + ":" + vMinutesNew + ":" + vSeconds; 
        } else { 
          vRemainingTime = vMinutes + ":" + vSeconds; 
        } 
        document.getElementById("div_countDown").innerHTML = vRemainingTime; 
        if (vTimeLength < 1) { 
          alert('do sth'); 
        } 
      } 
    </script> 
  </head> 
  <body> 
    <div id="div_countDown"></div> 
    <script type="text/javascript"> 
      setInterval("countDown()", 1000); 
    </script> 
  </body> 
</html> 

缺陷:

 1、定义了众多的全局变量,

 2、没有复用性,

 3、setInterval容易导致队列过多, 结束事件如果是非阻塞事件, 倒计时会继续执行出现负数,

 4、不符合面向对象思想。。。

针对缺陷1的解决方案是, 定义一个函数, 将相关全局变量放到函数内部,使之成为局部变量

针对缺陷2:为函数指定参数,提高复用性。 这里定义了3个参数vTimeLength为倒计时总秒数,showTagId为显示到页面元素的id, callback为倒计时结束后的回掉方法

针对缺陷3:用setTimeout替代setInterval

优化后的代码如下:

<html> 
  <head> 
    <title>countdown</title> 
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 
    <script type="text/javascript"> 
      function countDown(vTimeLength, showTagId, callback) { 
        var vHour; 
        var vMinutes; 
        var vMinutesNew 
        var vSeconds; 
        var vRemainingTime; 
        function countDownInner(vTimeLength){ 
          vMinutes = Math.floor(vTimeLength/60); 
          vSeconds = Math.floor(vTimeLength%60); 
          if (vMinutes >= 60){ 
            vHour = Math.floor(vMinutes/60); 
            vMinutesNew = Math.floor(vMinutes%60); 
            vRemainingTime = vHour + ":" + vMinutesNew + ":" + vSeconds; 
          } else { 
            vRemainingTime = vMinutes + ":" + vSeconds; 
          } 
          document.getElementById(showTagId).innerHTML = vRemainingTime; 
          vTimeLength = vTimeLength - 1; 
          if (vTimeLength > 0) { 
            setTimeout(function(){countDownInner(vTimeLength);}, 1000); 
          } else { 
            callback(); 
          } 
        } 
        countDownInner(vTimeLength); 
      } 
    </script> 
  </head> 
  <body> 
    <div id="div_countDown"></div> 
    <script type="text/javascript"> 
      countDown(5, "div_countDown", function(){alert('do sth');}); 
    </script> 
  </body> 
</html> 

这里有一点需要注意

setTimeout(function(){countDownInner(vTimeLength);}, 1000); 

第一次我将此句写成了

setTimeout(countDownInner(vTimeLength), 1000); 

结果函数直接执行了, 没有等待1秒的时间。如果没有入参, 即setTimeout("countDownInner()", 1000); 则可正常执行。

至于前面提到的不够面向对象的缺陷, 也是刚刚接触, 这里贴出代码,希望能够互相交流

<html> 
  <head> 
    <title>count_down</title> 
    <script type="text/javascript"> 
    var countDown = { 
      flag: true,  
      hour: 0, 
      minutes: 0, 
      minutesNew: 0, 
      seconds: 0, 
      show: 0, 
      current: 0, 
      length: 0, 
      showTagId: null, 
      // callback: null, 
      countDownInner: function(vTimeLength){ 
        if (!this.flag) { 
          return; 
        } 
        var that=this; 
        this.current = vTimeLength; 
        minutes = Math.floor(vTimeLength/60); 
        seconds = Math.floor(vTimeLength%60); 
        if (minutes >= 60){ 
          hour = Math.floor(minutes/60); 
          minutesNew = Math.floor(minutes%60); 
          show = hour + ":" + minutesNew + ":" + seconds; 
        } else { 
          show = minutes + ":" + seconds; 
        } 
        document.getElementById(this.showTagId).innerHTML = show; 
        vTimeLength = vTimeLength - 1; 
        if (vTimeLength > 0) { 
          setTimeout(function(){that.countDownInner(vTimeLength);}, 1000); 
        } else { 
          setTimeout(function(){that.callback();}, 1000); 
        } 
      }, 
      run: function(vTimeLength, showTagId, callback) { 
        if (!this.flag) { 
          this.flag = true; 
          this.countDownInner(this.current); 
        } else if (showTagId) { 
          this.length = vTimeLength; 
          this.showTagId = showTagId; 
          this.callback = callback; 
          this.countDownInner(vTimeLength);   
        } 
      }, 
      stop: function(){ 
        this.flag = false; 
      },  
      restart: function(){ 
        this.flag = true; 
        this.countDownInner(this.length); 
      } 
    }; 
    function countDownStart() { 
      countDown.run(); 
    } 
    function countDownStop() { 
      countDown.stop(); 
    } 
    </script> 
  </head> 
  <body> 
    <div id="div_countDown"></div> 
    <script type="text/javascript"> 
      countDown.run(5, 'div_countDown',function(){alert('12')}); 
    </script> 
    <span> 
      <button onclick="countDownStart();">start</button> 
      <button onclick="countDownStop();">stop</button> 
    </span> 
  </body> 
</html> 

一个难点是this的使用, 在函数内部, this是调用当前函数范围,所以setTimeout(function(){this.countDownInner(vTimeLength);}, 1000);会出现undefined。

解决方案是定义一个that变量接收外部函数的this指针,然后通过that即可调用外部域。

以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,同时也希望多多支持!


# js  # 倒计时  # 纯jsp实现的倒计时动态显示效果完整代码  # JS实现倒计时(天数、时、分、秒)  # PHP+JS实现的商品秒杀倒计时用法示例  # js制作支付倒计时页面  # JavaScript实现刷新不重记的倒计时  # js实现精确到毫秒的倒计时效果  # javascript特效实现——当前时间和倒计时效果的简单实例  # JS/jQ实现免费获取手机验证码倒计时效果  # 点击按钮出现60秒倒计时的简单js代码(推荐)  # js代码实现点击按钮出现60秒倒计时  # 可以得到  # 面向对象  # 复用  # 全局变量  # 并将  # 如果没有  # 不符合  # 将此  # 使之  # 则可  # 再将  # 贴出  # 需要注意  # 容易导致  # 写成了  # 结束后  # 一个函数  # floor  # countDown 


相关栏目: 【 网站优化151355 】 【 网络推广146373 】 【 网络技术251813 】 【 AI营销90571


相关推荐: 如何制作新型网站程序文件,新型止水鱼鳞网要拆除吗?  laravel怎么使用数据库工厂(Factory)生成带有关联模型的数据_laravel Factory生成关联数据方法  简单实现jsp分页  大连网站制作公司哪家好一点,大连买房网站哪个好?  python中快速进行多个字符替换的方法小结  网站制作报价单模板图片,小松挖机官方网站报价?  想要更高端的建设网站,这些原则一定要坚持!  如何在IIS服务器上快速部署高效网站?  如何在HTML表单中获取用户输入并结合JavaScript动态控制复利计算循环  活动邀请函制作网站有哪些,活动邀请函文案?  Android okhttputils现在进度显示实例代码  如何自定义建站之星模板颜色并下载新样式?  如何在自有机房高效搭建专业网站?  免费的流程图制作网站有哪些,2025年教师初级职称申报网上流程?  Laravel模型关联查询教程_Laravel Eloquent一对多关联写法  高性能网站服务器配置指南:安全稳定与高效建站核心方案  如何在IIS7上新建站点并设置安全权限?  Laravel请求验证怎么写_Laravel Validator自定义表单验证规则教程  成都网站制作公司哪家好,四川省职工服务网是做什么用?  Laravel怎么做数据加密_Laravel内置Crypt门面的加密与解密功能  佛山网站制作系统,佛山企业变更地址网上办理步骤?  Laravel集合Collection怎么用_Laravel集合常用函数详解  晋江文学城电脑版官网 晋江文学城网页版直接进入  高端企业智能建站程序:SEO优化与响应式模板定制开发  如何快速重置建站主机并恢复默认配置?  如何用AI一键生成爆款短视频文案?小红书AI文案写作指令【教程】  ai格式如何转html_将AI设计稿转换为HTML页面流程【页面】  Laravel如何实现邮箱地址验证功能_Laravel邮件验证流程与配置  Win11应用商店下载慢怎么办 Win11更改DNS提速下载【修复】  Laravel怎么在Controller之外的地方验证数据  如何在服务器上三步完成建站并提升流量?  如何在云主机上快速搭建网站?  零基础网站服务器架设实战:轻量应用与域名解析配置指南  Laravel如何处理文件下载请求?(Response示例)  Laravel如何记录自定义日志?(Log频道配置)  Python进程池调度策略_任务分发说明【指导】  ChatGPT常用指令模板大全 新手快速上手的万能Prompt合集  免费视频制作网站,更新又快又好的免费电影网站?  网站制作价目表怎么做,珍爱网婚介费用多少?  Google浏览器为什么这么卡 Google浏览器提速优化设置步骤【方法】  Laravel的契約(Contracts)是什么_深入理解Laravel Contracts与依赖倒置  高性价比服务器租赁——企业级配置与24小时运维服务  香港服务器租用费用高吗?如何避免常见误区?  Laravel如何配置中间件Middleware_Laravel自定义中间件拦截请求与权限校验【步骤】  Laravel Pest测试框架怎么用_从PHPUnit转向Pest的Laravel测试教程  Laravel storage目录权限问题_Laravel文件写入权限设置  Laravel如何实现本地化和多语言支持_Laravel多语言配置与翻译文件管理  Win11搜索栏无法输入_解决Win11开始菜单搜索没反应问题【技巧】  如何撰写建站申请书?关键要点有哪些?  公司门户网站制作流程,华为官网怎么做?