Change class onclick anyplace on document to close a menu? - javascript

I use this code which opens and closes a menu. How can I have it close when someone clicks anyplace on the screen?
function showElement(layer){
var myLayer = document.getElementById(layer);
if(myLayer.style.display=="none"){
myLayer.style.display="block";
myLayer.backgroundPosition="top";
} else {
myLayer.style.display="none";
}
}
The HTML
<div style="float:left;">
<a href="#" class="button" onclick="javascript:showElement('v-menu')">
<span>Monitoring</span></a>
<ul id="v-menu" class="v-menu" style="display:none;" >
<li>Start</li>
<li>Stop</li>
</div>

You will need to do two things to achieve this:
Bind a click event for the whole document, and hide the menu if it is shown.
document.addEventListener("click", function(event) {
var menu = document.getElementById('v-menu');
if (event.target !== menu && menu.style.display == 'block')
menu.style.display = "none";
});
Stop the click event propagation when the menu is clicked, so the event does not bubble up to the document.
<a href="javascript:void(0)" class="button"
onclick="showElement('v-menu'); event.stopPropagation()">
See this in action: http://jsfiddle.net/william/Pfv8N/.

You can attach an event on document.body and in the handler you can write your code to
hide the menu like this
document.body.addEventListener("click", function(){
//conditions to check if click is not on ur menu
showElement();
}, false);

Related

Why does my jQuery open and close my pop up before clicking the body?

I have a pop up that opens up so users can reply to messages. now when a user clicks <a> tag it opens the popup, but it doesn't close if they hit anywhere in the body. I tried fixing this by using jquery but it keeps opening and then closing the pop up again immediately after clicking on the <a> tag.
My <a> tag:
<a class="msg-icon2" onclick="openReplyModal(<?php echo $msg_id ; ?>)">
<i class="fas fa-reply"></i>
</a>
My jquery:
var msg_id;
function openReplyModal(id) {
msg_id = id
$("#reply_modal" + msg_id).fadeIn();
jQuery(document).ready(function($) {
jQuery("body").click(function() {
$("#reply_modal" + msg_id).fadeOut();
});
});
}
How can I adjust my code so that when the user clicks the button for the first time it would open the popup and stay opened unless he clicks anywhere in the body?
here is the code i got from the answer below:
`function openReplyModal(id, event) {
$(".modal").hide(); // close other modal
msg_id = id
$("#reply_modal" + msg_id).fadeIn();
event.preventDefault();
event.stopPropagation();
}
jQuery(document).ready(function($) {
// click on modal doesn't hide itself
$("body").on("click", ".modal", function(e) {
e.stopPropagation();
});
// clicl anywhere else hides all modals
$(window).click(function() {
$(".modal").fadeOut();
});
});`
Give all your modals a common class, such as class="reply_modal". Then you can have a general click handler that fades them all out when you click on the body.
The reason that the modal closes immediately is that the click event bubbles out from the <a> to the body, so it closes the modal. I added event.stopPropagation() to the function so it won't bubble out.
Use $(window).click() to detect clicks anywhere in the window outside the element. See How do I detect a click outside an element?.
var msg_id;
function openReplyModal(id, event) {
$(".reply_modal").hide(); // close other modal
msg_id = id
$("#reply_modal" + msg_id).fadeIn();
event.preventDefault();
event.stopPropagation();
}
jQuery(document).ready(function($) {
// click on modal doesn't hide itself
$("body").on("click", ".reply_modal", function(e) {
e.stopPropagation();
});
// clicl anywhere else hides all modals
$(window).click(function() {
$(".reply_modal").fadeOut();
});
});
.reply_modal {
display: none;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<a class="msg-icon2" onclick="openReplyModal(1, event)" href="#"> <i class="fas fa-reply">open 1</i></a>
<a class="msg-icon2" onclick="openReplyModal(2, event)" href="#"> <i class="fas fa-reply">open 2</i></a>
<div id="reply_modal1" class="reply_modal">This is modal 1<br>
<input></div>
<div id="reply_modal2" class="reply_modal">This is modal 2<br>
<input></div>
jQuery(document).ready(function ($) {
function openReplyModal(id) {
msg_id = id
$("#reply_modal" + msg_id).addClass('model-open').fadeIn();
}
$('body').click(function (e) {
$('.model-open').removeClass('open').fadeOut();
});
});

Use jQuery to click anywhere and remove 'active' class

I'm having some trouble figuring out how to close a div by clicking anywhere on the screen.
I'm currently toggling an 'active' class in order to display a drop down div, then attempting to remove that class by clicking on the body:
$(document).ready(function () {
$('.navbar a').click(function () {
$(this).next('.navbar-dropdown').toggleClass('active');
});
$(body).click(function() {
if($('.navbar-dropdown').hasClass('active')){
$('.navbar-dropdown').removeClass('active');
}
});
});
<ul class="navbar">
<li>
Link
<div class="navbar-dropdown">
Dropdown Content
</div>
</li>
</ul>
However they are conflicting with each other, so as soon as the class is toggled on, the 'body' click toggles it off at the same time. Have spent some time looking on here and came across this method a few times:
$(document.body).click( function() {
closeMenu();
});
$(".dialog").click( function(e) {
e.stopPropagation();
});
However any attempts to configure this to work correctly seemed to fall on deaf ears!
The click event from the navbar is bubbling up to the body, so both events fire. stopPropagation() is one way to prevent that, but you need to do it in the navbar link's event handler, so it stops that particular event; not in a separate event handler as you had it.
Another change you might consider making is to only assign the body click handler when you need it, instead of firing all the time -- create that handler inside the navbar's click handler, and deactivate it again when it's used:
$(document).ready(function() {
$('.navbar a').click(function(e) {
var myDropdown = $(this).next('.navbar-dropdown');
$('.navbar-dropdown.active').not(myDropdown).removeClass('active'); // close any other open dropdowns
myDropdown.toggleClass('active'); // open this one
$('body').click(function() {
// no need for an if statement here, just use a selector that matches the active elements:
$('.navbar-dropdown.active').removeClass('active');
$('body').off('click'); // cancel the body's click handler when it's used
});
e.stopPropagation(); // prevent the navbar event from bubbling up to the body
});
});
.active {
color: red
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<ul class="navbar">
<li>
Link
<div class="navbar-dropdown">
Dropdown Content
</div>
</li>
<li>
Link 2
<div class="navbar-dropdown">
Dropdown Content 2
</div>
</li>
<li>
Link 3
<div class="navbar-dropdown">
Dropdown Content 3
</div>
</li>
</ul>
(If there's a chance you might need more than one separate click event handler on the body, you can namespace the event so you can control which one you're turning off:
$('body').on("click.myNamespace", function() {
// do other stuff
$('body').off("click.myNamespace")
})
I did the exact thing as you and it works for me. Are you sure you don't have any other event listeners attached? Or maybe a z-index on the menu bringing it underneath other elements?
$(document).click(function(e) {
$(".dialog").text('closed')
});
$(".dialog").click(function(e) {
e.target.innerText = 'open';
e.stopPropagation();
});
.dialog {
width: 200px;
height: 200px;
background: antiquewhite;
text-align: center;
}
<html>
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
</head>
<body>
<div class="dialog">open</div>
</body>
</html>

hide a div when clicking outside 2 div jquery

i have a problem with js
i have a icon and a form
my form is appear when i click on icon
i want to my form was hide when clicked outside form
now when i click on icon to show my form , js hide my form becuase it outside of my form
any body can help me?
mycode for show/hide when click on icon:
$(document).ready(function(){
$("#icon").click(function(){
$("#form-subscribe").animate({
height: 'toggle'
});
});
});
and my code for hide form when clicked outside of form:
$(document).ready(function()
{
$("#main").mouseup(function(e)
{
var subject = $("#form-subscribe");
if(e.target.id != subject.attr('id') && !subject.has(e.target).length)
{
$("#form-subscribe").animate({
height: 'hide'
});
}
});
});
You can accomplish this by inspecting the e.target DOM node inside of a jQuery $.contains() method.
Link to jQuery Contains Method: https://api.jquery.com/jQuery.contains/
Here is a JSFiddle: https://jsfiddle.net/iamjpg/eq43eve5/
HTML:
<div>
<i class="fa fa-plus" aria-hidden="true"></i>
</div>
<form id="form">
<div>
<input>
</div>
<div>
<input>
</div>
<div>
<input>
</div>
</form>
Javascript:
$('.fa').on('click', function() {
$('#form').show();
})
$(document).on('click', function(e) {
// If e.target is not inside of the form container AND not
// the icon triggering the initial showing of the form,
// hide the form div.
if (!$.contains(document.querySelector('#form'), e.target) && !$(e.target).hasClass('fa')) {
$('#form').hide();
}
})

Close menu on overlay click requires double click instead of single click

I have a slide out menu that I want to close when the user clicks on the overlay. The menu closes but to open it again I have to click the toggle twice instead of once, where I'm I going wrong?Thanks. A sample page demonstrating this slideoutMenu
function expandOverlay() {
var overlay = document.createElement("div");
overlay.setAttribute("id", "overlay04");
overlay.setAttribute("class", "overlay04");
document.body.appendChild(overlay);
}
function restore() {
document.body.removeChild(document.getElementById("overlay04"));
}
// create menu variables
var slideoutMenu = $('.slideout-menu');
var slideoutMenuWidth = $('.slideout-menu').width();
$(document).ready(function() {
$('.slideout-menu-toggle').on('click', function(event) {
event.preventDefault();
// toggle open class
slideoutMenu.toggleClass("open");
// slide menu
if (slideoutMenu.hasClass("open")) {
slideoutMenu.animate({
left: "0px"
});
expandOverlay();
} else {
slideoutMenu.animate({
left: -slideoutMenuWidth
}, 250);
restore();
}
});
});
window.addEventListener('mouseup', function(event) {
var box = document.getElementById('menu_s');
if (event.target != box && event.target.parentNode != box) {
slideoutMenu.animate({
left: -slideoutMenuWidth
}, 250);
restore();
}
});
<nav>
<ul>
<li>open menu</li>
</ul>
</nav>
<!--begin slideout menu-->
<div id="menu_s" class="slideout-menu">
<h3>Last Week×</h3>
<div class="fslide"></div>
<ul>
<li>Dundaah</li>
<li>Pics</li>
<li>Blog</li>
<li>Music</li>
</ul>
</div>
I believe the problem here is that the class open is still on toggleMenu after the overlay is clicked.
Therefore, if you were to click open menu after closing, the click event would remove the open class from toggleMenu, resulting in the else part of the if statement being executed (which is to close the menu).
This is why 2 clicks are needed before the menu will be open if it was closed by clicking the overlay.
You could possibly try to toggleClass("open") when closing the menu by clicking on the overlay.

Hide a div on click but do nothing when click on image which is inside

I have a div main-wrap and an image in it.
I want to hide main-wrap when click on it. But when you click on image that is inside main-wrap I don't want to do anything. Right now I have this non-working code. When I click on image main-wrap still hides. (hidden is my class .hidden {display:none})
<div class="main-wrap" >
<div class="photo-wrap">
<img style="cursor:default;" onclick = "return false;" class="img img-responsive" src = "/stat_photo/1.jpg"/>
</div>
</div>
And I have this code
$(document).ready(function() {
$('.main-wrap').click(function(){$('.main-wrap').addClass('hidden')});
});
I ended up with this code
$('.main-wrap').on('click', function(e) {
$('.main-wrap').addClass('hidden');
}).on('click', 'img', function(e) {
// clicked on descendant div
e.stopPropagation();
});
which is taken from here
How to have click event ONLY fire on parent DIV, not children?
(the accepted answer didn't work though)
$('.main-wrap').click(function(e) {
$(this).addClass('hidden');
}).on('click', 'img', function(e) {
return false;
});
https://jsfiddle.net/bfwsqxko/1/
I added a click event, which extends with an exceptional click on image, which is set to return false;
Better add an id of the image. Then replace .img with #yourid
$(document).ready(function() {
$('.main-wrap').not('.img').click(function(){$('.main-wrap').addClass('hidden')});
});

Categories