I'm somewhat new to Javascript. Last year my countdown worked correctly. However, as soon Christmas hit, it started counting down to February 27 of the new year and I can't figure out why.
I tried moving some of the variables (year and countDownDate) and I also tried restarting countDownDate when I restart year. But since the year hasn't restarted I'm honestly not too sure if either of these worked.
var d = new Date();
var year = d.getFullYear();
// Set the date we're counting down to
var countDownDate = new Date("Dec 25, " + year + " 0:00:01").getTime();
// Update the count down every 1 second
var x = setInterval(function() {
// Get todays date and time
var now = new Date().getTime();
// Find the distance between now and the count down date
var distance = countDownDate - now;
// Time calculations for days, hours, minutes and seconds
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
// Output the result in an element with id="demo"
document.getElementById("demo").innerHTML = ('0' + days).slice(-2) + "d " + ('0' + hours).slice(-2) + "h " + ('0' + minutes).slice(-2) + "m " + ('0' + seconds).slice(-2) + "s ";
// If the count down is over, restart timer to next Christmas
if (distance == 0) {
year = d.getFullYear() + 1;
}
}, 1000);
I would like it to countdown to Christmas each year. So then when Christmas hits it needs to begin the countdown for the next year.
I used the advice below from Tyler Roper and iagowp to make it work correctly! Showing the hundredths place for the days is very important.
You have a bug here:
('0' + days).slice(-2)
When days are bigger than 100, you are removing one of the chars, so if days = 349, it will become 49 days.
If you want to make sure it has at least double digits, you could replace it by
(days > 10 ? days : '0' + days) + "d " + ('0' + hours).slice(-2) + "h " + ('0' + minutes).slice(-2) + "m " + ('0' + seconds).slice(-2) + "s ";
Related
I used the snippet below to create a countdown timer.
<script>
// Set the date we're counting down to
var countDownDate = new Date("Jan 5, 2024 15:37:25").getTime();
// Update the count down every 1 second
var x = setInterval(function() {
// Get today's date and time
var now = new Date().getTime();
// Find the distance between now and the count down date
var distance = countDownDate - now;
// Time calculations for days, hours, minutes and seconds
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
// Output the result in an element with id="demo"
document.getElementById("demo").innerHTML = days + "d " + hours + "h " +
minutes + "m " + seconds + "s ";
// If the count down is over, write some text
if (distance < 0) {
clearInterval(x);
document.getElementById("demo").innerHTML = "EXPIRED";
}
}, 1000);
</script>
How do I set the output (display) like so:
If the remaining time is still above 1 month, then display only the month.
If the remaining time is under 1 month, then display only days,
If the remaining time is below 24 hours, display the hours and minutes
If the remaining time is below 1 hour, display the minutes and seconds.
Thanks
first add a calculation for number of months left
then add a function that limits the times like so
const displayRemaining = () => {
if (/* there are months remaining */) return months + " months";
if (/* there are days remaining */) return days + " days";
if (/* there are hours remaining */) return hours + " hours";
if (/* there are days remaining */) return minutes + ":" + seconds + " m:s";
return "you have gone back in time or smth idk";
}
Im setting up a new years countdown (bit late i know) but i would like to know how to get this to work for other timezones
I have already got it working for the usual UTC timezone as thats default. I have tried the .toLocalString and it returned NaN on the countdown
var countDownDate = new Date("Dec 31, 2018 23:59:02").getTime();
var x = setInterval(function() {
var now = new Date().getTime();
var distance = countDownDate - now;
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 *
60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
document.getElementById("display").innerHTML = days + "d " + hours + "h "
+ minutes + "m " + seconds + "s ";
if (distance < 0) {
clearInterval(x);
document.getElementById("display").innerHTML = "Happy New Year!";
done()
}
}, 1000);
The Date function of javascript returns local time of each timezone depending from where the page is loaded. So you don't have to keep track of each timezone
explained here
You can achieve this with moment.js easily:
var tz = moment.tz.guess();
console.log("Current Timezone: " + tz);
var last = moment.tz("2018-12-31 23:59:02", tz);
setInterval(function(){
var current = moment.tz(tz);
if(current.isBefore(last, "seconds")){
var diff = moment.duration(last.diff(current));
document.getElementById("display").innerHTML = diff.days() + "d " +
diff.hours() + "h " + diff.minutes() + "m " + diff.seconds() + "s";
}else{
document.getElementById("display").innerHTML = "Happy New Year!";
}
}, 1000);
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.23.0/moment.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment-timezone/0.5.23/moment-timezone-with-data-2012-2022.min.js"></script>
<div id="display"></div>
I'm working on a countdown date script. However, the environment I'm working in does not refresh the page on submission, so I'm having an issue with multiple intervals being created. I believe if there was a way to check if there is an interval running, then to clear it and create a new one. But I'm not sure of how to do this. Of course, if there is a better strategy than how I currently have my code set up, then feel free to provide that as well.
My Code:
//get ready for a-togglin'
var finishedMessage = document.getElementById('finshedMessage');
//get dates value
var dateValue = document.getElementById('dateInput').innerText;
var dateEntered = new Date(dateValue);
//set the date we're counting down too
var targetDate = new Date(dateEntered).getTime();
//Update the countdown every second
var countInterval = setInterval(function() {
var now = new Date().getTime();
//get time remaining from now
var timeRemaining = targetDate - now;
//time calculations : days, hours, minutes and seconds
var days = Math.floor(timeRemaining / (1000 * 60 * 60 * 24));
var hours = Math.floor((timeRemaining % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((timeRemaining % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((timeRemaining % (1000 * 60)) / 1000);
//When the countdown is finished, report back completion text
if (timeRemaining <= 0 || NaN) {
finishedMessage.style.display = "inline-block";
clearInterval(countInterval);
} else {
//if day is over a year count the years remaining if no years just count days
if (days > 365) {
var years = Math.floor(days / 365);
days = days % 365;
document.getElementById("report").innerHTML = years + "Y " + days + "D " + hours + "H " + minutes + "M " + seconds + "s ";
} else {
//report the remaining time to report div
document.getElementById("report").innerHTML = days + "D " + hours + "H " + minutes + "M " + seconds + "s ";
}
}
}, 1000);
I'm afraid there's not how to clear all intervals declared without having the value returned from them. But you can save the reference to the global window object when running it for the first time, so you can reset it whenever you want:
if (window.countInterval) clearInterval(window.countInterval)
window.countInterval = setInterval(function () {
/* your code here */
})
It is not an error to call clearInterval for interval id already stopped. So you can do just
clearInterval(intervalId);
intervalId = setInterval(.....);
Key variables to keep in mind:
This is set to simulate 11:00 PM.
var bt = "23:00";
This is set to simulate 8:00 AM.
var wt = "08:00";
The desired functionality:
The countdown timer starts every morning at 8:00 AM.
It counts down until 11:00 PM, every night.
Then it stays at 00:00:00.
In the morning, at 8:00 AM, it repeats the count-down, again.
This should happen forever.
What is actually happening:
Everything is working fine, except it is starting a 24 hour countdown at midnight, until 8:00 AM.
I have tried debugging this, and I suspect the error lies in what is calculated as the distance variable, making the code think that it is comparing against the next day, but I am not sure how to remedy this.
Here is the Codepen.
and here is my JS code:
$(document).ready(function () {
var bt = "23:00"; // 11:00 PM
var wt = "08:00"; // 08:00 AM
var dateNow = moment().format('MMM D, YYYY');
placeHolderDate = dateNow + " " + bt;
var timeNow = moment().format('HH:mm');
var countDownDate = new Date(placeHolderDate).getTime();
var countDownHourMin = (wt.split(":"));
// Update the count down every 1 second
var x = setInterval(function () {
// Get todays date and time
var now = new Date().getTime();
// Find the distance between now and the count down date
var distance = countDownDate - now;
// Time calculations for days, hours, minutes and seconds
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
$("#countDown").val(hours + ":" + minutes + ":" + seconds);
// If the countdown is over, write some text
if (hours === 0 && minutes === 0 && seconds === 0) {
//clearInterval(x);
$("#countDown").val("00:00:00");
}
if (hours < 0 || minutes < 0 || seconds < 0) {
//clearInterval(x);
$("#countDown").val("00:00:00");
}
var timeNow = moment().format('HH:mm');
//console.log('Time Now:' + timeNow);
//console.log('Wake Time:' + wt);
if (timeNow === wt) {
clearInterval(x);
restartCountdown();
}
//console.log(hours + ":" + minutes + ":" + seconds);
}, 1000);
function restartCountdown() {
//log("restartCountdown Started!");
var bt = "23:00"; // 11:00 PM
var wt = "08:00"; // 08:00 AM
var dN = (moment().add(moment.duration({d: 1})).format('MMM D, YYYY'));
console.log('dn ' + dN);
var placeHolderDate = dN + " " + bt;
var countDownDate = new Date(placeHolderDate).getTime();
var countDownHourMin = (wt.split(":"));
// Update the count down every 1 second
var x = setInterval(function () {
// Get todays date and time
var now = new Date().getTime();
// Find the distance between now and the count down date
var distance = countDownDate - now;
// Time calculations for days, hours, minutes and seconds
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
$("#countDown").val(hours + ":" + minutes + ":" + seconds);
// If the countdown is over, write some text
if (hours === 0 && minutes === 0 && seconds === 0) {
//clearInterval(x);
$("#countDown").val("00:00:00");
}
if (hours < 0 || minutes < 0 || seconds < 0) {
//clearInterval(x);
$("#countDown").val("00:00:00");
}
// console.log(hours + ":" + minutes + ":" + seconds);
}, 1000);
}
});
I have edited your code and created this codepen https://codepen.io/anon/pen/aabjEb?editors=0010. Please feel free to optimize the code since I have not done it. The idea was is check if time is between 8 AM and 11 PM. If yes show value else show 00:00:00. Also once the date changes, update the dates and now compute accordingly
$(document).ready(function () {
function countdown() {
var bt = "23:00", // 11:00 PM
wt = "08:00"; // 08:00 AM
var today = new Date(),
dd = today.getDate(),
mm = today.getMonth()+1,
yyyy = today.getFullYear();
var startTime = new Date(mm + '/' + dd + '/' + yyyy + ' ' + wt),
endTime = new Date(mm + '/' + dd + '/' + yyyy + ' ' + bt);
setInterval(function() {
var now = new Date();
var nowdd = today.getDate();
var nowTime = now.getTime();
if(dd !== nowdd) {
dd = nowdd;
var nowmm = now.getMonth() + 1,
nowyyyy = now.getFullYear();
startTime = new Date(dd + '/' + mm + '/' + yyyy + ' wt');
endTime = new Date(dd + '/' + mm + '/' + yyyy + ' bt');
}
if(nowTime > startTime && nowTime < endTime) {
// Find the distance between now and the count down date
var distance = endTime - nowTime;
// Time calculations for days, hours, minutes and seconds
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60)),
minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60)),
seconds = Math.floor((distance % (1000 * 60)) / 1000);
$("#countDown").val(hours + ":" + minutes + ":" + seconds);
} else {
$("#countDown").val("00:00:00");
}
}, 1000);
}
countdown();
});
I am trying to make a countdown timer which displays the amount of time remaining for a customer to purchase in order to receive same day shipping.
For example, if they purchase before 15:30 the timer will say something like order within 30 minutes for shipping today (if it was 15:00).
However, when it reaches 15:30, I want it to say order within 23 hours and 59 minutes to receive shipping tomorrow. Then obviously when it reaches midnight it will turn to today. Alternatively it can just display the day/date so today/tomorrow won't matter.
I know I need to call the function again looking at tomorrows date but I'm not very handy with javascript so cannot figure it out.
Can someone help?
// Set the date we're counting down to
var nowDate = new Date();
var countDownDate = new Date(nowDate.getFullYear(), nowDate.getMonth(), nowDate.getDate(), 15, 30, 0, 0);
// Update the count down every 1 second
var x = setInterval(function() {
// Get todays date and time
var now = new Date().getTime();
// Find the distance between now an the count down date
var distance = countDownDate - now;
// Time calculations for hours, minutes and seconds
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
// Display the result in the element with id="demo"
if (hours >= 1) {
document.getElementById("shipping-countdown").innerHTML = "Order within " + hours + "h "
+ minutes + "m " + seconds + "s " + "to have your order shipped on " // date of shipment;
}
else if (hours < 1 && minutes < 1) {
document.getElementById("shipping-countdown").innerHTML = "Order within " + seconds + "s "
+ "to have your order shipped on " // date of shipment;
}
else {
document.getElementById("shipping-countdown").innerHTML = "Order within " + minutes + "m "
+ seconds + "s " + "to have your order shipped on " // date of shipment;
}
// If the count down is finished, write some text
if (distance < 0) {
clearInterval(x);
// Start again but looking at tomorrows date
}
// If the count down is finished, write some text
if (nowDate.getDay() == 0 || nowDate.getDay() == 6) {
clearInterval(x);
document.getElementById("shipping-countdown").innerHTML = "Order within " + days + "d "
+ hours + "h "
+ minutes + "m " + seconds + "s " + "to have your order shipped on " // Start of the week;
}
}, 1000);
<!-- Display the countdown timer in an element -->
<p id="shipping-countdown"></p>
You don't need to clear the setInterval function. Just reset the new target date while keeping it alive. You also had some issues with the countdown going into the negatives which I fixed by moving the distance check and resetting the distance if it is under 1 second.
// Set the date we're counting down to
var nowDate = new Date();
var countDownDate = new Date(nowDate.getFullYear(), nowDate.getMonth(), nowDate.getDate(), 11, 2, 50, 0);
// Update the count down every 1 second
var x = setInterval(function() {
// Get todays date and time
var now = new Date().getTime();
// Find the distance between now an the count down date
var distance = countDownDate - now;
if (distance < 1) {
countDownDate = countDownDate.setDate(countDownDate.getDate()+1);
distance = countDownDate - now;
}
// Time calculations for hours, minutes and seconds
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance%(1000 * 60))/ 1000);
// Display the result in the element with id="demo"
if (hours >= 1) {
document.getElementById("shipping-countdown").innerHTML = "Order within " + hours + "h "
+ minutes + "m " + seconds + "s " + "to have your order shipped on " // date of shipment;
}
else if (hours < 1 && minutes < 1) {
document.getElementById("shipping-countdown").innerHTML = "Order within " + seconds + "s "
+ "to have your order shipped on " // date of shipment;
}
else {
document.getElementById("shipping-countdown").innerHTML = "Order within " + minutes + "m "
+ seconds + "s " + "to have your order shipped on " // date of shipment;
}
// If the count down is finished, write some text
if (nowDate.getDay() == 0 || nowDate.getDay() == 6) {
clearInterval(x);
document.getElementById("shipping-countdown").innerHTML = "Order within " + days + "d "
+ hours + "h "
+ minutes + "m " + seconds + "s " + "to have your order shipped on " // Start of the week;
}
}, 1000);
<!-- Display the countdown timer in an element -->
<p id="shipping-countdown"></p>
I have managed to achieve this with the following code, figured out I was along the wrong lines and could simply just adjust the countDownDate variable.
// Set the date we're counting down to
var nowDate = new Date();
var countDownDate = new Date(nowDate.getFullYear(), nowDate.getMonth(), nowDate.getDate(), 15, 30, 0, 0);
// Update the count down every 1 second
var x = setInterval(function() {
// Get todays date and time
var now = new Date().getTime();
// Find the distance between now an the count down date
var distance = countDownDate - now;
// Time calculations for hours, minutes and seconds
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
// If the count down is finished, write some text
if (countDownDate.getDay() == 6) {
countDownDate.setDate(countDownDate.getDate()+2);
}
if (days >= 1) {
document.getElementById("shipping-countdown").innerHTML = "Order within " + days + "d " + hours + "h "
+ minutes + "m " + seconds + "s " + "to have your order shipped on " + countDownDate;
}
else if (hours >= 1) {
document.getElementById("shipping-countdown").innerHTML = "Order within " + hours + "h "
+ minutes + "m " + seconds + "s " + "to have your order shipped on " + countDownDate.getDate() + "/"
+ (countDownDate.getMonth()+1) + "/" + countDownDate.getFullYear();
}
else if (minutes >= 1) {
document.getElementById("shipping-countdown").innerHTML = "Order within " + minutes + "m " + seconds + "s "
+ "to have your order shipped on " + countDownDate.getDate() + "/"
+ (countDownDate.getMonth()+1) + "/" + countDownDate.getFullYear();
}
else {
document.getElementById("shipping-countdown").innerHTML = "Order within " + seconds + "s "
+ "to have your order shipped on " + countDownDate.getDate() + "/"
+ (countDownDate.getMonth()+1) + "/" + countDownDate.getFullYear();
}
// If the count down is finished
if (distance < 0) {
countDownDate.setDate(countDownDate.getDate()+1);
}
}, 1000);
<!-- Display the countdown timer in an element -->
<p id="shipping-countdown"></p>