How to properly hide selected dropdown? - javascript

I'm trying to achieve something similar to the bootstrap button drop downs (http://twitter.github.io/bootstrap/components.html#buttonDropdowns) but need something lightweight. Basic functionality is more or less this:
On clicking the link, corresponding dropdown div opens (works)
On clicking another link, the previous dropdown closes as well as the css class is removed (works)
On clicking on the link of the opened dropdown, close the dropdown (does not work (closes and reopens))
On clicking anywhere in the body (so outside the link and dropdown), close the dropdown (does not work)
What should be the logic behind this?
Demo: http://jsfiddle.net/fU2BZ/
Does the code below make sense?
$(document).click( function(){
$('.dropdownbox').hide(0);
$('.dropdown').removeClass('active');
});
$('.dropdown').click( function(event){
event.stopPropagation();
$('.dropdown').removeClass('active');
$('.dropdownbox').hide();
$(this).addClass('active').find('.dropdownbox').slideToggle(200);
});

Made some changes to your code, added some if else logic, seems to work.
fiddle: http://jsfiddle.net/fU2BZ/1/
Code:
$('.dropdown').click( function(event){
event.stopPropagation();
if ($(this).hasClass("active")) {
$('.dropdown').removeClass('active');
$('.dropdownbox').hide();
} else {
$('.dropdownbox').hide();
$(this).addClass('active').find('.dropdownbox').slideToggle(200);
}
});

You were pretty close. I'd store a flag if it was visible (so that you don't double-up on the same code)
$('.dropdown').click( function(event){
event.stopPropagation();
var active = false;
if ( $(this).hasClass('active') )
active = true;
$('.dropdown').removeClass('active');
$('.dropdownbox').hide();
if ( ! active )
$(this).addClass('active').find('.dropdownbox').slideToggle(200);
});
jsFiddle: http://jsfiddle.net/fU2BZ/4/

Simple code to resolve your third issue:
$('.dropdown').click(function (event) {
event.stopPropagation();
$('.dropdown').removeClass('active').not(this).find('.dropdownbox').hide();
$(this).toggleClass('active').find('.dropdownbox').slideToggle(200);
});
To resolve your last issue, do this:
$('.dropdownbox').click(function (event) {
event.stopPropagation();
});

Related

automatic close function for selection

I have a button which creates a pulldown in which you can select several categories.
Now i want this to close automatically when i click outside the pulldown.
Something like a lightbox or modal popup which closes if you click anywhere else on the page.
Now i have to click the button again to close it. If i dont and go elsewhere on the page, the dropdown stays visible (until i click it)
This is the code of the button:
$(function(){
$('#browse-btn').click(function(){
$('#browse-content').toggle('1000');
$(this).toggleClass('active');
if ($(this).hasClass('active')) $(this).find('span').html('▲')
else $(this).find('span').html('▼')
});
$(".scroll-top").scrollToTop();
$("#category_id").selectbox();
});
Is this possible?
thanks
Using jquery this is the code I used for a similar case scenario sometime ago:
$(document).click(function(event) {
if(!$(event.target).closest('.pulldown').length) {
if($('.pulldown').is(":visible")) {
$('.pulldown').slideUp()
}
}
})
You can read more about this in the original post How to detect a click outside an element? submitted by Art.
I'm not exactly sure of the elements you want to hide as you don't have a demo, so I cannot provide a fully working code, however you should do something like this:
$("body").click(function(event) {
if (event.target.id != "browse-btn") {
// Do something when there's a click outside of #browse-btn
// and the element you want to hide is currently visible
}
});
You can attach a click event to all chidren of the body tag that removes that active class, but you would want to make sure to unbind that event so it doesn't run every time a click takes place that doesn't have some sort of prevent default on it. Something like this:
$(function(){
var hidePulldown = function(){
$('#browse-btn').removeClass('active');
$('body *').unbind("click", hidePulldown);
}
$('#browse-btn').click(function(){
$('#browse-content').toggle('1000');
$(this).toggleClass('active');
if ($(this).hasClass('active')) $(this).find('span').html('▲')
else {
$(this).find('span').html('▼');
$(document).on('click', 'body *', hidePulldown);
}
});
$(".scroll-top").scrollToTop();
$("#category_id").selectbox();
});
Also, the
$(document).on('click', element, function(){function body})
is the preferred way to attach click events i believe: $(document).on('click', '#id', function() {}) vs $('#id').on('click', function(){})
This is what worked flawlessly for me after reading some of the answers here:
$(document).click(function(event) {
if(!$(event.target).closest('#menucontainer').length &&
!$(event.target).is('#menucontainer')) {
if($('#menucontainer').is(":visible")) {
$('#menucontainer').hide();
}
}
})
Thanks for pointing me in the right way!

jQuery if body hasClass then sidemenu toggleClass issue

What I'm trying to achieve is toggling the sidemenu on click anywhere in the body except inside sidemenu div itself. I currently can toggle the sidemenu from its toggle link (comment out line 13-14 in js fiddle) but not by clicking anywhere on body. This is the concerned code:
$('body').bind('click', function (e) {
var opened = $('body').hasClass('sidemenu-open');
if (opened === true) {
$('.sidemenu').removeClass('is-visible');
$('body').removeClass('sidemenu-open');
}
});
JSFIDDLE
I know I can add a wrapper for the content but I don't have much flexibility in the HTML structure.
There are two problems. First, when you click on the link, the click is bubbling out to the body. So the menu toggles open, then it toggles closed again, so nothing happens. Use event.stopPropagation() to prevent that.
Second, when the side menu is closed, <body> is just the one line containing the link. If you want to be able to click anywhere in the window, use $(document) rather than $('body').
$(function () {
$('.sidemenu-toggle').on('click', function (event) {
event.preventDefault();
event.stopPropagation();
$('.sidemenu').toggleClass('is-visible');
$('body.sidemenu-enabled').toggleClass('sidemenu-open');
$('.sidemenu').toggleClass('sidemenu-open');
});
});
$(document).on('click', function (e) {
var opened = $('body').hasClass('sidemenu-open');
if (opened === true) {
$('.sidemenu').removeClass('is-visible');
$('body').removeClass('sidemenu-open');
}
});
DEMO
Your click on the side menu is propagating down to the body and activating that handler as well - preventDefault isn't what you're after, you need to return false as well. Try this click handler instead.
$(function () {
$('.sidemenu-toggle').on('click', function (event) {
$('.sidemenu').toggleClass('is-visible');
$('body.sidemenu-enabled').toggleClass('sidemenu-open');
$('.sidemenu').toggleClass('sidemenu-open');
return false;
});
});
You can get the target element in click event by which you can have further conditions.
$('body').click(function(evt){
if(evt.target.id == "your_sidemenu_id"){
//do nothing
}
else{
//do the toggle here as this will be implemented whenever any element is clicked other than your sidemenu
}
});

Close a Dropdown menu when you click somewhere in the page with jQuery? [duplicate]

This question already has answers here:
jQuery drop down menu closing by clicking outside
(7 answers)
Closed 8 years ago.
I have a simple Dropdown menu that I am showing on inline text links. I am using jQuery click event to show the Dropdown menu when a link is clicked on.
What I would like to do is have the Dropdown menu go back to a hidden state when a click anywhere is made. Right now you have to click the link again to close the menu.
Demo http://codepen.io/jasondavis/pen/sFpwK?editors=101
jQuery
// Show Dropdown Menu when link is clicked
$(function(){
$(".inline-dropdown-menu").click(function(e){
$(this).find(".inline-dropdown-menu-list:first").toggle();
e.preventDefault(); // Stop navigation
});
});
HTML
<span class="inline-dropdown-menu">
My Link that reveals a DropDown Menu when clicked on<span class="caret"></span>
<ul class="inline-dropdown-menu-list">
<li class="bottomBorder">
alphabetically
</li>
<li>
2. the first report, alphabetically
</li>
<li>
3. the first report, alphabetically
</li>
</ul>
</span>
http://codepen.io/anon/pen/JmLsB
$(function () {
$(".inline-dropdown-menu").click(function (e) {
$(".inline-dropdown-menu-list").hide(); // to hide other drop down
$(this).find(".inline-dropdown-menu-list:first").toggle();
e.preventDefault(); // Stop navigation
});
});
// to hide drop down if you click other than inline-dropdown-menu class
$(document).click(function (e) {
var container = $(".inline-dropdown-menu");
if (!container.is(e.target) && container.has(e.target).length === 0) {
$(".inline-dropdown-menu-list").hide();
}
});
This might be useful:
var flag = false;
$(".inline-dropdown-menu").click(function(e){
$(".inline-dropdown-menu-list").not(':hidden').hide();
$(this).find(".inline-dropdown-menu-list:first").toggle();
e.preventDefault(); // Stop navigation
flag = true;
});
$('body').click(function(){
if (flag) {
flag = false;
return;
}
$(".inline-dropdown-menu-list").not(':hidden').hide();
});
try this
$(function(){
$(".inline-dropdown-menu").click(function(e){
e.stopPropagation();
$(this).find(".inline-dropdown-menu-list:first").toggle();
e.preventDefault(); // Stop navigation
});
$("body").click(function(e){
$(".inline-dropdown-menu-list").hide();
});
});
When your link is clicked, you will have to add a click event to body. When body is clicked, you can hide your dropdown, and also remove the event on body again. I used an setTimeout to prevent double click. I also add a namespace to the click event on body (click.ddls), so you can have other click events.
So check this demo out: http://jsfiddle.net/gdxyef46/2/
// Show Dropdown Menu when link is clicked
$(function(){
$(".inline-dropdown-menu a").click(function(e){
e.preventDefault(); // Stop navigation
$("body").off("click.ddls");
$(".inline-dropdown-menu-list").toggle();
//to prevent double click
setTimeout(function(){
$("body").on("click.ddls", function(){
console.log("body clicked");
$(".inline-dropdown-menu-list").hide();
$("body").off("click.ddls");
});
}, 300);
});
});
without unique class names, you could loop through them and check if they are visible and if so , close it. This code isn't working (apologies), but will hopefully point you in the right direction. I personally like to use on("click") vs click() in case you are dealing with dynamic elements that the DOM doesn't have access to yet.
$('*').not(".inline-dropdown-menu").on("click", function(){
$('.inline-dropdown-menu-list').each(function() {
if ($(this).is(":visible")) {
$(this).toggle();
}
});
You could also create a counter based on $('.inline-dropdown-menu-list').length and assign a data-id to each so you can match and keep track of them. Hope this helps.
If I understand you correctly you want to to replicate what the drop down arrow is doing, when you click on the body. If that is so, then try this:
$("body").click(function(e){
$('.inline-dropdown-menu.open ').find('.inline-dropdown-menu-list:first').toggle();
});
link to demo.
But do note that if you click the body again it will again show the drop down. You can play around to remove that if you don't want that.

jquery trouble with not() and dropdown

i have a horizontal list menu which when clicked toggles the visibility of a nested list. the function almost works, i click the menu and the visibility toggles. however, when i click inside the element that has just appeared, the visibility of the nested list reverts back to original state and is hidden. this is a bit difficult when the elements require an interaction (whether it's a form or another menu).
Here's the code i've got so far:
/* menu */
var menu = function(clicktarget, dropdown){
$(clicktarget).click( function(event){
// stop bubbling
event.stopPropagation();
//show
$(dropdown).toggle();
return false;
});
$('body').not($(dropdown)).click( function(){
//hide when click anywhere out the menu
$(dropdown).hide();
return false;
});
}
menu($('#loginAcc'),$('#auth-menu'));
As you can see i have tried using the .not() function in an attempt to remove it, but nothing changes and the dropdown still gets removed when it's clicked.
Try
$('body').click( function(e){
//hide when click anywhere out the menu
var $target = $(e.target)
if(!$target.closest(dropdown).length){
$(dropdown).hide();
}
return false;
});

jQuery blur()....How exactly does it work?

I've created a mobile dropdown menu for a responsive website, that essentially shows a hidden unordered list when you click on a certain element. It works great, except for the fact that I can't get the blur() function to work, so that when a user clicks anywhere on the page other than inside the menu, it hides the menu. Here's a codepen: http://codepen.io/trevanhetzel/pen/wIrkH
My javascript looks like so:
$(function() {
var pull = $('#pull');
menu = $('header ul');
$(pull).on('click', function(e) {
e.preventDefault();
$('.close-menu').toggle();
$('.mobi-nav span').toggle();
menu.slideToggle(250);
});
$(menu).blur(function() {
$(this).slideToggle();
});
});
I've struggled with blur() in the past, so would really like to figure out once and for all how exactly it works, and whether or not I'm using it in the right context here. Thanks!
You have to watch for clicks yourself. And use $.contains to see if the clicked thing is within your menu:
$(document).click(function (ev) {
if (ev.target !== menu.get(0) && !$.contains(menu.get(0), ev.target)) {
menu.slideUp();
}
});
Just be sure to call ev.stopPropagation() in your toggle click handler to prevent the handler above from immediately closing the menu when the event bubbles up.

Categories

Resources