使用react hooks写一个倒计时功能

先要明确的是,setTimeout函数中执行代码的时间肯定是要大于等于setTimeout时间的,那么就可能出现设定的 1 秒,实际执行却执行了 2 秒的情况,那么我们的实现思路也很简单,每次计算一下setTimeout实际执行的时间,然后动态的调整下一次执行的时间,而不是设置固定的值

第n次执行 executionTime 实际执行时间 nextTime 下次需要执行的时间 totleTime 执行的总时间
0 0 1000 0
1 1200 800 1200
2 1100 700 2300
3 1000 700 3300
4 2200 500 5500
5 1300 200 6800
6 1200 1000 8000

const useCountDown = ({ leftTime, ms = 1000, onEnd }) => {const countdownTimer = useRef();const startTimer = useRef();//记录初始时间const startTimeRef = useRef(performance.now());// 第一次执行的时间处理,让下一次倒计时时调整为整数const nextTimeRef = useRef(leftTime % ms);const [count, setCount] = useState(leftTime);const clearTimer = () => {countdownTimer.current && clearTimeout(countdownTimer.current);startTimer.current && clearTimeout(startTimer.current);};const startCountDown = () => {clearTimer();const currentTime = performance.now();// 算出每次实际执行的时间const executionTime = currentTime - startTimeRef.current;// 实际执行时间大于上一次需要执行的时间,说明执行时间多了,否则需要补上差的时间const diffTime =executionTime > nextTimeRef.current? executionTime - nextTimeRef.current: nextTimeRef.current - executionTime;setCount((count) => {const nextCount =count - (Math.floor(executionTime / ms) || 1) * ms - nt;return nextCount <= 0 ? 0 : nextCount;});// 算出下一次的时间nextTimeRef.current =executionTime > nextTimeRef.current ? ms - diffTime : ms + diffTime;// 重置初始时间startTimeRef.current = performance.now();countdownTimer.current = setTimeout(() => {requestAnimationFrame(startCountDown);}, nextTimeRef.current);};useEffect(() => {setCount(leftTime);startTimer.current = setTimeout(startCountDown, nextTimeRef.current);return () => {clearTimer();};}, [leftTime]);useEffect(() => {if (count <= 0) {clearTimer();onEnd && onEnd();}}, [count]);return count;
};export default useCountDown;

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/7390.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

羊大师分解,羊奶不为人知的健康奇迹

羊大师分解&#xff0c;羊奶不为人知的健康奇迹 羊奶是一种营养丰富的食品&#xff0c;拥有许多不为人知的健康益处。 益智健脑&#xff1a;羊奶中含有较高的钙、蛋白质、氨基酸、维生素、矿物质、无机盐、核酸等营养成分&#xff0c;这些都对大脑发育及增强智力有很大帮助。…

MySQL mydumper工具

目录 1. mydumper介绍 2. mydumper参数解释 3. 备份例子 3.1 备份全库(未包含其他) 3.2 备份全库(包含其他) 3.3 备份指定数据库(-B或--database) 3.4 导出指定表(-T或--tables-list) 3.5 只导出表结构&#xff0c;不导出表数据(-d或--no-data) 3.6 只导出表数据&#…

iOS 横竖屏的正确打开姿势

一、使用场景概述 一种是在present出来的vc中打开横竖屏 固定只有一个方向&#xff08;横屏的方向&#xff09; 可根据重力感应进行横竖屏 某个特定的push出来的vc中打开横竖屏&#xff08;只能根据重力感应横竖屏&#xff0c;不能设置强制的方向&#xff09; 二、具体代码…

包管理工具npm的安装和使用

包管理工具 管理 包 的应用软件&#xff0c;可以对 包 进行下载 安装&#xff0c;更新&#xff0c;删除&#xff0c;上传 等操作。 借助包管理工具&#xff0c;可以快速开发项目&#xff0c;提升开发效率。 包管理工具是一个通用的概念&#xff0c;很多编程语言都有包管理工…

likeshop多商户单商户商城_likeshop跑腿源码_likeshop物品租赁系统开源版怎么配置小程序对接?

本人是商业用户所以能持续得到最新商业版&#xff0c;今天我说下likeshop里面怎么打包小程序&#xff0c;大家得到程序时候会发现它有admin目录 app目录 server目录 这三个目录分别是做什么呢&#xff1f; 1.admin目录 下面都是架构文件使用得是Node.js打包得&#xff0c;至于…

管道通信与Linux命令的执行-(读书笔记-十三)

|前一个命令的输出作为后一个命令的输入。 在Linux中&#xff0c;|符号是一个管道符号&#xff0c;用于将前一个命令的输出作为后一个命令的输入。这种机制允许你将多个命令组合在一起&#xff0c;以执行复杂的操作。下面是一些基本的例子&#xff1a; 查看当前目录下的文件列…

数据互通新纪元,企业如何实现系统无缝对接?

一、客户介绍 某文化发展有限公司&#xff0c;是一家在二次元文化领域深耕的领先企业&#xff0c;自成立以来&#xff0c;始终致力于为广大二次元爱好者提供丰富多样的正版衍生品和独特的文化体验。作为一家专注于二次元周边产品的公司&#xff0c;该公司拥有全面的产品线&…

网站访问免费升级成 HTTPS——值得收藏

实现HTTPS协议可以分为四个主要步骤&#xff0c;以确保网站数据传输的安全性。以下是简明清晰的流程概述&#xff1a; 1. 申请SSL证书 - SSL证书是实现HTTPS的基础&#xff0c;它包含了网站的身份信息以及公钥等。首先&#xff0c;你需要从受信任的证书颁发机构(CA)申请一个SSL…

新建的springBoot WEB项目无法自动返回html模版(gradle+kotlin版本)

最近研究了springBoot创建web项目&#xff0c; 第一步服务端返回字符串没有问题&#xff0c;第二步返回html时&#xff0c;还是返回的字符串。 文章目录 一、参考方案二、新建springBoot web项目三、启动项目的三种方式 一、参考方案 将控制器类的 RestController 改为 Contro…

Listview控件的5种视图

在C#中&#xff0c;ListView控件是用于显示和编辑列表数据的常用控件。它可以显示数据项的列表&#xff0c;并允许用户对列表中的数据进行操作。 ListView控件有五种视图模式&#xff0c;分别是&#xff1a; LargeIcon视图&#xff1a;在此视图中&#xff0c;每个数据项都显示…

如何剪辑视频中不想要的片段?教你轻松剪辑

如何剪辑视频中不想要的片段&#xff1f;在视频编辑的精湛艺术中&#xff0c;精确剪辑掉不想要的片段无疑是提升视频品质和专业水准的关键一环。技术的进步使我们得以借助多种高效、易用的视频剪辑软件&#xff0c;轻松去除冗余&#xff0c;保留精华&#xff0c;从而创作出更加…

大模型模型简化机器人训练;简单易用的 3D 工具Project Neo;特斯拉放出了擎天柱机器人最新训练视频

✨ 1: DrEureka 利用大语言模型自动化将机器人仿真环境训练结果转移到真实世界 DrEureka是一种利用大型语言模型&#xff08;LLMs&#xff09;自动化和加速从仿真&#xff08;sim&#xff09;到现实世界&#xff08;real&#xff09;转移的技术。在机器人技能学习领域&#x…

使用socat 做端口转发 调试设备

使用 socat 监听设备的端口&#xff0c;转发到PC的 一个sniff 程序上&#xff0c;查看wireshark 或者直接用 scapy 进行分析 有了socat 也可以做 nat 映射

MySQL mysqldump备份恢复

目录 1. 备份类型 2. 逻辑备份VS物理备份 3. mysqldump工具 3.1 备份命令格式 3.2 备份选项 3.3 备份全库(结构和数据) 3.4 备份全库(仅结构) 3.5 备份全库(仅数据) 3.6 备份单个数据库(结构和数据) 3.7 备份单个数据库(仅结构) 3.8 备份单个数据库(仅数据) 3.9…

低代码系统能够解决哪些痛点?

不同的应用场景下&#xff0c;低代码系统解决的痛点是不一样的。工业应用场景中的组态软件应该说是最早的低代码系统了。以 Topstack 为代表的Web 组态软件&#xff0c;其核心功能设备数据采集、图形监控画面、数据报表、数据看板、业务逻辑开发等&#xff0c;都是无代码或低代…

个人出租房屋收入需汇算吗?柯桥会计培训

2023年度个人所得税综合所得汇算清缴正在进行&#xff0c;个人出租房屋的收入需并入汇算清缴吗&#xff1f;汇算最后一步显示免申报是什么意思&#xff1f; 1 个人出租房屋的收入需并入汇算清缴吗&#xff1f; 答&#xff1a;不用。根据《国家税务总局关于办理2023年度个人所…

申请SSL证书需要验证哪些内容?

SSL证书是一种数字证书&#xff0c;它用于在线传输加密数据&#xff0c;确保数据的安全性和完整性。在申请SSL证书之前&#xff0c;需要验证一些重要内容&#xff0c;以确保证书的可信度和有效性。本文将介绍申请SSL证书所需进行的验证&#xff0c;并探讨验证的过程和重要性。 …

UaExpert(OPCUA上位机第三方工具)通过OPCUA协议读写PLC 1500数据

一、CPU1500配置参数 1.激活OPC UA服务器 2.选择许可证&#xff08;所需要的许可证类型&#xff09; 3.启用访客认证&#xff08;如果需要上位机输入用户信息访问&#xff0c;则需要添加用户名和密码&#xff09; 4.选择TCP/IP&#xff0c;本地仿真选择local、single adapt…

基于大模型的idea提炼:围绕论文和引用提炼idea之ResearchAgent

前言 对本博客比较熟悉的朋友知道&#xff0c;我司论文项目组正在基于大模型做论文的审稿(含CS英文论文审稿、和金融中文论文审稿)、翻译&#xff0c;且除了审稿翻译之外&#xff0c;我们还将继续做润色/修订、idea提炼(包含论文检索)&#xff0c;是一个大的系统&#xff0c;包…

CVE-2022-32250漏洞原理

CVE-2022-32250漏洞原理 原创 hope 蚁景网安 2024-05-06 20:00 湖南 前言 在nftales中存在着集合(sets)&#xff0c;用于存储唯一值的集合。sets 提供了高效地检查一个元素是否存在于集合中的机制&#xff0c;它可以用于各种网络过滤和转发规则。 而CVE-2022-32250漏洞则是由…