Allow only one tab to be open at a time

I am currently writing a tab-box in vanilla JavaScript where pressing buttons toggles open text content. This has been easy enough. I want to close any other open boxes when so only one is opened at a time. I am finding this really hard.
The working code I have is:

function openDrawer() {

  if ( == "block") { = "none"
  else if ( == "none") { = "block"

I am already using a forEach to iterate over all the buttons to add a click event listener.

buttons.forEach(function(button) {
  button.addEventListener("click", openDrawer)

I thought of using a forEach inside the forEach to iterate over the same elements again and check whether they were ‘this’ or not but this feels wrong?

The usual technique for this is a two-step process.

First close all of the tabs.
Then, when all of them are closed, open up only the one that is required.

1 Like

Hi Paul. I’m trying that at the moment.
When I look at the html in the devtools I see the display property is momentarily going to display: block then right back to display none, in a flash of a microsecond :frowning:
(this is a reduced test case on codepen. My problem is on mobile-only as their is different behaviour on desktop, but I removed that code for this test case)

Here is your code for the openDrawer

button.addEventListener("click", openDrawer);
button.addEventListener("focus", openDrawer);

I don’t see anything in the JavaScript that’s creating the button variable.

Sorry, i had updated that but forgot to press the save button :s The code should be there now

What is the problem that I should on my mobile be looking at?

Currently my mobile shows one tap to select, then another tap to open, with another tap to close the tab.

Tabbing through on desktop (with window made narrow so that i get the mobile view) : works fine.
Touching to open on an actual mobile device: works fine.
Clicking with a mouse on a narrow screen size: starts to open tab, then closes it again :s

First the focus event fires, and then the click event fires.
You may want to use a debounce technique on the tabs so that it only fires once.

You can get a good debounce function from 7 Essential JavaScript Functions and use it like this:

var openDrawerHandler = debounce(openDrawer, 100);
buttons.forEach(function (button) {
  button.addEventListener("click", openDrawerHandler);
  button.addEventListener("focus", openDrawerHandler)

So it will only trigger when 100 milliseconds have passed without it being called again.

Thank you :smiley:

That makes a lot of sense but I never would have thought of it!
Everything works perfectly now :sunny:

1 Like

This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.