5120bee
5120bee

Reputation: 709

How To Prevent Drop Down Menu From Closing When User Clicks Into It?

I followed a tutorial on W3Schools website about making a dropdown menu from a button. Everything works fine EXCEPT that when the user clicks inside the dropdown menu the menu itself disappears.

I wanted to make a LOGIN button where the user clicks on the button, it displays a dropdown menu where he/she can input his/her username and password and click Login.

I want to keep the feature where if the user clicks any other area outside the drop down menu, it would automatically close the drop down menu.

My problem is that the dropdown menu disappears when the user clicks any area inside it. How do I prevent it from disappearing while clicking inside the drop down menu using only JavaScript? What about using jQuery (I'm not really familiar with jQuery yet)

/* When the user clicks on the button, 
toggle between hiding and showing the dropdown content */
function myFunction() {
    document.getElementById("myDropdown").classList.toggle("show");
}

// Close the dropdown menu if the user clicks outside of it
window.onclick = function(event) {
  if (!event.target.matches('.dropbtn')) {

    var dropdowns = document.getElementsByClassName("dropdown-content");
    var i;
    for (i = 0; i < dropdowns.length; i++) {
      var openDropdown = dropdowns[i];
      if (openDropdown.classList.contains('show')) {
        openDropdown.classList.remove('show');
      }
    }
  }
}
/* Dropdown Button */
.dropbtn {
    background-color: #4CAF50;
    color: white;
    padding: 16px;
    font-size: 16px;
    border: none;
    cursor: pointer;
}

/* Dropdown button on hover & focus */
.dropbtn:hover, .dropbtn:focus {
    background-color: #3e8e41;
}

/* The container <div> - needed to position the dropdown content */
.dropdown {
    position: relative;
    display: inline-block;
}

/* Dropdown Content (Hidden by Default) */
.dropdown-content {
    display: none;
    position: absolute;
    background-color: #f9f9f9;
    min-width: 160px;
    box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
}

/* Contents inside the dropdown */
.dropdown-content input, .dropdown-content button {
    color: black;
    padding: 12px 16px;
    text-decoration: none;
    display: block;
}

/* Change color of dropdown links on hover */
.dropdown-content a:hover {background-color: #f1f1f1}

/* Show the dropdown menu (use JS to add this class to the .dropdown-content container when the user clicks on the dropdown button) */
.show {display:block;}
<div class="dropdown">
  <button onclick="myFunction()" class="dropbtn">LOG IN</button>
  <div id="myDropdown" class="dropdown-content">
    <input type="text" name="username" placeholder="Enter username"/>
    <input type="text" name="password" placeholder="Enter password"/>
    <button type="submit" name="submit">Submit</button>
  </div>
</div>

Upvotes: 0

Views: 1954

Answers (2)

Praveen Kumar T
Praveen Kumar T

Reputation: 84

When you click inside dropdown, you should not remove show class

/* When the user clicks on the button, 
toggle between hiding and showing the dropdown content */
function myFunction() {
    document.getElementById("myDropdown").classList.toggle("show");
}

// Close the dropdown menu if the user clicks outside of it
window.onclick = function(event) {
   
  if (event.target.matches('.dropdown-content *')) {
    return;
   } 

  if (!event.target.matches('.dropbtn')) {

    var dropdowns = document.getElementsByClassName("dropdown-content");
    var i;
    for (i = 0; i < dropdowns.length; i++) {
      var openDropdown = dropdowns[i];
      if (openDropdown.classList.contains('show')) {
        openDropdown.classList.remove('show');
      }
    }
  }
}
/* Dropdown Button */
.dropbtn {
    background-color: #4CAF50;
    color: white;
    padding: 16px;
    font-size: 16px;
    border: none;
    cursor: pointer;
}

/* Dropdown button on hover & focus */
.dropbtn:hover, .dropbtn:focus {
    background-color: #3e8e41;
}

/* The container <div> - needed to position the dropdown content */
.dropdown {
    position: relative;
    display: inline-block;
}

/* Dropdown Content (Hidden by Default) */
.dropdown-content {
    display: none;
    position: absolute;
    background-color: #f9f9f9;
    min-width: 160px;
    box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
}

/* Contents inside the dropdown */
.dropdown-content input, .dropdown-content button {
    color: black;
    padding: 12px 16px;
    text-decoration: none;
    display: block;
}

/* Change color of dropdown links on hover */
.dropdown-content a:hover {background-color: #f1f1f1}

/* Show the dropdown menu (use JS to add this class to the .dropdown-content container when the user clicks on the dropdown button) */
.show {display:block;}
<div class="dropdown">
  <button onclick="myFunction()" class="dropbtn">LOG IN</button>
  <div id="myDropdown" class="dropdown-content">
    <input type="text" class="form-input" name="username" placeholder="Enter username"/>
    <input type="text" class="form-input" name="password" placeholder="Enter password"/>
    <button type="submit" name="submit">Submit</button>
  </div>
</div>

Upvotes: 1

Khoa
Khoa

Reputation: 2932

On window.onClick handler, we add a condition to exclude "dropdown content" and its children.

/* When the user clicks on the button, 
toggle between hiding and showing the dropdown content */
function myFunction() {
    document.getElementById("myDropdown").classList.toggle("show");
}

// Close the dropdown menu if the user clicks outside of it
window.onclick = function(event) {
  if (!event.target.matches('.dropbtn')) {
    // [BEGIN][Here is the condition]
    if (event.target.matches('.dropdown-content') || event.target.matches('.dropdown-content *') ) {
       event.stopPropagation();
       return;
    }
  // [END][Here is the condition]
    var dropdowns = document.getElementsByClassName("dropdown-content");
    var i;
    for (i = 0; i < dropdowns.length; i++) {
      var openDropdown = dropdowns[i];
      if (openDropdown.classList.contains('show')) {
        openDropdown.classList.remove('show');
      }
    }
  }
}
/* Dropdown Button */
.dropbtn {
    background-color: #4CAF50;
    color: white;
    padding: 16px;
    font-size: 16px;
    border: none;
    cursor: pointer;
}

/* Dropdown button on hover & focus */
.dropbtn:hover, .dropbtn:focus {
    background-color: #3e8e41;
}

/* The container <div> - needed to position the dropdown content */
.dropdown {
    position: relative;
    display: inline-block;
}

/* Dropdown Content (Hidden by Default) */
.dropdown-content {
    display: none;
    position: absolute;
    background-color: #f9f9f9;
    min-width: 160px;
    box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
}

/* Contents inside the dropdown */
.dropdown-content input, .dropdown-content button {
    color: black;
    padding: 12px 16px;
    text-decoration: none;
    display: block;
}

/* Change color of dropdown links on hover */
.dropdown-content a:hover {background-color: #f1f1f1}

/* Show the dropdown menu (use JS to add this class to the .dropdown-content container when the user clicks on the dropdown button) */
.show {display:block;}
<div class="dropdown">
  <button onclick="myFunction()" class="dropbtn">LOG IN</button>
  <div id="myDropdown" class="dropdown-content">
    <input type="text" name="username" placeholder="Enter username"/>
    <input type="text" name="password" placeholder="Enter password"/>
    <button type="submit" name="submit">Submit</button>
  </div>
</div>

Upvotes: 2

Related Questions