Categories
JavaScript

Javascript for optimizers #7: Inserting a countdown offer

Want to test inserting a countdown offer? Then, you need to learn JavaScript. I started a series covering practical step-by-step ways to use JavaScript to set up winning experiments on your website.

Each article in the series covers a different JavaScript method, illustrated by applying best practices to websites as hypothetical cases.

Business case: Inserting a countdown offer to increase the conversion rate

Our hypothetical case for this chapter is about inserting a countdown offer to increase the conversion rate.

In this hypothetical scenario, we arrive at the following hypothesis:

“Because we saw that people are more likely to buy something when the product is scarce, we expect that adding a countdown timer will cause an increase in conversions. We’ll measure this using conversion-rate.”

To test this hypothesis, we’re going to apply the changes below:

We are inserting a countdown above our products
We are inserting a countdown above our products

The code used in the experiment

Now for the fun part! 

To execute the change, we run the following JavaScript code on the testing page. Try it out for yourself to see it in action!

var warning = document.querySelector(".warning");
var productBlock = document.querySelector(".countdown");
productBlock.innerHTML = "--" + " HR " + "--" + " MIN " + "--" + " SEC ";
var todayDate = new Date();
var targetDate = todayDate.setDate(todayDate.getDate() + 1);
//var targetDate = new Date("Jan 1, 2023 16:32:55").getTime();

var x = setInterval(function() {
  var nowDate = new Date();
  var difference = targetDate - nowDate;
  var hours = Math.floor(
    (difference % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60)
  );
  var minutes = Math.floor((difference % (1000 * 60 * 60)) / (1000 * 60));
  var seconds = Math.floor((difference % (1000 * 60)) / 1000);
  productBlock.innerHTML =
    hours + " HR " + minutes + " MIN " + seconds + " SEC ";
  if (difference < 0) {
    clearInterval(x);
    productBlock.style.display = "none";
    warning.style.display = "none";
  }
}, 1000);

productBlock.style.color = "#d72756";
productBlock.style.textAlign = "center";
productBlock.style.border = "1px solid #d72756";
productBlock.style.borderRadius = "4px";
warning.innerHTML = "DISCOUNT OFFER EXPIRES IN:";
warning.style.textAlign = "center";
warning.style.color = "#d72756";
warning.style.fontSize = "24px";
warning.style.fontWeight = "bold";

Breakdown of the code

1. New syntax

The breakdown starts by going over all the new syntax in the example above. Since this article is part of a series, make sure you check the syntax’s complete documentation in the previous articles.

“–” + ” HR ” + “–” + ” MIN ” + “–” + ” SEC “ is an example of concatenation. You can use the + operator to combine values into a single string. Once you try to concatenate something with a string, it will automatically convert that value to a string. This behavior can be relevant when you are combining a number with a string.

new is an operator that creates an instance of an object type. You can use this operator to create a bunch of different versions of an object constructor.

Date() is an object that represents a single point of time. It contains the number of milliseconds since 1-1-1970. This way, it can calculate the time in many different formats.

.setDate(dayNumber) is a method of the date object that changes the day. You can pass down a number as the argument to define the day. We don’t have to change the number to a string, so you need to leave out the quotes this time.

.getDate() is a method that returns the day of a date object. It will produce a number type.

.getTime() is a method that returns the number of milliseconds between the date object and 1-1-1970.

setInterval(function(){ },delay) is a method of the window object. You can use it to run specific functions on an interval. The interval is decided by passing down the delay argument as milliseconds in the method.

Math.floor() is a math object method and removes the decimals from a number to return an integer. When you pass down a 5.5, the method will return it as a 5.

% is a remainder operator and works just like standard arithmetics. It returns what is left after dividing the number left of the operator by the right one.

* is a multiplication operator and also works as it does in standard arithmetics. It will multiply the value left of the operator by the value right of the operator.

/ is a division operator that divides the value left of the operator by the right one.

is a subtraction operator that subtracts the value on the left of the operator by the right one.

clearInterval(x) is a method that stops a setInterval function from running. Setting the setInterval to a variable, you can pass this instance as the argument of clearInterval to stop the specified method you want.

.style.color is a property that sets the text color of an element.

.style.textAlign is a property that sets the text alignment of an element.

.style.border is a property that sets the border style of an element.

.style.borderRadius is a property that sets the border-radius of an element.

.style.fontSize is a property that sets the font size of an element.

.style.fontWeight is a property that sets the font-weight of an element.

2. Logic

var warning = document.querySelector(".warning");

First, we select the div with the class warning using the querySelector method. The warning class will be the spot where we input our discount warning. We declare the variable warning and assign the selected div.

var productBlock = document.querySelector(".countdown");

Then we select the div with the class countdown using the querySelector method. Here we are going append our actual countdown. We declare the variable productBlock and assign the selected div.

productBlock.innerHTML = "--" + " HR " + "--" + " MIN " + "--" + " SEC ";

Before we input our time, I insert a placeholder string into de product block variable using the innerHTML method. We do this because it takes a short time before it knows what time should be inserted. This way, the visitor doesn’t experience that an element is loaded slightly later than usual. That’s also why we do it before the main function.

The countdown timer while it loads the time
The countdown timer while it loads the time
var todayDate = new Date();

Here we create a new Date object using the new operator and calling the data function. The date that is created represents the time that it is created. We declare the variable todayDate and assign our new date.

var targetDate = todayDate.setDate(todayDate.getDate() + 1);

For this example to work, we need to have a target date. This target date needs to be in the future. Otherwise, you will be counting in the past. This piece of code sets the targetDate 24 hours later than the todayDate.

It does this by getting the day of the todayDate variable with the getDate method. Then we add one more day to the value and set it using the setDate property. We declare the variable targetDate and assign our new date Object to it.

//var targetDate = new Date("Jan 1, 2023 16:32:55").getTime();

If you want to use a specific date for a promotion, you need to comment out the previous line by adding two slashes. Remove the slashes from this line and insert that date you want. It will automatically convert the variable time to milliseconds because of the getTime method.

var x = setInterval(function() {

This line starts the interval function. We declare the variable x and assign the interval function. Everything that is between the curly brackets of this function will run every interval. The interval time is set after the function. Notice how this entire function is actually in the first argument of setInterval.

var nowDate = new Date();

Every time our function runs, we need to know what time it is to update our timer. By checking this every one second, we have a timer. We declare the variable nowDate for this and assign a new date object every time the function runs.

var difference = targetDate - nowDate;

This line finds out the difference in milliseconds between the two date objects. It does this by subtracting the nowDate variable from the targetDate variable. We declare the difference variable and assign this subtracted value to it.

var hours = Math.floor((difference % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));

In this line of code, we do some math to find out how many hours the difference variable contains. It does this by finding the milliseconds and using the Math.Floor method to get the hour without decimals. We declare the variable hours and assign this value to it.

var minutes = Math.floor((difference % (1000 * 60 * 60)) / (1000 * 60));

Here we do the same for the minutes.

var seconds = Math.floor((difference % (1000 * 60)) / 1000);

And again for the seconds.

productBlock.innerHTML = hours + " HR " + minutes + " MIN " + seconds + " SEC ";

Then we set the screen’s timer to the time of the current interval by using string concatenation. Using the innerHTML method on the productBlock variable will show it on the screen.

The countdown timer when it starts ticking
The countdown timer when it starts ticking
if (difference < 0) {

This line of code checks if the variable difference in milliseconds is smaller than 0. Smaller means that the current time has surpassed the target time. If this is true, it will run the code between the curly brackets.

clearInterval(x);

When it has reached the target time, we don’t have to run the interval anymore. We run the clearInterval method and pass down the setInterval function that is assigned to the variable X as an argument. This action will stop the function.

productBlock.style.display = "none";

Then we hide the countdown timer because it has stopped counting. We do this using the style method and adding display none to the element.

warning.style.display = "none";

Then we also hide the warning message. The code has a fallback option now. It is recommended to think about ways that it can go wrong and coding a fallback for it.

}

Then we close the condition with the curly bracket.

}, 1000);

Then we close the function in the first argument of setInterval. We also set the interval time in milliseconds after the comma. We can now close the function call with a bracket and semicolon.

productBlock.style.color = "#d72756";

We change the text color to red.

The countdown timer now has a red color
The countdown timer now has a red color
productBlock.style.textAlign = "center";

Then we align the text of the countdown in the center.

The countdown timer is now centered
The countdown timer is now centered
productBlock.style.border = "1px solid #d72756";

We add a border 1-pixel solid border to our countdown.

The countdown timer with red border
The countdown timer with red border
productBlock.style.borderRadius = "4px";

Make it look a little nicer with some rounded corners.

The countdown timer with rounded corners
The countdown timer with rounded corners
warning.innerHTML = "DISCOUNT OFFER EXPIRES IN:";

Then we give some context to our countdown by adding some text.

Adding context to the countdown timer
Adding context to the countdown timer
warning.style.textAlign = "center";

We align the text to the center.

Centering the discount text
Centering the discount text
warning.style.color = "#d72756";

We give the text some color.

Giving the discount text some color
Giving the discount text some color
warning.style.fontSize = "24px";

Increase the text size a little bit.

Making sure everyone can read it
Making sure everyone can read it
warning.style.fontWeight = "bold";

Change the font weight to bold.

Inserting a countdown offer triggers the feeling of scarcity
Inserting a countdown offer triggers the feeling of scarcity

Now you are to start inserting your own countdown offer!

3. Exercise

The best way to learn JavaScript is to try it. 

I want you to change the text, so it says: “THE DISCOUNT IS ALMOST OVER.” I also want you to remove the visible hours from the timer. And shoot me a message to let me know what you think!

We remove the hours and change the text
We remove the hours and change the text

Get access to all JavaScript exercise code.