Tari Ibaba

Tari Ibaba is a software developer with years of experience building websites and apps. He has written extensively on a wide range of programming topics and has created dozens of apps and open-source libraries.

How to Subtract Minutes From a Date in JavaScript

Let’s learn how to easily subtract any number of minutes from a Date object in JavaScript.

1. Date getMinutes() and setMinutes() methods

To subtract minutes from a Date:

  1. Call the getMinutes() method on the Date to get the minutes.
  2. Subtract the minutes.
  3. Pass the difference to the setMinutes() method.

For example:

function subtractMinutes(date, minutes) {
  date.setMinutes(date.getMinutes() - minutes);

  return date;
}

// 2:20 pm on May 18, 2022
const date = new Date('2022-05-18T14:20:00.000Z');

const newDate = subtractMinutes(date, 10);

// 2:10 pm on May 18, 2022
console.log(newDate); // 2022-05-18T14:10:00.000Z

Our subtractMinutes() function takes a Date object and the number of minutes to subtract as arguments. It returns the same Date object with the minutes subtracted.

The Date getMinutes() method returns a number between 0 and 59 that represent the minutes of a particular Date.

The Date setMinutes() method set the minutes of a Date to a specified number.

If the minutes subtracted decrease the hour, day, month, or year of the Date object, setMinutes() will automatically update the information in the Date to reflect this.

// 10:10 am on March 13, 2022
const date = new Date('2022-03-13T10:10:00.000Z');

date.setMinutes(date.getMinutes() - 30);

// 9:40 am on March 13, 2022
console.log(date); // 2022-05-18T14:10:00.000Z

In this example, decreasing the minutes of the Date by 30 rolls the hour back by 1.

Avoiding side effects

The setMinutes() method mutates the Date object it is called on. This introduces a side effect into our subtractMinutes() function. To avoid modifying the passed Date and create a pure function, make a copy of the Date and call setMinutes() on this copy, instead of the original.

function subtractMinutes(date, minutes) {
  // πŸ‘‡ make copy with "Date" constructor
  const dateCopy = new Date(date);

  dateCopy.setMinutes(date.getMinutes() - minutes);

  return dateCopy;
}

const date = new Date('2022-02-20T11:25:00.000Z');

const newDate = subtractMinutes(date, 5);

// 11:20 am on Feb 20, 2022
console.log(newDate); // 2022-02-20T11:20:00.000Z

// πŸ‘‡ Original not modified
console.log(date); // 2022-02-20T11:25:00.000Z

Tip:Β Functions that don’t modify external state (i.e., pure functions) tend to be more predictable and easier to reason about, as they always give the same output for a particular input. This makes it a good practice to limit the number of side effects in your code.

2. date-fns subMinutes() function

Alternatively, we can use the subMinutes() function from the date-fns NPM package to quickly subtract minutes from a Date in JavaScript. It works like our pure subtractMinutes() function.

import { subMinutes } from 'date-fns';

const date = new Date('2022-10-03T20:50:00.000Z');

const newDate = subMinutes(date, 25);

// 8:25 pm on October 3, 2022
console.log(newDate); // 2019-02-20T11:20:00.000Z

// Original not modified
console.log(date); // 2022-02-20T11:25:00.000Z

How to Remove All Classes From an Element With JavaScript

Related: How to Remove a Class From All Elements in JavaScript

To remove all classes from an element in JavaScript, set the className property of the element to an empty string (''), i.e., element.className = ''. Setting the className property to an empty string will eliminate every class in the element.

const box = document.getElementById('box');

// πŸ‘‡ Remove all classes from element.
box.className = '';

For this HTML:

index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>Coding Beauty Tutorial</title>
    <style>
      .class-1 {
        height: 30px;
        width: 300px;
        font-size: 1.1em;
        box-shadow: 0 2px 3px #c0c0c0;
      }

      .class-2 {
        background-color: blue;
        color: white;
        border: 1px solid black;
        border-radius: 3px;
      }
    </style>
  </head>
  <body>
    <input id="input" type="text" class="class-1 class-2" />
    <br /><br />
    <button id="btn">Remove classes</button>
    <script src="index.js"></script>
  </body>
</html>

This JavaScript code will remove all classes from the input field when the button is clicked:

index.js

const btn = document.getElementById('btn');

const input = document.getElementById('input');

btn.addEventListener('click', () => {
  input.className = '';
});
All classes from the input field are removed when the button is clicked.

The className property is used to get and set the value of the class attribute of a specified element.

Setting className to an empty string effectively removes all the classes from the element.

Remove all classes from element with removeAttribute() method

To remove all classes from an element with this approach, call the removeAttribute() method on the specified for the class attribute, i.e., element.removeAttribute('class'). This method will remove the class attribute from the element, effectively removing all the element’s classes.

const box = document.getElementById('box');

// πŸ‘‡ Remove all classes from element
box.removeAttribute('class');

removeAttribute() takes a name and removes the attribute from an element with that name.

For this HTML:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>Coding Beauty Tutorial</title>
    <style>
      .class-1 {
        height: 30px;
        font-size: 1.1em;
        box-shadow: 0 2px 3px #c0c0c0;
      }

      .class-2 {
        background-image: linear-gradient(to bottom, rgb(136, 136, 255), blue);
        color: white;
        border: none;
      }
    </style>
  </head>
  <body>
    <button id="styled-btn" type="text" class="class-1 class-2">
      Download
    </button>
    <br /><br />
    <button id="btn">Remove classes</button>
    <script src="index.js"></script>
  </body>
</html>

This JavaScript code will remove all classes from the styled button when the other button is clicked.

const btn = document.getElementById('btn');

const styledButton = document.getElementById('styled-btn');

btn.addEventListener('click', () => {
  styledButton.removeAttribute('class');
});
All classes from removed from the button when the other button is clicked.

In the first method, the class attribute remains on the element after setting the className property. But using the removeAttribute() method completely removes the class attribute from the element.

If the element doesn’t have a class attribute, removeAttribute() will return without causing an error.

Either of these two methods is fine, it’s up to you which one to pick. I think using the className property is better because it more clearly shows what you’re trying to do.

How to Fix the “Cannot read property ‘0’ of undefined” Error in JavaScript

The “cannot read property ‘0’ of undefined” error occurs when you try to access the 0 index of an array-like variable, but the variable turns out to be undefined. To fix it, initialize the variable to a value of the correct data type before accessing the index.

The "cannot read property '0' of undefined" error occuring in JavaScript.

Depending on your scenario, you might be able to resolve the error by doing one of the following:

  1. Provide a defined fallback value for the variable.
  2. Ensure that the variable has been initialized.
  3. If accessing an index of a nested array, check that none of the outer arrays are undefined.

We’ll be touching on these three solutions in this article.

1. Provide defined fallback value

We can fix the “cannot read property ‘0’ of undefined” error in JavaScript by giving the variable a fallback value before accessing it at a specific index. This solution is beneficial when accessing an array property of an object that might return a value of undefined.

We can provide a fallback value with the null coalescing operator (??):

// πŸ‘‡ Initialize to empty array if undefined
const books = library.books ?? [];

const firstBook = books[0];

console.log(library.books); // undefined

console.log(firstBook); // undefined

// Initialize to empty string if undefined
const content = firstBook ?? '';

console.log(content); // '' (empty string)

The nullish coalescing operator (??) returns the value to its left if it is not null or undefined. If it is, then ?? returns the value to its right.

console.log(2 ?? 5); // 2
console.log(undefined ?? 5); // 5

We can use the logical OR (||) operator to replace ??:

console.log(2 || 5); // 2
console.log(undefined || 5); // 5

2. Ensure variable initialization

The “cannot read property ‘0’ of undefined” error in JavaScript will occur when you access the 0 index of a variable that is uninitialized. Unintialized variables in JavaScript have a default value of undefined.

let arr;

console.log(arr); // undefined

// ❌ Cannot read properties of undefined (reading '0')
console.log(arr[0]);

const str;

// ❌ Cannot read properties of undefined (reading '0')
console.log(str[0]);

Fixing the error in this case is easy; just set the variable to a value, e.g., an empty array ([]) for arrays, an empty string ('') for strings, etc.

let arr = [];

console.log(arr); // []

// βœ… No error
console.log(arr[0]); // undefined

const str = '';

// βœ… No error
console.log(str[0]); // undefined

3. Check outer arrays for undefined

The “cannot read property ‘0’ of undefined” error can also occur when accessing the 0 index in nested arrays.

const arr = [[1, 2, 3]];

// ❌ Cannot read properties of undefined (reading '0')
console.log(arr[1][0]);

The array here contains only one element, so accessing the 1 index returns undefined. Accessing the 0 index on undefined then causes the error.

The optional chaining operator is a concise way to prevent this error:

const arr = [[1, 2, 3]];

// βœ… No error
console.log(arr?.[1]?.[0]); // undefined

For nullish values (undefined or null), the optional chaining operator (?.) returns undefined instead of trying to access the property and causing an error.

Since the 1 index of the outer array returned undefined, the optional chaining operator will prevent the property access.

If the value is not nullish, the ?. operator will perform the property access:

const words = [['javascript']];

console.log(words?.[0]?.[0]); // javascript

console.log(words?.[0]?.[0]?.[0]); // j

JavaScript Intersection Observer: Everything You Need to Know

The Intersection Observer API is used to asynchronously observe changes in the intersection of an element with the browser’s viewport. It makes it easy to perform tasks that involve detecting the visibility of an element, or the relative visibility of two elements in relation to each other, without making the site sluggish and diminishing the user experience. We’re going to learn all about it in this article.

Uses of Intersection Observer

Before we start exploring the Intersection Observer API, let’s look at some common reasons to use it in our web apps:

Infinite scrolling

This is a web design technique where content is loaded continuously as the user scrolls down. It eliminates the need for pagination and can improve user dwell time.

Lazy loading

Lazy loading is a design pattern in which images or other content are loaded only when they are scrolled into the view of the user, to increase performance and save network resources.

Scroll-based animations

This means animating elements as the user scrolls up or down the page. Sometimes the animation plays completely once a certain scroll position is reached. Other times, the time in the animation changes as the scroll position changes.

Ad revenue calculation

We can use Intersection Observer to detect when an ad is visible to the user and record an impression, which affects ad revenue.

Creating an Intersection Observer

Let’s take a look at a simple use of an Intersection Observer in JavaScript.

index.js

const observer = new IntersectionObserver((entries) => {
  for (const entry of entries) {
    const intersecting = entry.isIntersecting;
    entry.target.style.backgroundColor = intersecting ? 'blue' : 'orange';
  }
});

const box = document.getElementById('box');

observer.observe(box);

The callback function receives an array containing objects of the IntersectionObserverEntry interface. This object contains intersection-related information about an element currently being watched by the Observer.

The callback is called whenever the target element intersects with the viewport. It is also called the first time the Observer is asked to watch the element.

We use the for...of loop to iterate through the entries passed to the callback. We’re observing only one element, so the entries array will contain just the IntersectionObserverEntry element that represents the box, and the for...of loop will have only one iteration.

The isIntersecting property of an IntersectionObserverEntry element returns a boolean value that indicates whether the element is intersecting with the viewport.

When isIntersection is true, it means that the element is transitioning from non-intersecting to intersecting. But when it is false, it indicates that the element is transitioning from intersecting to non-intersecting.

So we use the isIntersection property to set the color of the element to blue as it enters the viewport, and back to black as it leaves.

We call the observe() method on the IntersectionObserver object to make the Observer start watching the element for an intersection.

In the demo below, the white area with the scroll bar represents the viewport. The gray part indicates areas on the page that are outside the viewport and not normally visible in the browser.

Watch how the color of the box changes as soon as one single pixel of it enters the viewport:

The element changes color once a single pixel of it enters the viewport.
The element changes color once one single pixel of it enters the viewport.

Intersection Observer options

Apart from the callback function, the IntersectionObserver() constructor also accepts an options object we use to customize the conditions that must be met for the callback to be invoked.

threshold

The threshold property accepts a value between 0 and 1 that specifies the percentage of the element that must be visible within the viewport for the callback to be invoked. It has a value of 0 by default, meaning that the callback will be run once a single pixel of the element enters the viewport.

Let’s modify our previous example to use a threshold of 1 (100%):

index.js

const observer = new IntersectionObserver(
  (entries) => {
    for (const entry of entries) {
      const intersecting = entry.isIntersecting;
      entry.target.style.backgroundColor = intersecting ? 'blue' : 'black';
    }
  },
  // πŸ‘‡ Threshold is 100%
  { threshold: 1 }
);

const box = document.getElementById('box');

observer.observe(box);

Now the callback that changes the color will only be executed when every single pixel of the element is visible in the viewport.

The element changes color once every single pixel of it enters the viewport.
The element changes color once every single pixel of it enters the viewport.

threshold also accepts multiple values, which makes the callback get each time the element passes one of the threshold values set.

For example:

index.js

const threshold = document.getElementById('threshold');

const observer = new IntersectionObserver(
  (entries) => {
    for (const entry of entries) {
      const ratio = entry.intersectionRatio;
      threshold.innerText = `${Math.round(ratio * 100)}%`;
    }
  },
  // πŸ‘‡ Multiple treshold values
  { threshold: [0, 0.25, 0.5, 0.75, 1] }
);

const box = document.getElementById('box');

observer.observe(box);

We pass 5 percentage values in an array to the threshold property and display each value as the element reaches it. To do this we use the intersectionRatio property, a number between 0 and 1 indicating the current percentage of the element that is in the viewport.

The text is updated each time a percentage of the element in the viewport reaches a certain threshold.
The text is updated each time a percentage of the element in the viewport reaches a certain threshold.

Notice how the text shown doesn’t always match our thresholds, e.g., 2% was shown for the 0% threshold in the demo. This happens because when we scroll fast and reach a threshold, by the time the callback can fire to update the text, we have already scrolled in more of the element beyond the threshold.

If we scrolled more slowly the callback would have time to update the text before the element scrolls past the current threshold.

rootMargin

The rootMargin property applies a margin around the viewport or root element. It accepts values that the CSS margin property can accept e.g., 10px 20px 30px 40px (top, right, bottom, left). A margin grows or shrinks the region of the viewport that the Intersection Observer watches for an intersection with the target element.

Here’s an example of using the rootMargin property:

index.js

const observer = new IntersectionObserver(
  (entries) => {
    for (const entry of entries) {
      const intersecting = entry.isIntersecting;
      entry.target.style.backgroundColor = intersecting ? 'blue' : 'black';
    }
  },
  // πŸ‘‡ Root margin 50px from bottom of viewport
  { rootMargin: '50px' }
);

const box = document.getElementById('box');

observer.observe(box);

After setting a rootMargin of 50px, the viewport is effectively increased in height for intersection purposes, and the callback function will be invoked when the element comes within 50px of the viewport.

The red lines in the demo indicate the bounds of the region watched by the Observer for any intersection.

The element changes color when it comes within 50px of the viewport.
The element changes color when it comes within 50px of the viewport.

We can also specify negative margins to shrink the area of the viewport used for the intersection.

const observer = new IntersectionObserver(
  (entries) => {
    for (const entry of entries) {
      const intersecting = entry.isIntersecting;
      entry.target.style.backgroundColor = intersecting ? 'blue' : 'black';
    }
  },
  // πŸ‘‡ Negative margin
  { rootMargin: '-50px' }
);

const box = document.getElementById('box');

observer.observe(box);

Now the callback is fired when a single pixel of the element is more than 50px inside the viewport.

The element changes color when a single pixel of the element is more than 50px inside the viewport.
The element changes color when a single pixel of the element is more than 50px inside the viewport.

root

The root property accepts an element that must be an ancestor of the element being observed. By default, it is null, which means the viewport is used. You won’t need to use this property often, but it is handy when you have a scrollable container on your page that you want to check for intersections with one of its child elements.

For instance, to create the demos in this article, I set the root property to a scrollable container on the page, to make it easy for you to visualize the viewport and the areas outside it and gain a better understanding of how the intersection works.

Second callback parameter

The callback passed to the IntersectionObserver() constructor actually has two parameters. The first parameter is the entries parameter we looked at earlier. The second is simply the Observer that is watching for intersections.

const observer = new IntersectionObserver((entries, o) => {
  console.log(o === observer); // true
});

This parameter is useful for accessing the Observer from within the callback, especially in situations where the callback is in a location where the Observer variable can’t be accessed, e.g., in a different file from the one containing the Observer variable.

Preventing memory leaks

We need to stop observing elements when they no longer need to be observed, like when they are removed from the DOM or after one-time scroll-based animations, to prevent memory leaks or performance issues.

We can do this with the unobserve() method.

new IntersectionObserver((entries, observer) => {
  entries.forEach(entry => {
    if (entry.isIntersecting) {
      doAnim(entry.target);
      observer.unobserve(entry.target);
    }
  });
});

The unobserver() takes a single element as its argument and stops observing that element.

There is also the disconnect() method, which makes the Observer stop observing all elements.

Conclusion

Intersection Observer is a powerful JavaScript API for easily detecting when an element has intersected with the viewport or a parent element. It lets us implement lazy loading, scroll-based animations, infinite scrolling, and more, without causing performance issues and having to use complicated logic.

How to Get the Mouse Position in React

To get the position of the mouse in React, add a mousemove event handler to the window object and access the clientX and clientY properties of the MouseEvent object to get the X and Y coordinates of the mouse respectively.

For example:

App.js

import { useEffect, useState } from 'react';

export default function App() {
  const [mousePos, setMousePos] = useState({});

  useEffect(() => {
    const handleMouseMove = (event) => {
      setMousePos({ x: event.clientX, y: event.clientY });
    };

    window.addEventListener('mousemove', handleMouseMove);

    return () => {
      window.removeEventListener(
        'mousemove',
        handleMouseMove
      );
    };
  }, []);

  return (
    <div>
      The mouse is at position{' '}
      <b>
        ({mousePos.x}, {mousePos.y})
      </b>
    </div>
  );
}
The current mouse position is displayed.
The current mouse position is displayed.

The mousemove event is triggered on an element when the mouse hovers on it. To be more precise, it is fired when the mouse is moved and the hotspot of the cursor is within the bounds of the element.

We attach the event listener to the window object to trigger the event whenever the mouse is moved anywhere in the page.

We passed an empty dependencies array to the useEffect hook because we want to add a handler for the mousemove event only once – when the component mounts.

In the cleanup function, we use the removeEventListener() method to remove the event listener previously added and prevent a memory leak when the component is unmounted.

The mousemove event listener receives a MouseEvent object used to access information and perform actions related to the event. We use the clientX and clientY properties of this object to get the position of the mouse on the X-coordinate and Y-coordinate respectively in the viewport of the application.

Get mouse position relative to element in React

In the previous example we were able to get the mouse position in global coordinates.

In global coordinates position (0,0) is at the top left of the webpage and position (Xmax, Ymax) is at the bottom right.

We might instead want to get the mouse position within the region of an element.

To get the mouse position relative to an element in React, set an onMouseMove event handler on the element, then calculate the local X and Y position using properties of the MouseEvent object passed to the event handler.

For example:

App.js

import { useEffect } from 'react';
import { useState } from 'react';

export default function App() {
  const [globalMousePos, setGlobalMousePos] = useState({});
  const [localMousePos, setLocalMousePos] = useState({});

  const handleMouseMove = (event) => {
    // πŸ‘‡ Get mouse position relative to element
    const localX = event.clientX - event.target.offsetLeft;
    const localY = event.clientY - event.target.offsetTop;

    setLocalMousePos({ x: localX, y: localY });
  };

  useEffect(() => {
    const handleMouseMove = (event) => {
      setGlobalMousePos({
        x: event.clientX,
        y: event.clientY,
      });
    };

    window.addEventListener('mousemove', handleMouseMove);

    return () => {
      window.removeEventListener(
        'mousemove',
        handleMouseMove
      );
    };
  }, []);

  return (
    <div>
      <div
        style={{
          border: '1px solid gray',
          display: 'inline-block',
          padding: '75px',
          textAlign: 'center',
        }}
        onMouseMove={handleMouseMove}
      >
        Local
        <br />
        <b>
          ({localMousePos.x}, {localMousePos.y})
        </b>
      </div>
      <br />
      Global
      <br />
      <b>
        ({globalMousePos.x}, {globalMousePos.y})
      </b>
    </div>
  );
}

Now the resulting X and Y coordinates will be relative to the element. For example, position (0,0) will be at the top left of the element, not the page:

The mouse position relative to the element is shown.
The mouse position relative to the element is shown.

We subtract the offsetLeft property of the element from the clientX property of the MouseEvent object to get the X position relative to the element.

Similarly, to get the Y position, we subtract the offsetTop property of the element from the clientY property of the MouseEvent object.

const handleMouseMove = (event) => {
  // Calculate position within bounds of element
  const localX = event.clientX - event.target.offsetLeft;
  const localY = event.clientY - event.target.offsetTop;

  setLocalMousePos({ x: localX, y: localY });
};

The offsetLeft property returns the number of pixels between the left position of an element and that of its parent.

Likewise, the offsetTop property returns the number of pixels between the top position of an element and that of its parent.

How to Convert JSON to XML in Node.js

We can use the xml-js library to easily convert a JSON string to an XML string in Node.js.

import { json2xml } from 'xml-js';

const jsonObj = {
  name: 'Garage',
  cars: [
    { color: 'red', maxSpeed: 120, age: 2 },
    { color: 'blue', maxSpeed: 100, age: 3 },
    { color: 'green', maxSpeed: 130, age: 2 },
  ],
};

const json = JSON.stringify(jsonObj);

const xml = json2xml(json, { compact: true, spaces: 4 });

console.log(xml);

This code will have the following output:

<name>Garage</name>
<cars>
    <color>red</color>
    <maxSpeed>120</maxSpeed>
    <age>2</age>
</cars>
<cars>
    <color>blue</color>
    <maxSpeed>100</maxSpeed>
    <age>3</age>
</cars>
<cars>
    <color>green</color>
    <maxSpeed>130</maxSpeed>
    <age>2</age>
</cars>

Install xml-js

Before using xml-js, we’ll need to install it in our project. We can do this with the NPM CLI.

npm i xml-js

Or with the Yarn CLI:

yarn add xml-js

After installation, we’ll be able to import it into a JavaScript module, like this:

import { json2xml } from 'xml-js';

We use import destructuring to access the json2xml() method directly from the library.

For a CommonJS module, we’ll import it like this instead:

const { json2xml } = require('xml-js');

The json2xml() function

The json2xml() function from the library has two parameters. The first is the JSON string to convert to XML, and the second is an object.

const xml = json2xml(json, { compact: true, spaces: 4 });

Customize conversion of JSON to XML in Node.js

This object is used to specify various options for customizing the conversion process.

In our example, we set the compact property to true to indicate that the JSON string input is in a compact form.

We set the spaces property to 4 to indent nested XML nodes by 4 spaces. So we can reduce the indentation by setting spaces to 1:

import { json2xml } from 'xml-js';

const jsonObj = {
  name: 'Garage',
  cars: [
    { color: 'red', maxSpeed: 120, age: 2 },
    { color: 'blue', maxSpeed: 100, age: 3 },
    { color: 'green', maxSpeed: 130, age: 2 },
  ],
};

const json = JSON.stringify(jsonObj);

const xml = json2xml(json, { compact: true, spaces: 1 });

console.log(xml);

Now we will have the following XML output:

<name>Garage</name>
<cars>
 <color>red</color>
 <maxSpeed>120</maxSpeed>
 <age>2</age>
</cars>
<cars>
 <color>blue</color>
 <maxSpeed>100</maxSpeed>
 <age>3</age>
</cars>
<cars>
 <color>green</color>
 <maxSpeed>130</maxSpeed>
 <age>2</age>
</cars>

Native conversion of JSON to XML in Node.js

If you don’t want to use any third-party libraries, then you can use this recursive function to convert JSON to XML in Node.js.

function JSONtoXML(obj) {
  let xml = '';
  for (let prop in obj) {
    xml += obj[prop] instanceof Array ? '' : '<' + prop + '>';
    if (obj[prop] instanceof Array) {
      for (let array in obj[prop]) {
        xml += '\n<' + prop + '>\n';
        xml += JSONtoXML(new Object(obj[prop][array]));
        xml += '</' + prop + '>';
      }
    } else if (typeof obj[prop] == 'object') {
      xml += JSONtoXML(new Object(obj[prop]));
    } else {
      xml += obj[prop];
    }
    xml += obj[prop] instanceof Array ? '' : '</' + prop + '>\n';
  }
  xml = xml.replace(/<\/?[0-9]{1,}>/g, '');
  return xml;
}

const jsonObj = {
  name: 'Garage',
  cars: [
    { color: 'red', maxSpeed: 120, age: 2 },
    { color: 'blue', maxSpeed: 100, age: 3 },
    { color: 'green', maxSpeed: 130, age: 2 },
  ],
};

const xml = JSONtoXML(jsonObj);

console.log(xml);

This code will produce the following output:

<name>Garage</name>

<cars>
<color>red</color>
<maxSpeed>120</maxSpeed>
<age>2</age>
</cars>
<cars>
<color>blue</color>
<maxSpeed>100</maxSpeed>
<age>3</age>
</cars>
<cars>
<color>green</color>
<maxSpeed>130</maxSpeed>
<age>2</age>
</cars>

How to Change the Style of an Element on Click in Vue

To change the style of an element on click in Vue:

  1. Create a boolean state variable to conditionally set the style on the element depending on the value of this variable.
  2. Set a click event handler on the element that toggles the value of the state variable.

For example:

App.vue

<template>
  <div id="app">
    <p>Click the button to change its color.</p>

    <button
      role="link"
      @click="handleClick"
      class="btn"
      :style="{
        backgroundColor: active ? 'white' : 'blue',
        color: active ? 'black' : 'white',
      }"
    >
      Click
    </button>
  </div>
</template>

<script>
export default {
  data() {
    return {
      active: false,
    };
  },
  methods: {
    handleClick() {
      this.active = !this.active;
    },
  },
};
</script>

<style>
.btn {
  border: 1px solid gray;
  padding: 8px 16px;
  border-radius: 5px;
  font-family: 'Segoe UI';
  font-weight: bold;
}
</style>
Clicking the element changes its stye.
Clicking the element changes its style.

The active state variable determines the style that will be applied to the element. When it is false (the default), a certain style is applied.

We set a click event handler on the element, so that the handler will get called when it is clicked. The first time this handler is called, the active variable gets toggled to true, which changes the style of the element.

Note

To prevent the style from changing every time the element is clicked, we can set the state variable to true, instead of toggling it:

handleClick() {
  this.active = true

  // this.active = !this.active
},

We used ternary operators to conditionally set the backgroundColor and color style on the element.

The ternary operator works like an if/else statement. It returns the value before the ? if it is truthy. Otherwise, it returns the value to the left of the :.

const treshold = 10;

const num = 11;

const result = num > treshold ? 'Greater' : 'Lesser';

console.log(result) // Greater

So if the active variable is true, the backgroundColor and color are set to white and black respectively. Otherwise, they’re set to blue and white respectively.

Change element style on click with classes

To change the style of an element on click in Vue, we can also create classes containing the alternate styles and conditionally set them to the class prop of the element, depending on the value of the boolean state variable.

For example:

App.vue

<template>
  <div id="app">
    <p>Click the button to change its color.</p>

    <button
      role="link"
      @click="handleClick"
      class="btn"
      :class="active ? 'active' : 'non-active'"
    >
      Click
    </button>
  </div>
</template>

<script>
export default {
  data() {
    return {
      active: false,
    };
  },
  methods: {
    handleClick() {
      this.active = !this.active;
    },
  },
};
</script>

<style>
.btn {
  border: 1px solid gray;
  padding: 8px 16px;
  border-radius: 5px;
  font-family: 'Segoe UI';
  font-weight: bold;
}

.active {
  background-color: white;
  color: black;
}

.non-active {
  background-color: blue;
  color: white;
}
</style>

We create two classes (active and non-active) with different styles, then we use the ternary operator to add the active class if the active variable is true, and add the non-active class if otherwise.

The advantage of using classes is that we get to cleanly separate the styles from the template markup. Also, we only need to use one ternary operator.

Change element style on click with event.currentTarget.classList

There are other ways to change the style of an element in Vue without using a state variable.

With classes defined, we can use the currentTarget.classList property of the Event object passed to the click event handler to change the style of the element.

For example:

App.vue

<template>
  <div id="app">
    <p>Click the button to change its color.</p>

    <button
      role="link"
      @click="handleClick"
      class="btn non-active"
    >
      Click
    </button>
  </div>
</template>

<script>
export default {

  methods: {
    handleClick(event) {
      // πŸ‘‡ Change style
      event.currentTarget.classList.remove('non-active');
      event.currentTarget.classList.add('active');
    },
  },
};
</script>

<style>
.btn {
  border: 1px solid gray;
  padding: 8px 16px;
  font-family: Arial;
  font-size: 1.1em;
  box-shadow: 0 2px 5px #c0c0c0;
}

.active {
  background-color: white;
  color: black;
}

.non-active {
  background-color: rebeccapurple;
  color: white;
}
</style>
Clicking the element changes its style.
Clicking the element changes its style.

We don’t use a state variable this time, so we add the non-active class to the element, to customize its default appearance.

The click event listener receives an Event object used to access information and perform actions related to the click event.

The currentTarget property of this object returns the element that was clicked and had the event listener attached.

We call the classList.remove() method on the element to remove the non-active class, then we call the classList.add() method on it to add the active class.

Notice that the style of the element didn’t change anymore after being clicked once. If you want to toggle the style whenever it is clicked, you can use the toggle() class of the element to alternate the classes on the element.

App.vue

<template>
  <div id="app">
    <p>Click the button to change its color.</p>

    <button
      role="link"
      @click="handleClick"
      class="btn non-active"
    >
      Click
    </button>
  </div>
</template>

<script>
export default {
  methods: {
    handleClick(event) {

      // πŸ‘‡ Alternate classes
      event.currentTarget.classList.toggle('non-active');
      event.currentTarget.classList.toggle('active');
    },
  },
};
</script>

<style>
.btn {
  border: 1px solid gray;
  padding: 8px 16px;
  font-family: Arial;
  font-size: 1.1em;
  box-shadow: 0 2px 5px #c0c0c0;
}

.active {
  background-color: white;
  color: black;
}

.non-active {
  background-color: rebeccapurple;
  color: white;
}
</style>
Clicking the element toggles its color.
Clicking the element toggles its color.

The classList.toggle() method removes a class from an element if it is present. Otherwise, it adds the class to the element.

How to Fix the “Cannot read property ‘addEventListener’ of null” Error in JavaScript

The “cannot read property ‘addEventListener’ of null” error occurs in JavaScript when you try to call the addEventListener() method on an element that cannot be found in the DOM. This happens for two main reasons:

  1. Accessing the addEventListener() method on an element absent from the DOM.
  2. Inserting the script tag referencing the JavaScript file at a point above the declaration of the DOM element in the HTML.

We’ll learn how to handle the error for these two scenarios in this article.

The "cannot read property 'addEventListener' of null" error occurring in JavaScript.

Cause 1: Accessing addEventListener() on an element not present in the DOM

index.js

const btn = document.getElementById('does-not-exist');

console.log(btn); // null

// ❌ Cannot read property 'addEventListener' of null
btn.addEventListener('click', () => {
  alert('You clicked the button');
});

When a method like getElementById() or querySelector() method is used to search for an element that doesn’t exist in the DOM, it returns null. And attempting to call the addEventListener() method on a null value will cause the error.

Solve: Ensure correct selector

To fix the “cannot read property ‘addEventListener’ of null” error, make sure the selector used the access the element is properly defined. Ensure that there are no mistakes in the ID or class name, and the correct symbols are used.

Solve: Check for null

To fix the “cannot read property ‘addEventListener’ of null” error, check that the element is not null before calling the addEventListener() method on it.

We can do this with an if statement:

const btn = document.getElementById('does-not-exist');

console.log(btn); // null

// βœ… Check if element exists before calling addEventListener()
if (btn) {
  // Not called
  btn.addEventListener('click', () => {
    alert('You clicked the button');
  });
}

When a value is placed in between the brackets of an if statement, it is coerced to a Boolean before being evaluated, i.e., truthy values become true, and falsy values become false. null is a falsy value, so it is coerced to false and the code in the if statement block is never run.

Note: In JavaScript, there are six falsy values: undefined, null, NaN, 0, '' (empty string) and false. Every other value is truthy.

We can also use the optional chaining operator (?.) to check if the element is null.

const btn = document.getElementById('does-not-exist');

console.log(btn); // null

// βœ… Check if element exists before calling addEventListener()

// Not called
btn?.addEventListener('click', () => {
  alert('You clicked the button');
});

The optional chaining operator (?.) is null-safe way of accessing a property or calling a method of an object. If the object is nullish (null or undefined), the operator prevents the member access and returns undefined instead of throwing an error.

Cause 2: Inserting the script tag above the DOM element

Another common cause of this error is placing the <script> tag referencing the JavaScript file at a point above where the target element is declared.

For example, in this HTML markup:

index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>Coding Beauty Tutorial</title>
    <!-- ❌ Script is run before button is declared -->
    <script src="index.js"></script>
  </head>
  <body>
    <button id="btn">Sign up</button>
  </body>
</html>

the script tag is placed in the head tag, above where the button element is declared, so the index.js file will not be able to access the button element.

index.js

const btn = document.getElementById('btn');

console.log(btn); // null

// ❌ TypeError: Cannot read properties of null
btn.addEventListener('click', () => {
  alert('You clicked the button');
});

Solve: Move script tag to bottom of body

To fix the error in this case, move the script tag to the bottom of the body, after all the HTML elements have been declared.

index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>Coding Beauty Tutorial</title>
  </head>
  <body>
    <button id="btn">Sign up</button>

    <!-- βœ… Script is run after button is declared -->
    <script src="index.js"></script>
  </body>
</html>

Now the index.js script file will have access to the button element and all the other HTML elements, because they would have already been declared when the script is run.

index.js

const btn = document.getElementById('btn');

console.log(btn); // HTMLButtonElement object

// βœ… Works as expected
btn.addEventListener('click', () => {
  alert('You clicked the button');
});

Solve: Access element in DOMContentLoaded event listener

Another way to fix the “cannot read property ‘addEventListener’ of null” error in JavaScript is to add a DOMContentLoaded event listener to the document, and access the element in this listener. With this approach it won’t matter where we place the script in the HTML.

index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>Coding Beauty Tutorial</title>

    <!-- Script placed above element accessed -->
    <script src="index.js"></script>
  </head>
  <body>
    <button id="btn">Sign up</button>
  </body>
</html>

The DOMContentLoaded event is fired when the browser has fully loaded the HTML, and the DOM tree has been built, but external resources like images and stylesheets may not have loaded. So regardless of where we place the script, the code in the listener is only called after all the declared HTML elements have been added to the DOM.

index.js

document.addEventListener('DOMContentLoaded', () => {
  const btn = document.getElementById('btn');

  console.log(btn); // HTMLButtonElement object

  // βœ… Works as expected
  btn.addEventListener('click', () => {
    alert('You clicked the button');
  });
});

Conclusion

We can fix the “cannot read property addEventListener’ of null” error in JavaScript by ensuring that the correct selector is defined, adding a null check to the element before calling addEventListener(), moving the script tag to the bottom of the body, or accessing the element in a DOMContentLoaded event listener added to the document.

How to Open a Link in a New Tab in Vue

To open a link in a new tab in Vue, create an anchor (<a>) element and set its target attribute to _blank, e.g., <a href="https://wp.codingbeautydev.com" target="_blank"></a>. The _blank value specifies that the link should be opened in a new tab.

App.vue

<template>
  <div id="app">
    <a
      href="https://wp.codingbeautydev.com"
      target="_blank"
      rel="noreferrer"
    >
      Coding Beauty
    </a>

    <br /><br />

    <a
      href="https://wp.codingbeautydev.com/blog"
      target="_blank"
      rel="noreferrer"
    >
      Coding Beauty Blog
    </a>
  </div>
</template>

The target property of the anchor element specifies where to open the linked document. By default target has a value of _self, which makes the linked page open in the same frame or tab where it was clicked. To make the page open in a new tab, we set target to _blank.

We also set the rel prop to noreferrer for security purposes. It prevents the opened page from gaining any information about the page that it was opened from.

The link is opened in a new tab.
The link is opened in a new tab.

Sometimes we’ll prefer a button instead of a link to open the new tab when clicked.

To open a link in a new tab on button click, create a button element and set an click event listener that calls the window.open() method.

App.vue

<template>
  <div id="app">
    <p>
      Click this button to visit Coding Beauty in a new tab
    </p>

    <button
      role="link"
      @click="openInNewTab('https://wp.codingbeautydev.com')"
    >
      Click
    </button>
  </div>
</template>

<script>
export default {
  methods: {
    openInNewTab(url) {
      window.open(url, '_blank', 'noreferrer');
    },
  },
};
</script>
The link is opened when the button is clicked.
The link is opened when the button is clicked.

We use the open() method of the window object to programmatically open a link in a new tab. This method has three optional parameters:

  1. url: The URL of the page to open in a new tab.
  2. target: like the target attribute of the <a> element, this parameter’s value specifies where to open the linked document, i.e., the browsing context. It accepts all the values the target attribute of the <a> element accepts.
  3. windowFeatures: A comma-separated list of feature options for the window. noreferrer is one of these options.

Passing _blank to the target parameter makes the link get opened in a new tab.

When the button is clicked, the event listener is called, which in turn calls window.open(), which opens the specified link in a new tab.

How to Remove Special Characters From a String in JavaScript

To remove all special characters from a string, call the replace() method on the string, passing a whitelisting regex and an empty string as arguments, i.e., str.replace(/^a-zA-Z0-9 ]/g, ''). The replace() method will return a new string that doesn’t contain any special characters.

For example:

const str = 'milk and @#$%&!bread';

const noSpecialChars = str.replace(/[^a-zA-Z0-9 ]/g, '');

console.log(noSpecialChars); // milk and bread

The String replace() method searches a string for a value (substring or regular expression), and returns a new string with the value replaced by a substring. It doesn’t modify the original string.

The square brackets in the regular expression ([]) indicates a character class. Only characters that are enclosed in it will be matched.

But after placing the caret (^) as the first character in the square bracket, only characters that are not enclosed in the square bracket will be matched.

After the caret, we specify:

  • ranges for lowercase (a-z) and uppercase (A-Z) letters.
  • a range for digits from 0-9.
  • a space character (' ').

So the regex matches any character is not a lowercase or uppercase letter, digit or space, and the replace() method returns a new string with all of these characters removed from the original string.

The g (global) flag specifies that every occurrence of the pattern should be matched.

If we don’t pass a global flag, only the first special character in the string will be matched and removed.

const str = 'milk and @#$%&!bread';

// πŸ‘‡ No 'g' flag in regex
const noSpecialChars = str.replace(/[^a-zA-Z0-9 ]/, '');

// πŸ‘‡ Only first special character removed
console.log(noSpecialChars); // milk and #$%&!bread

Shorten regular expression with \w character.

We can shorten this regular expression a bit with the \w character.

const str = 'milk and @#$%&!bread';

const noSpecialChars = str.replace(/[^\w ]/g, '');

console.log(noSpecialChars); // milk and bread

The \w character matches uppercase and lowercase Latin letters, digits, and underscores.

Since \w matches underscores, it can’t be used on its own to remove this special character from a string.

const str = '_milk_ _and _@#$%&!_bread_';

const noSpecialChars = str.replace(/[^\w ]/g, '');

console.log(noSpecialChars); // _milk_ _and_ _bread_

We’ll need a different regex to remove the underscores:

const str = '_milk_ _and _@#$%&!_bread_';

const noSpecialChars = str.replace(/([^\w ]|_)/g, '');

console.log(noSpecialChars); // milk and bread

The pipe symbol (|) allows either of two patterns to be matched in a string, similar to a character class. To use the pipe symbol we need to wrap the two patterns in parentheses (( and )), which is what we did.