I'm trying to apply the slideToggle function over a menu based on screen size , but this code is applying the function multiple times with just one click , tried every solution here but nothing works .
I know the problem is the click event inside a window resize, but the application should be like that, so please i need alternative solution to have a working code.
$(window).on("resize", function () {
if (screen.width < 768) {
$(".part-heading").click(function (e) {
$(this).next(".sections").slideToggle("slow");
});
}
});
You are registering multiple event listeners, one every time the screen size change. And when you click all of them will run. You can change your script as below, so check the size on each click rather than watching the resize:
$(".part-heading").click(function (e) {
if (screen.width < 768) {
$(this).next(".sections").slideToggle("slow");
}
});
Related
I have some code which adds a class at a certain page scroll point, which I need for a particular scenario however I do not need this on mobile.
$(window).scroll(function() {
if ($(".navbar").offset().top > 500) {
$(".navbar-fixed-top").addClass("top-nav-collapse");
} else {
$(".navbar-fixed-top").removeClass("top-nav-collapse");
}
});
Could I combine this with something like...
function checkWidth() {
if ($(window).width() < 514) {
$('#menu2').addClass('f-nav');
} else {
$('#menu2').removeClass('f-nav');
}
}
$(window).resize(checkWidth);
To say switch the classes but only if the width is above say 480px?
I appreciate this is probably newbie but I wondered if the window scroll function could just be part of the if condition?
Try out this fiddle:https://jsfiddle.net/cxn6t946/
You need to put if ($(window).width() > 514) inside the scroll function and it will work.
Edited my answer as the previous fiddle had a problem. It worked fine on sceen size >514 and added top-nav-collapse on an offset>500. However on returning to screen size <514 the top-nav-collaspe class remained there. So had to rewrite the fiddle by incorporating resize.
Check out the updated fiddle:https://jsfiddle.net/cxn6t946/1/
Hope this helps.
If you place the conditional check on the event listener as opposed to the action of the event listener, you can save yourself some resources on mobile while also accomplishing your task.
Try:
if ($(window).width() > 514) {
$(window).scroll(function() {
if ($(".navbar").offset().top > 500) {
$(".navbar-fixed-top").addClass("top-nav-collapse");
} else {
$(".navbar-fixed-top").removeClass("top-nav-collapse");
}
});
}
By doing the conditional check before applying the event listener, you're not adding an event listener on mobile devices and saving the resources it would be using. This also keeps you from having to add any conditional logic to your functionality since it won't be getting called without the scroll listener being applied on devices smaller than 514px.
I'm trying to make this site show a tab-box on large screens, but just a normal layout on smaller screens. Here's what I have:
function adapt() {
if(document.documentElement.clientWidth > 800) {
$(document).ready(function() {
$(".box").hide();
$(".box:first").show();
$("ul.tabs li").click(function() {
$("ul.tabs li").removeClass("active");
$(this).addClass("active");
$(".box").hide();
var activeTab = $(this).attr("rel");
$("#"+activeTab).show();
});
});
}else{
$(document).ready(function () {
$('.box').show();
});
};}
window.onload = adapt();
window.onresize = adapt();
The onload event handler works, so the tab-box jquery function only works if the page is loaded on a larger screen, and it shows all the content when loaded on a smaller screen. I added the onresize event so it would also change when the browser window is shrunk down, but it doesn't work. If I load on a large screen and then shrink it, all that shows is the content that was in the first tab, and if I load on a small screen, and then make the window bigger, all the content is displayed and the tab buttons don't work. Am I just misinterpreting how window.resize is supposed to work?
I'm guessing that maybe the event only fires once the first time the resize occurs, and if the difference isn't enough that time for my other conditional to take over, it doesn't happen. If this is the case, is there a way to make it continually check for screen size, like with CSS media queries?
don't forget, that if some other code in your project also uses window.onresize or window.onload - your code will be overwritten
it's a better practice to use addEventListener function
window.addEventListener('resize', adapt);
You need to call the reference, not execute the function
window.onload = adapt;
window.onresize = adapt;
Because when you do
window.onload = adapt();
window.onresize = adapt();
You execute adapt() and since it return nothing, you have nothing done on these events
You can try with jquery:
$(document).ready(function() {
adapt(); // onload
$(window).resize(adapt()); // resize
});
I have a page with content (on the left) and sidebar (on the right). For screen widths <= 480px the 2 div's are placed one under the other (100% widths). The "Show/Hide" button that becomes visible is meant to toggle the sidebar's visibility when clicked. I use
$(".sidebar .box").slideToggle(200);
for this purpose.
See everything together on jsfiddle.
The problem: if I switch to wide screen and then back to narrow screen (width <= 480px) again, clicking the button produces a "back and forth" bug.
Where is my mistake?
Thank you!
I believe the reason is that this code:
$("a.expander").click(function () {
$(this).toggleClass('close');
$(".sidebar .box").slideToggle(200);
});
gets executed every time the function showSidebar is run, which is every time the window is resized. JQuery's click function adds a new event handler each time, and executes all of them on each window resize.
The solution would be to move the click handler registration outside of the function.
I believe that your problem is that your slide function gets called continuously when your window is resized. Rather than have this event occur unchecked, try to control it using an event handler like so:
Use .one():
$('#your_element_id').one("click", function () {
$('.your_css_style_class').slideToggle(200);
});
Another thing to keep in mind is that if down the line, you desire to display it hidden, you may want to use .slideDown() rather than .slideToggle() to begin with.
Here is a jQuery reference to the 'one' function: http://api.jquery.com/one
something like this? http://jsfiddle.net/jqdvj42u/3/
$(document).ready(function() {
$("a.expander").click(function () {
$(this).toggleClass('close');
$(".sidebar .box").slideToggle(200);
});
});
function showSidebar() {
if ($(window).width() <= 480) {
// Close sidebar when window width <= 480px
$(".sidebar .box").removeClass('open');
// Click expander button to show/hide sidebar
} else {
$("a.expander").removeClass('close');
// Open sidebar when window width > 480px;
$(".sidebar .box").addClass('open');
}
}
showSidebar();
$(window).resize(showSidebar);
your click shouldnt be called within showSidebar() because it'll bind the click event every time that function is called. resize triggers showSidebar() multiple times, so the click is bound multiple times. also, you should use jQuery 1.11 as the lowest version since its the most up-to-date version thats stable on IE<9. if you dont mind support on IE<9, use jQuery version 2.0 or higher.
I'm using scrollTo() for page scrolling. One problem I found is, when I resize browser, page don't scroll again to element I specified, but it stays somewhere in middle, so I have to click 'scroll' button again to align the page. Is there any way to align page when user resize browser.
I tried using this:
window.onresize = function() {
scrollToPosition(section[position]);
}
// position is variable which I declared above this event
But this makes scrolling crazy, the page start to move right/left really fast which is not normal. I believe it binds onresize event every time I resize browser.
Is there any solution for my problem
EDIT:
This is jsFiddle, but it seems I don't know how to use jsFiddle since nothing works here: http://jsfiddle.net/52eRj/1/
You can avoid reruning function everytime the resize event is executed by writing code as below. scrollToPosition function will be executed every 1 second when scrolling.
var last = new Date().getTime();
var interval = 1000; // Set your own time.
window.addEventListener('resize', function() {
var curr = new Date().getTime();
if (curr - last > interval) {
last = curr;
scrollToPosition(section[position]);
}
});
The problem might be that you are calling your scrollToPosition function on every resize event, which can be fired 100 times in a normal manual resize.
To avoid this you can use clearTimeout like this:
$(window).resize(function () {
clearTimeout(resizeId);
resizeId = setTimeout(doneResizing, 500);
});
function doneResizing() {
scrollToPosition(section[position]);
}
This way the doneResizing function would only be called after 500 miliseconds since the window has stopped resizing, avoiding therefore, those tens or hundreds of unnecessary calls.
People!
This is the first time I come here to ask something, so far, always when I had a problem, I could find a good answer here. So, in first place, thanks for this amazing community!
Now let's go to the problem:
I'm doing a responsive menu that check the window.resize event and, when it fits the minimum browser width, a click function for a button is allowed. If the browser width is greater, then the click function is unbound. I need to do this because the same element that is the button on the mobile version, is a visual element on the desktop version.
The problem is that, with the code that I have now, when the page is loaded, the click function works fine. But, if I resize the browser and click on the element again, it triggers more than once the state, sometimes leaving the impression that the function isn't triggered. And, if I resize the browser again, it triggers the click function more than the last time I clicked. Really annoying.
To help understand what is happening, I've made a simple example. Here's is the simple code (just to check the click function issue):
HTML:
<ul>
<li><span class="sub-toggle">Testing 01</span></li>
<li><span class="sub-toggle">Testing 02</span></li>
<li><span class="sub-toggle">Testing 03</span></li>
</ul>
CSS:
.sub-toggle{
display:block;
padding: 20px;
}
.sub-toggle.active{
background-color: #ffcc00;
color: #fff;
}
Javascript (jQuery):
jQuery(function($){
var i = 1;
// check if browser size is compatible with click event
onResize = function() {
// if browser size is ok, do the click function
if($(window).width() <= 480){
// click function
$('.sub-toggle').click(function(){
alert('click');
if($(this).hasClass('active')){
alert('active');
$(this).removeClass('active');
} else {
$(this).addClass('active');
}
});
} else{
// if browser size is greater than expected, unbind the click function
$('.sub-toggle').removeClass('active').unbind('click');
}
// just checking how many times the resize function is triggered
console.log('resize: '+ i);
i++;
}
$(document).ready(onResize);
var timer;
$(window).bind('resize', function(){
timer && clearTimeout(timer);
timer = setTimeout(onResize, 500);
});
});
(Edited to remove some unnecessary code)
If you want to see it in action, I've made a Fiddle (try resize the output frame to see it working): http://jsfiddle.net/C7ppv/1/
Maybe I've missing something really stupid, since I don't have a huge knowledge in JavaScript. But what I want to do is just trigger the click event once, even if multiple resizes.
I hope I could explain well my problem. I've searched and didn't found a solution for this issue (or maybe I just didn't know really well what to look for).
Any help would be appreciated!
Your code currently binds a new click events every time the method onResize is called and the window width is less than or equal to 480px.
Simply unbind any existing click events on the .sub-toggle element before binding a new one.
$('.sub-toggle').unbind('click').click(function() {
...
});
DEMO
The resize event is triggered multiple times during resizing, and each time you're binding a new click handler. My suggestion: bind only once, from outside the resize handler, and set a flag while resizing to let the click handler know if it should do something or not.
Then you won't even need to defer the handling of resize with setTimeout as you're doing.
DEMO
jQuery(function($){
var i = 1;
// flag to allow clicking
var clickAllowed = true;
// click function
$('.sub-toggle').click(function(){
if(clickAllowed) {
alert('click');
if($(this).hasClass('active')){
alert('active');
$(this).removeClass('active');
} else {
$(this).addClass('active');
}
}
});
// check if browser size is compatible with click event
onResize = function() {
//if browser size is ok, do the click function
if($(window).width() <= 480){
clickAllowed = true;
}
else{
// if browser size is greater than expected, disallow clicking
clickAllowed = false;
}
// just checking how many times the resize function is triggered
console.log('resize: '+ i);
i++;
}
$(document).ready(onResize);
var timer;
$(window).bind('resize', onResize);
});
Move $('.sub-toggle').click(function(){...} outside the onResize event handler and move if($(window).width() <= 480){...} into the click handler.