我无法在 javascript 中重复某个功能
I can't repeat a function in javascript
我正在尝试编写一个简单的 tabata 计时器。直到现在它仍然有效,但是当我尝试根据存储在变量中的值重复计数更多次时出现问题。
所以,假设我们从 10 开始到 0,我们想重复这个计数两次。会说:当我按下按钮时,在开始计数之前,程序将检查带有次数的变量是否为 NaN 或者其中是否包含数字。如果是 NaN 因为我不想重复,它就开始从 10 倒计时到 0 然后停止。好的,这部分有效。但是如果我说我想重复倒计时两次呢?我将我想要重复的次数放入名为 "var times" 的变量中,比方说 2,然后我将使用 for 循环,例如:
for(var i=0; i<times; i++){}
但是当我开始倒计时时,它没有重复两次,而是跳过了许多数字作为时间变量值。这是为什么?
提前致谢
这是我的代码。
var times = 2;
var counter = 0;
var operation;
document.getElementById("timer").textContent = 10;
function calculate(){
counter = document.getElementById("timer").textContent
operation = setInterval(function(){
if(counter >= 1 && counter <= 10){
counter -- ;
document.getElementById("timer").textContent = counter;
}
else if(counter == 0){
clearInterval(operation);
document.getElementById("timer").textContent = 10;
}
},1000);
}
document.getElementById("btn").addEventListener("click", function(){
for(var i=0; i<times; i++){
calculate();
}
})
.btn{
position: absolute;
width: 100%;
top: 20%;
margin:auto;
text-align: center;
}
.timer{
position: absolute;
width: 100%;
top:30%;
margin:auto;
text-align: center;
font-size: 10rem;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<link rel="stylesheet" href="style.css">
<title>Document</title>
</head>
<body>
<div class="container">
<div class="btn">
<button id="btn">
<h1>Click me</h1>
</button>
</div>
<div class="timer">
<p id="timer"></p>
</div>
</div>
<script src="main.js"></script>
</body>
</html>
首先不确定你的逻辑是否有效。我只是在没有测试的情况下查看代码,似乎 calculate()
> operation = setInterval(function(){...
正在调用回调函数,它将异步执行。
如果调用calculate()
两次,只会同时触发两次异步方法,不按顺序。
意思是你里面的逻辑calculate()
同时执行了两次,不是按顺序执行的。
你可以像calculate(times)
一样把times
变量传入函数中,然后在里面执行循环,见下例
function calculate(times){
counter = document.getElementById("timer").textContent
operation = setInterval(function(){
/////////////////////////////
// do the times loop here
/////////////////////////////
for(let i=0; i < times; i++){
if(counter >= 1 && counter <= 10){
counter -- ;
document.getElementById("timer").textContent = counter;
} else if(counter == 0) {
clearInterval(operation);
document.getElementById("timer").textContent = 10;
}
}
},1000);
}
document.getElementById("btn").addEventListener("click", function(){
calculate(times);
})
我明白了,问题是当你执行 for 循环时,它调用了两倍的 setinterval,所以对于这种情况,你必须做的是使用递归,这是这种情况的工作代码 - >
var times = 2;
var counter = 0;
var operation;
document.getElementById("timer").textContent = 10;
function calculate(){
counter = document.getElementById("timer").textContent
operation = setInterval(function(){
if(counter >= 1 && counter <= 10){
counter -- ;
document.getElementById("timer").textContent = counter;
}
else if(counter == 0){
times--
console.log(times)
if(times > 0){
document.getElementById("timer").textContent = 10;
clearInterval(operation);
calculate()
}else if(times == 0){
clearInterval(operation);
document.getElementById("timer").textContent = 10;
}
}
},1000);
}
.btn{
z-index: 9999;
position: absolute;
width: 100%;
top: 20%;
margin:auto;
text-align: center;
}
.timer{
position: absolute;
width: 100%;
top:30%;
margin:auto;
text-align: center;
font-size: 10rem;
}
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<link rel="stylesheet" href="style.css">
<title>Document</title>
</head>
<body>
<div class="container">
<div class="btn">
<button onClick="calculate()" id="btn">
<h1>Click me</h1>
</button>
</div>
<div class="timer">
<p id="timer"></p>
</div>
</div>
</body>
</html>
我正在尝试编写一个简单的 tabata 计时器。直到现在它仍然有效,但是当我尝试根据存储在变量中的值重复计数更多次时出现问题。 所以,假设我们从 10 开始到 0,我们想重复这个计数两次。会说:当我按下按钮时,在开始计数之前,程序将检查带有次数的变量是否为 NaN 或者其中是否包含数字。如果是 NaN 因为我不想重复,它就开始从 10 倒计时到 0 然后停止。好的,这部分有效。但是如果我说我想重复倒计时两次呢?我将我想要重复的次数放入名为 "var times" 的变量中,比方说 2,然后我将使用 for 循环,例如:
for(var i=0; i<times; i++){}
但是当我开始倒计时时,它没有重复两次,而是跳过了许多数字作为时间变量值。这是为什么?
提前致谢
这是我的代码。
var times = 2;
var counter = 0;
var operation;
document.getElementById("timer").textContent = 10;
function calculate(){
counter = document.getElementById("timer").textContent
operation = setInterval(function(){
if(counter >= 1 && counter <= 10){
counter -- ;
document.getElementById("timer").textContent = counter;
}
else if(counter == 0){
clearInterval(operation);
document.getElementById("timer").textContent = 10;
}
},1000);
}
document.getElementById("btn").addEventListener("click", function(){
for(var i=0; i<times; i++){
calculate();
}
})
.btn{
position: absolute;
width: 100%;
top: 20%;
margin:auto;
text-align: center;
}
.timer{
position: absolute;
width: 100%;
top:30%;
margin:auto;
text-align: center;
font-size: 10rem;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<link rel="stylesheet" href="style.css">
<title>Document</title>
</head>
<body>
<div class="container">
<div class="btn">
<button id="btn">
<h1>Click me</h1>
</button>
</div>
<div class="timer">
<p id="timer"></p>
</div>
</div>
<script src="main.js"></script>
</body>
</html>
首先不确定你的逻辑是否有效。我只是在没有测试的情况下查看代码,似乎 calculate()
> operation = setInterval(function(){...
正在调用回调函数,它将异步执行。
如果调用calculate()
两次,只会同时触发两次异步方法,不按顺序。
意思是你里面的逻辑calculate()
同时执行了两次,不是按顺序执行的。
你可以像calculate(times)
一样把times
变量传入函数中,然后在里面执行循环,见下例
function calculate(times){
counter = document.getElementById("timer").textContent
operation = setInterval(function(){
/////////////////////////////
// do the times loop here
/////////////////////////////
for(let i=0; i < times; i++){
if(counter >= 1 && counter <= 10){
counter -- ;
document.getElementById("timer").textContent = counter;
} else if(counter == 0) {
clearInterval(operation);
document.getElementById("timer").textContent = 10;
}
}
},1000);
}
document.getElementById("btn").addEventListener("click", function(){
calculate(times);
})
我明白了,问题是当你执行 for 循环时,它调用了两倍的 setinterval,所以对于这种情况,你必须做的是使用递归,这是这种情况的工作代码 - >
var times = 2;
var counter = 0;
var operation;
document.getElementById("timer").textContent = 10;
function calculate(){
counter = document.getElementById("timer").textContent
operation = setInterval(function(){
if(counter >= 1 && counter <= 10){
counter -- ;
document.getElementById("timer").textContent = counter;
}
else if(counter == 0){
times--
console.log(times)
if(times > 0){
document.getElementById("timer").textContent = 10;
clearInterval(operation);
calculate()
}else if(times == 0){
clearInterval(operation);
document.getElementById("timer").textContent = 10;
}
}
},1000);
}
.btn{
z-index: 9999;
position: absolute;
width: 100%;
top: 20%;
margin:auto;
text-align: center;
}
.timer{
position: absolute;
width: 100%;
top:30%;
margin:auto;
text-align: center;
font-size: 10rem;
}
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<link rel="stylesheet" href="style.css">
<title>Document</title>
</head>
<body>
<div class="container">
<div class="btn">
<button onClick="calculate()" id="btn">
<h1>Click me</h1>
</button>
</div>
<div class="timer">
<p id="timer"></p>
</div>
</div>
</body>
</html>