I have created this stopwatch and it runs pretty well. The only problem that I am having is that whenever I click my "stop" button, the time stops on the screen but it is still running in the background.
Is there any way to stop this from happening? I want the timer to stop on its current time, then when I click "start", it resumes from the time it was stopped on.
Im thinking maybe create a "new Date()" variable before the update function and another "new Date()" variable inside of the update function and somehow subtract those to get the current date. But I cannot figure that out either.
start = document.getElementById('Start');
stop = document.getElementById('Stop');
let watchRunning = false;
Start.addEventListener('click', startHandler);
Stop.addEventListener('click', stopHandler);
function startHandler() {
if (!watchRunning) {
watchRunning = setInterval(update, 70);
}
}
function stopHandler() {
clearInterval(watchRunning);
watchRunning = null;
}
update();
var seconds;
var milliseconds;
var d;
function update() {
d = new Date();
seconds = d.getSeconds();
milliseconds = Math.floor((d.getMilliseconds() / 10));
if (milliseconds < 10 && seconds < 10) {
document.getElementById("Time").innerHTML =
"0" + seconds + ".0" + milliseconds;
} else if (milliseconds < 10 && seconds >= 10) {
document.getElementById("Time").innerHTML =
seconds + ".0" + milliseconds;
} else if (milliseconds >= 0 && seconds < 10) {
document.getElementById("Time").innerHTML =
"0" + seconds + "." + milliseconds;
} else if (milliseconds >= 0 && seconds >= 10) {
document.getElementById("Time").innerHTML =
seconds + "." + milliseconds;
}
}
#Time {
background-color: yellow;
max-width: 2.3%;
}
<h1>Stop Watch</h1>
<button id="Start">Start</button>
<button id="Stop">Stop</button>
<h3>Elapsed Time:</h3>
<p id="Time"></p>
Try running the snippet and you will see what I mean. The time doesn't stop "running" after I click stop, and when I click start it resumes as if it was never stopped.
clearTimeout( return ID of setTimeout() );
clearTime variable is returned as a value by the setTimeout( ) timing method, which can be pass to the clearTimeout( ID ) as an ID to reference it - clearTimeout( clearTime );
How It Works
Whenever the clearTimeout( ) timing method is called on a setTimeout( ) timing method that is active, the clearTimeout( ) timing method will stop the execution of the setTimeout( ) timing method but without destroying its execution entirely.
The setTimeout( ) timing method is left idle during the period that the clearTimeout( ) timing method is called, and when you re-execute the setTimeout( ) timing method, it will start from the point its execution was stopped, not starting all over from the beginning.
You're good to go!
You should use a setInterval to run your code to update the stopwatch instead of relying on a Date; you can not stop the Date from changing, so even though you stopped updating your stopwatch, the seconds are still ticking by which makes it seem like your stopwatch never stopped.
#Time {
background-color: yellow;
max-width: 2.3%;
}
<h1>Stop Watch</h1>
<button id="Start">Start</button>
<button id="Stop">Stop</button>
<h3>Elapsed Time:</h3>
<p id="Time">00:00</p>
<script>
var start = document.getElementById('Start'), stop = document.getElementById('Stop'), time = document.getElementById('Time');
function StopWatch(props){
this.seconds = props.seconds||0;
this.milliseconds = props.milliseconds||0;
this.updateCallback = props.updateCallback;
this._running = false;
}
StopWatch.prototype = {
start: function(){
var _this = this;
if(!_this._running){
_this._running = true;
_this._intervalID = window.setInterval(function(){
if(++_this.milliseconds==100){
_this.seconds++;
_this.milliseconds = 0;
}
if(_this.updateCallback){
_this.updateCallback(_this.milliseconds, _this.seconds);
}
}, 10);
}
},
stop: function(){
window.clearInterval(this._intervalID);
this._running = false;
},
getTimeString: function(){
var ms = this.milliseconds, s = this.seconds;
if(ms<10){
ms = "0"+ms;
}
if(s<10){
s = "0"+s;
}
return s + ":" + ms;
}
}
var sw = new StopWatch({updateCallback: function(){
time.textContent = sw.getTimeString();
}});
start.addEventListener('click', function(){
sw.start();
});
stop.addEventListener('click', function(){
sw.stop();
});
</script>
Related
I'm quite new to javascript so the answer is probably quite easy but anyways
I'm trying to make a simple click speed test but i cant get the timer to start when the user presses the click me button, so i resorted to just starting it automatically. if anyone can help me to start it on the button press it will be much appreciated
HTML code:
<button id="click2" onclick="click2()">Click Me!</button><br>
<span id="clicksamount">0 Clicks</span><br><br>
<span id="10stimer">10s</span>
JS code:
var click = document.getElementById("click2");
var amount = 0;
var seconds = 10;
var endOfTimer = setInterval(click2, 1000);
function click2() {
seconds--;
document.getElementById("10stimer").innerHTML = seconds + "s";
if (seconds <= 0) {
var cps = Number(amount) / 10;
document.getElementById("clicksamount").innerHTML = "You got " + cps + " CPS!";
document.getElementById("click2").disabled = true;
document.getElementById("10stimer").innerHTML = "Ended";
clearInterval(seconds);
}
}
document.getElementById("click2").onclick = function() {
amount++;
document.getElementById("clicksamount").innerHTML = amount + " Clicks";
}
It looks like you're overwriting your onclick function on the button with id click2 with the lowest 4 lines.
Also, you call clearInterval() with the seconds variable instead of the actual interval, which is referenced by endOfTimer.
I'd suggest to have a separated timer management in a function which you call only on the first click of your button.
See JSFiddle
<button id="clickbutton" onclick="buttonClick()">Click Me!</button><br>
<span id="clicksamount">0 Clicks</span><br><br>
<span id="secondcount">10s</span>
// We will have timerStarted to see if the timer was started once,
// regardless if it's still running or has already ended. Otherwise
// we would directly restart the timer with another click after the
// previous timer has ended.
// timerRunning only indicates wether the timer is currently running or not.
var timerStarted = false;
var timerRunning = false;
var seconds = 10;
var clickAmount = 0;
var timer;
function buttonClick() {
if (!timerStarted) {
startTimer();
}
// Only count up while the timer is running.
// The button is being disabled at the end, therefore this logic is only nice-to-have.
if (timerRunning) {
clickAmount++;
document.getElementById("clicksamount").innerHTML = clickAmount + " Clicks";
}
}
function startTimer() {
timerStarted = true;
timerRunning = true;
timer = setInterval(timerTick,1000);
}
function timerTick() {
seconds--;
document.getElementById("secondcount").innerHTML = seconds + "s";
if (seconds <= 0) {
timerRunning = false;
clearInterval(timer);
var cps = Number(clickAmount) / 10;
document.getElementById("clickbutton").disabled = true;
document.getElementById("clicksamount").innerHTML = "You got " + cps + " CPS (" + clickAmount + "clicks in total)!";
}
}
I made some changes to your code. Effectively, when the user clicks the first time, you start the timer then. The timer variables is null until the first the user clicks.
var click = document.getElementById("click2");
var noOfClicks = 0;
var seconds = 10;
var timer = null;
function doTick(){
seconds--;
if(seconds<=0){
seconds = 10;
clearInterval(timer);
document.getElementById("10stimer").innerHTML= "Ended"
timer=null;
document.getElementById("click2").disabled = true;
}
updateDisplay()
}
function updateClicks(){
if(!timer){
timer=setInterval(doTick, 1000);
clicks= 0;
seconds = 10;
}
noOfClicks++;
updateDisplay();
}
function updateDisplay(){
var cps = Number(noOfClicks) / 10;
document.getElementById("clicksamount").innerHTML = "You got " + cps + " CPS!";
document.getElementById("10stimer").innerHTML =seconds;
}
click.addEventListener('click', updateClicks)
https://jsbin.com/bibuzadasu/1/edit?html,js,console,output
function timer(startEvent, stopEvent) {
let time = 0;
startEvent.target.addEventListener(startEvent.type, () => {
this.interval = setInterval(()=>{
time++;
}, 10); // every 10 ms... aka 0.01s
removeEventListener(startEvent.type, startEvent.target); // remove the listener once we're done with it.
stopEvent.target.addEventListener(startEvent.type, () => {
clearInterval(this.interval); // stop the timer
// your output function here, example:
alert(time);
removeEventListener(stopEvent.type, stopEvent.target); // remove the listener once we're done with it.
});
});
}
Use event listeners rather than onclicks
usage example:
HTML
<button id="mybutton">Click me!</button>
JS
/* ABOVE CODE ... */
let mybutton = document.getElementById("mybutton");
timer(
{target: mybutton, type: "click"},
{target: mybutton, type: "click"}
);
function timer(startEvent, stopEvent) {
let time = 0;
startEvent.target.addEventListener(startEvent.type, () => {
this.interval = setInterval(()=>{
time++;
}, 10); // every 10 ms... aka 0.01s
removeEventListener(startEvent.type, startEvent.target); // remove the listener once we're done with it.
stopEvent.target.addEventListener(startEvent.type, () => {
clearInterval(this.interval); // stop the timer
// your output function here, example:
alert(time);
removeEventListener(stopEvent.type, stopEvent.target); // remove the listener once we're done with it.
});
});
}
let mybutton = document.getElementById("mybutton");
timer(
{target: mybutton, type: "click"},
{target: mybutton, type: "click"}
);
<button id="mybutton">Click me!</button>
//state initialization
var amount = 0;
var seconds = 10;
var timedOut=false;
var timerId=-1;
//counters display
var clicksDisplay= document.getElementById("clicksamount");
var timerDisplay= document.getElementById("10stimer");
function click2(e){
//first click
if(timerId===-1){
//start timer
timed();
}
//still in time to count clicks
if(!timedOut){
amount++;
clicksDisplay.innerText=amount +" Clicks";
}
}
function timed(){
//refresh timer dispaly
timerDisplay.innerText=seconds+"s";
seconds--;
if(seconds<0){
//stop click count
timedOut=true;
}else{
//new timerId
timerId=setTimeout(timed,1000);
}
}
I have a button its disabled and i want to put a counter inside it, what i want to do is when the counter reaches zero it get enabled, how can i do that? in the code below the counter doesn't appear inside the button and i don't want the reset button i just want the button to be enabled when it reaches zero, here is what i have tried so far:
function Countdown()
{
this.start_time = "00:30";
this.target_id = "#timer";
this.name = "timer";
this.reset_btn = "#reset";
}
Countdown.prototype.init = function()
{
this.reset();
setInterval(this.name + '.tick()',1000)
}
Countdown.prototype.reset = function()
{
$(this.reset_btn).hide();
time = this.start_time.split(":");
//this.minutes = parseInt(time[0]);
this.seconds = parseInt(time[1]);
this.update_target();
}
Countdown.prototype.tick = function()
{
if(this.seconds > 0) //|| this.minutes > 0)
{
if(this.seconds == 0)
{
// this.minutes = this.minutes - 1;
this.seconds = 59
} else {
this.seconds = this.seconds - 1;
}
}
this.update_target()
}
Countdown.prototype.update_target = function()
{
seconds = this.seconds;
if (seconds == 0) $(this.reset_btn).show();
else if(seconds < 10) seconds = "0" + seconds;
$(this.target_id).val(this.seconds)
}
timer = new Countdown();
timer.init();
$(document).ready(function(){
$("#reset").click(function(){
//timer = new Countdown();
timer.reset();
});
});
.hidden {
display: none;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<button type="text" id="timer" disabled>Counter should be inside me, and enable me when it reaches 0</button>
<button id="reset">Reset</button>
This is much simpler than what you've got. Just use window.setTimeout().
Keep in mind that tracking time to a high precision is not super reliable in a browser. You may want to look at moment.js or use performance.now() for an easier API to handle that.
// Get refreence to span and button
var spn = document.getElementById("count");
var btn = document.getElementById("btnCounter");
var count = 5; // Set count
var timer = null; // For referencing the timer
(function countDown(){
// Display counter and start counting down
spn.textContent = count;
// Run the function again every second if the count is not zero
if(count !== 0){
timer = setTimeout(countDown, 1000);
count--; // decrease the timer
} else {
// Enable the button
btn.removeAttribute("disabled");
}
}());
<button id="btnCounter" disabled>Time left: <span id="count"></span></button>
var secondsP = document.getElementById('seconds');
var btn1 = document.getElementById("btnSurrender");
var clock = null;
btn1.addEventListener("click", surrender);
function timer () {
clearInterval(clock);
var start = new Date().getTime();
clock = setInterval(function() {
var seconds = Math.round(15 - (new Date().getTime() - start) / 1000);
if (seconds >= 0) {
secondsP.textContent = seconds;
} else {
clearInterval(clock);
}
if (seconds === 0) {
}
}, 1000);
}
function surrender(){
clearInterval(clock);
secondsP.textContent = 0;
setTimeout(timer,2000);
}
timer();
setInterval(timer, 17000);
<html>
<head>
<style>
</style>
<script src="/scripts/snippet-javascript-console.min.js?v=1"></script>
</head>
<body>
<p id="seconds">15</p>
<button id= "btnSurrender">end now</button>
</body>
</html>
I need help with my little problem. I made a stopwatch which counts down 15 seconds. After this 15 seconds, it waits two seconds and starts again. You have option to stop counting when you want to, using "end now" button (then it'll start again after 2 sec). Now, my question is: how can I make a function which is going to stop whole counting after 3/4 rounds?
You restart the clock in surrender() using the call setTimeout(timer, 2000). All you need to do is add an if statement inside that function testing a variable that controls how many times you have run the timer, and then call/not call timer() accordingly. Here is a working example of it: https://jsfiddle.net/L38q6k5d/, but just to give you an idea of how it would work:
At the top of the js file:
var timesRun = 0
var timerInterval = null;
Inside the surrender function:
timesRun += 1 // Increment it each time the timer ends
if (timesRun > 4) { // If the timer has run less than 4 times
return; // this will stop the function here, so we dont start the timer again
}
setTimeout(timer, 2000); // Reset the timer
Inside the timer function,
if (timesRun > 1) {
clearInterval(timerInterval);
return; // end the function here
}
When starting the initial timer:
timer();
timerInterval = setInterval(timer, 17000);
Complete JS:
var secondsP = document.getElementById('seconds');
var btn1 = document.getElementById("btnSurrender");
var clock = null;
var timerInterval = null;
// New Code
var numberOfTimesRun = 0; // this is where we keep track of how many times the timer has run
btn1.addEventListener("click", surrender);
function timer () {
clearInterval(clock);
// New Code
if (numberOfTimesRun > 1) {
clearInterval(timerInterval);
return; // end the function here
}
// End New Code
var start = new Date().getTime();
clock = setInterval(function() {
var seconds = Math.round(15 - (new Date().getTime() - start) / 1000);
if (seconds >= 0) {
secondsP.textContent = seconds;
} else {
clearInterval(clock);
numberOfTimesRun += 1; // so we know that 1 iteration of the timer has been completed
}
if (seconds === 0) {
}
}, 1000);
}
function surrender(){
clearInterval(clock);
secondsP.textContent = 0;
//New Code
numberOfTimesRun += 1;
if (numberOfTimesRun > 4) {
return; // end the function there
}
setTimeout(timer, 2000)
//End New Code
}
timer();
timerInterval = setInterval(timer, 17000);
I am working on a clock that needs to display seconds into a
minutes:seconds
format.
I have worked on some auxiliary functions for display, but I have never really gotten the full display. Here is some of my code:
var time = 1500;
//Must declare timeHandler as global variable for stopTimer()
var timeHandler;
//Set intial HTML to time
document.getElementById("timer").innerHTML = display;
//Timer function for start button
function timer() {
timeHandler = setInterval(function() {
if (time > 0) {
time--;
document.getElementById("timer").innerHTML = time;
}
}, 1000);
}
//Stop function for stop button
function stopTimer() {
clearTimeout(timeHandler);
}
//Timer Display
var minutes = time/60;
var second = time%60;
var display = minutes + ":" + seconds;
HTML:
<h1> Pomodoro Clock</h1>
<!--Place holder for timer-->
<div id="timer" class="circle">Timer</div>
<!--//Start Button-->
<button onclick="setTimeout(timer, 1000);">Start</button>
<!--Stop Button-->
<button onclick="stopTimer()">Stop</button>
Thie formatTime function below will take a number of seconds, and convert it to MM:SS format (including padded zeroes):
var time = 1500;
//Must declare timeHandler as global variable for stopTimer()
var timeHandler;
//Set intial HTML to time
document.getElementById("timer").innerHTML = display;
//Timer function for start button
function timer() {
timeHandler = setInterval(function() {
if (time > 0) {
time--;
document.getElementById("timer").innerHTML = formatTime(time);
}
}, 1000);
}
//Stop function for stop button
function stopTimer() {
clearTimeout(timeHandler);
}
function formatTime(seconds) {
//Timer Display
var minutes = seconds / 60;
var second = seconds % 60;
return ('0'+minutes).substr(-2) +":"+ ('0'+seconds).substr(-2);
}
first of all you have to use clearInterval, then you don't update your display every second
check this fiddle out
I am having trouble getting a javascript function to reset itself after an onclick event. When I click the "Start" button the counter begins to count up. But when I click the "Reset" button nothing happens. I need the timer to reset to "0:00" and wait for me to click "Start" again. Here is my code:
<script type="text/javascript">
var seconds = 0;
var minutes = 0;
function zeroPad(time) {
var numZeropad = time + '';
while(numZeropad.length < 2) {
numZeropad = "0" + numZeropad;
}
return numZeropad;
}
function countSecs() {
seconds++;
if (seconds > 59) {
minutes++;
seconds = 0;
}
document.getElementById("timeBox").innerHTML = "Time " + zeroPad(minutes) + ":" + zeroPad(seconds);
}
function startTimer() {
action = window.setInterval(countSecs,1000);
}
function resetTimer() {
var seconds = 0;
var minutes = 0;
}
</script>
<body>
<button onclick = "startTimer()">Start</button>
<div id="timeBox">Time 00:00</div>
<button onclick = "resetTimer">Reset</button>
</body>
Call the clearInterval() method.
function resetTimer() {
window.clearInterval(action);
}
This is a scoping issue, using var inside a function, makes seconds and minutes local to that function. Removing the leading var will start you off in the right direction.
function resetTimer() {
seconds = 0;
minutes = 0;
}
Onclick events must call functions like: onclick="resetTimer();" with the parenthesis at the end. Some browsers may try to submit on button clicks if you don't define type="button". I didn't assume you wanted reset timer to stop the timer so I added a stop button.
http://jsfiddle.net/iambriansreed/WRdSK/
<button type="button" onclick="startTimer();">Start</button>
<div id="timeBox">Time 00:00</div>
<button type="button" onclick="resetTimer();">Reset</button>
<button type="button" onclick="stopTimer();">Stop</button>
<script>
window.seconds = 0;
window.minutes = 0;
function startTimer() {
window.action = setInterval(countSecs,1000);
}
function resetTimer() {
seconds = 0;
minutes = 0;
}
function stopTimer() {
clearInterval(action);
seconds = -1;
minutes = 0;
countSecs();
}
function zeroPad(time) {
var numZeropad = time + '';
while(numZeropad.length < 2) {
numZeropad = "0" + numZeropad;
}
return numZeropad;
}
function countSecs() {
seconds++;
if (seconds > 59) {
minutes++;
seconds = 0;
}
document.getElementById("timeBox").innerHTML = "Time " + zeroPad(minutes) + ":" + zeroPad(seconds);
}
</script>
You have two errors in your code:
First, in the button you missed the () after the function's name in order to make an actual call:
<button onclick = "resetTimer()">Reset</button>
Second, you did not stop the interval using window.clearInterval() (MDN docu), so the timer went on and on.
// just to make it an explicit global variable. already was an implicit one.
var action;
// rest of your code
function resetTimer() {
// clear the timer
window.clearInterval( action );
// reset variables
var seconds = 0;
var minutes = 0;
// update output
document.getElementById("timeBox").innerHTML = "Time " + zeroPad(minutes) + ":" + zeroPad(seconds);
}
I set up a working fiddle here.