I am looking to add two different "navigation" sections to a page on mobile. Here is the jQuery pull to make the dropdown work. However, when I add in a second section of markup for the second dropdown, the one menu button opens BOTH menus. Is it possible to use more than one? Or what am I missing to make it open each one separately?
<script>
jQuery(function() {
var pull = jQuery('#pull');
menu = jQuery('nav ul');
menuHeight = menu.height();
jQuery(pull).on('click', function(e) {
e.preventDefault();
menu.slideToggle();
});
});
jQuery(window).resize(function(){
var w = jQuery(window).width();
if(w > 320 && menu.is(':hidden')) {
menu.removeAttr('style');
}
});
</script>
You need to change the menu and pull variable values.
Also, add a var before the variables as so, so the variables don't become global:
var pull = jQuery('#pull');
var menu = jQuery('nav ul');
var menuHeight = menu.height();
Related
I have converted my first HTML to WordPress website and have a responsive sub menu which is not opening properly on mobile because obviously there is no hover functionality. I have looked up solutions and have come to nothing as my JavaScript knowledge is non existent therefore copying and pasting code from examples on here is not getting me the result I want to achieve.
The menu I am trying to fix is on the following website:
https://www.piogroup.in/wordpress/
I have 2 parents which are "about" and "products" and they are not clickable links. So far I have tried the following code:
$(document).ready(function(){
$("#menu-item-74").off("click").on("click", function() {
$(".sub-menu").fadeToggle("slow");
});
})
$(document).ready(function(){
$("#menu-item-72").off("click").on("click", function() {
$(".sub-menu").fadeToggle("slow");
});
})
and then added this as well:
var $handle = $('.sub-menu').prev();
var opened = 0;
$handle.on('click', function(e){
if (opened) {
window.location.href = $(this).attr('href');
} else {
e.preventDefault();
e.stopPropagation();
$('.sub-menu').slideToggle();
opened = 1;
}
});
$('html').on('click', function(){
if (opened) {
$('.sub-menu').slideToggle();
opened = 0;
}
});
I am not sure if I am meant to put up any other files but can do so.
#R Alexander if I understand you correctly, Your sub menu is not working on mobile devices. Below code may be help you out.
minWidth = $(window).width();
if(winWidth < 768){
$(".menu-main-menu-container li").click(function(){
$(".menu-main-menu-container li ul").slideToggle();
$(".menu-main-menu-container li ul").parent().siblings().children(".menu-main-menu-container li ul").slideUp();
});
}
I went through your code and there are some logical inconsistencies.
First of all you should change this as follows:
var $handle = $('.sub-menu').prev();
var opened = 0;
$handle.on('click', function(e) {
if (opened) {
window.location.href = $(this).attr('href');
} else {
e.preventDefault();
e.stopPropagation();
$(this).next().slideToggle();
opened = 1;
}
});
This makes the particular clicked element to slideToggle instead of all the .sub-menu elements.
Then to emulate the closing of the drop downs use this:
$('html').on('click', function() {
if (opened) {
$('.sub-menu').slideUp();
opened = 0;
}
});
I have a code snippet that shows a div once you click the menu item, there are different divs on this space and what the menu does is hide the one that was there before and show the new one, the problem is when I click on the same menu item it shows the current div again and I want to stop that from happening, it should only show the animation if it's not the current one, if it is nothing should happen.
Here is the code snippet:
var curPage="";
$("#menu a").click(function() {
if (curPage.length) {
$("#"+curPage).hide("slide");
}
curPage=$(this).data("page");
$("#"+curPage).show("slide");
});
And here is a demo of how it's occuring now: https://jsfiddle.net/Lfsvc1ta/
Just add an additional check to see whether curPage is the same as the clicked page.
var curPage;
$("#menu a").click(function () {
var page = $(this).data("page");
if (curPage && page != curPage) {
$("#" + curPage).stop().hide("slide");
}
$("#" + page).stop().show("slide");
curPage = page;
});
Demo: Fiddle
You have to check what the before page was, adding a variable.
var curPage="";
$("#menu a").click(function() {
var page=$(this).data("page");
if (curPage!=page && curPage.length) {
$("#"+curPage).hide("slide");
curPage=$(this).data("page");
}
$("#"+curPage).show("slide");
});
Like this fiddle https://jsfiddle.net/7b1wh70h/
Check what data-page is clicked first bro.
var curPage="";
$("#menu a").click(function() {
var newPage = $(this).data("page");
if (newPage !== curPage) {
$("#"+curPage).hide("slide");
$("#"+newPage).show("slide");
curPage = newPage;
}
});
Code:
<script type="text/javascript">
$(document).ready(function () {
$('.box').on('click', function (e) {
e.preventDefault();
var $btn = $(this);
$btn.toggleClass('opened');
var heights = $btn.hasClass('opened') ? 300 : 100;
$(this).stop().animate({ height: heights }, 800);
//$(".sync_store_info_input_holder").toggle();
});
});
</script>
Using the above code i am able to accomplish what i need but i have a slight problem with the following line:
$(".sync_store_info_input_holder").toggle();
I need that to show only when the .box opens and not when it closes. I also need it so show only for the box that the user opens. I have 18 boxes that use the .box class and only ids are unique so the only box the user opens thats when the toggle function should work.
It seems like you can use the showOrHide version of toggle(). If not, make a jsFiddle of your code to explain the problem.
<script type="text/javascript">
$(document).ready(function () {
$('.box').on('click', function(e) {
e.preventDefault();
var $btn = $(this);
$btn.toggleClass('opened');
// Make whether the box is open a variable for reuse
var isOpen = $btn.hasClass('opened');
var heights = isOpen ? 300 : 100;
// Reuse $btn instead of $(this)
$btn.stop().animate({ height: heights }, 800);
// Important change
$(".sync_store_info_input_holder").toggle(isOpen);
});
});
</script>
Edit
I also need it so show only for the box that the user opens. I have 18 boxes that use the .box class and only ids are unique so the only box the user opens thats when the toggle function should work.
Do you mean that there is an .sync_store_info_input_holder element within each box? If so, you can change the line to
$(".sync_store_info_input_holder", this).toggle(isOpen);
to select only the element within the .box context. If it's outside of the .box, you'd have to show the HTML for us to give an example.
I have two similar functions performing a responsive menu toggle via a handle on the page, see the code:
//responsive main navigation
$(function() {
var pull = $('#pull');
menu = $('.main-nav ul');
menuHeight = menu.height();
$(pull).on('click', function(e) {
e.preventDefault();
menu.slideToggle('fast');
});
});
//responsive blog navigation
$(function() {
var toggle = $('#toggle-handle');
sidebar = $('.blog-sidebar-wrap');
sidebarHeight = sidebar.height();
$(toggle).on('click', function(e) {
e.preventDefault();
sidebar.slideToggle('fast');
});
});
My question is how can I write this so that I'm not repeating the same kind of procedure (function). Do i set up a single function and pass in the parameters? Help mostly appreciated, jQuery/Javascript beginner here!
Try
//a function that creates a slide based menu
function slideMenu(ctrl, target){
ctrl.on('click', function(e) {
e.preventDefault();
target.slideToggle('fast');
});
}
//responsive main navigation
$(function() {
var pull = $('#pull');
menu = $('.main-nav ul');
menuHeight = menu.height();
slideMenu(pull, menu)
});
//responsive blog navigation
$(function() {
var toggle = $('#toggle-handle');
sidebar = $('.blog-sidebar-wrap');
sidebarHeight = sidebar.height();
slideMenu(toggle, sidebar)
});
$(function() {
effectdemo("#pull",'.main-nav ul');
effectdemo('#toggle-handle','.blog-sidebar-wrap');
});
function effectdemo(starter,sliderconatiner)
{
var toggle = $(starter);
sidebar = $(sliderconatiner);
sidebarHeight = sidebar.height();
$(toggle).on('click', function(e) {
e.preventDefault();
sidebar.slideToggle('fast');
});
}
I have a couple nested & hidden sub-nav lists
<ul class="nav">
<li>Home</li>
<li><a class="profile" href="#">Profile</a>
<ul id="profile">
<li>Company</li>
<li>Structure</li>
<li>Team</li>
</ul>
</li>
<li><a class="projects" href="#">Projects</a>
<ul id="projects">
<li>Chapter</li>
<li>Pblc Trde</li>
<li>Globe</li>
<li>Komforte</li>
</ul>
</li>
I am currently using some jQuery i found online to show/hide the sub-nav upon click. What I am trying to accomplish is:
Hopefully clean up the show/hide click function of the sub-nab menus.
When clicking on the sub-nav menu items, the corresponding page that opens, needs to have the sub-nav expanded and give the corresponding menu item active class, so as to let the user know which page they are on.
I am hoping to do this purely in JS/jQuery. The installation of the site will be in WordPress.
$(document).ready(function () {
$(".profile").click(function () {
var X = $(this).attr('id');
if (X == 1) {
$("#profile").hide();
$(this).attr('id', '0');
} else {
$("#profile").show();
$(this).attr('id', '1');
}
});
//Mouse click on nav
$("#profile").mouseup(function () {});
//Document Click
$(document).mouseup(function () {
$("#profile").hide();
$(".profile").attr('id', '');
});
$(".projects").click(function () {
var X = $(this).attr('id');
if (X == 1) {
$("#projects").hide();
$(this).attr('id', '0');
} else {
$("#projects").show();
$(this).attr('id', '1');
}
});
//Mouse click on nav
$("#projects").mouseup(function () {});
//Document Click
$(document).mouseup(function () {
$("#projects").hide();
$(".projects").attr('id', '');
});
});
window.onload = function () {
$("ul#profile li:first").addClass("active");
};
$(document).ready(function () {
$("ul#profile").show()
});
$(document).ready(function()
{
// Get the name of the page. Split the URL at the '/':s and get the last part
// with pop():
var pageName = (location.pathname).split('/').pop();
// If we couldn't get a page name, default to index.html:
if( pageName == '' )
{
pageName = 'index.html';
}
// Hide ul:s that are children of the navigation:
$('.nav ul').hide();
// Event handler for clicks on navigation links:
$('.nav a').on('click', function()
{
// Change visibility for the first ul-child of the current li.
// $(this) refers to the clicked element.
$(this).parent('li').find('ul').first().toggle();
// Hide other sub-menus:
$(this).parents('li').siblings('li').children('ul').hide();
});
// Search through all link elements in the nav menu:
$('.nav').find('a').each(function(index, value)
{
// Append a '$' to the pagename to make the match()-function search
// from the end of the href value:
pageName += '$';
if( value.href.match(pageName))
{
// If the pagename matches the href-attribute, then add the 'active'
// class to the parent li, and show parent ul:s:
$(this).parent('li').addClass('active').parents('ul').show();
}
});
});
You could use a Cookie to hold the value of the currently open menu. This will allow for the value to be saved/retrieved between page loads and browser sessions.
As you've already got jQuery setup you can use the jQuery Cookie plugin to simplify things.
The code for it is quite simple (more examples on plugin page).
$.cookie('open_menu', 'projects'); //Save 'projects' under 'open_menu'
$.cookie('open_menu') //Returns 'projects'
Just check the value on page load and save it when one of the menu's is clicked.
If you'd prefer not to add any extra plugins here's some documentation on JavaScript's inbuilt cookie API.
Edit: I've created a JSFiddle with an example for you. The Cookie code doesn't seem to work in there sandbox, but the code should work for you, let me know if you have any troubles.
$(window).load(function() {
if ($.cookie('show_menu') !== undefined) {
$('#' + $.cookie('show_menu')).click();
}
$('.nav > li > ul').each(function () {
//Hide the sub lists
$(this).hide();
//Get link with same ID as Class
var id = $(this).attr('id');
//When link is clicked
$('.' + id).click(function () {
//Get the sub list
var list = $('#' + $(this).attr('class'));
//Check if it's currently visible
if (list.is(':visible')) {
list.hide(); //Hide list
$.cookie('show_menu', ''); //Unset open menu
} else {
$('.nav > li > ul').hide(); //Hide all other lists
list.show(); //Show list
$.cookie('show_menu', list.attr('class')); //Set open menu
}
});
});
});