i am using window.scroll event to load content on div just when buttom of scroll reached.
$(window).scroll(function() {
if($(window).scrollTop() + $(window).height() > $(document).height() - 100) {
$(window).unbind('scroll');
loadMoreCommentsOnArticle();
}
});
function loadMoreCommentsOnArticle(){
$(window).bind('scroll');
var dynamicData = fetchData();
$('#parentElement').append(dynamicData);
}
scroll is not binding after once bind initially. maybe by $(window).unbind('scroll'). But i am trying to bind scroll again using $(window).bind('scroll'); but it is not working.
By not using $(window).unbind('scroll') . Scroll event is firing ample of times in no time.
I am using this way according to Rory
var $window = $(window);
function windowScroll() {
if ($window.scrollTop() + $window.height() > $(document).height() - 100) {
window.off('scroll');
loadMoreCommentsOnArticle();
}
}
$window.scroll(windowScroll);
The issue is because when you re-bind the scroll event in loadMoreCommentsOnArticle() you're not providing a function to run. You can solve the issue by extracting the scroll logic out to it's own function to make binding/rebinding easier.
Also note that bind() and unbind() are deprecated. You should use on() and off() instead.
var $window = $(window);
function windowScroll() {
if ($window.scrollTop() + $window.height() > $(document).height() - 100) {
$window.off('scroll');
loadMoreCommentsOnArticle();
}
}
$window.scroll(windowScroll);
function loadMoreCommentsOnArticle() {
$window.on('scroll', windowScroll);
$('#parentElement').append(fetchData());
}
function fetchData() {
console.log('loading data...')
return '<div>More data...</div>';
}
#parentElement div {
height: 3000px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="parentElement">
<div>Some data...</div>
</div>
Related
I just write a script to auto positioning an element on my page.
$(document).ready(function(){
$(window).scroll(function() {
var scroll = $(window).scrollTop();
if (scroll < 180) {
$(".header-bottom").removeClass("scroll-menu");
if ($(window).width() > 991) {
$(".header_user_top").css("position", "absolute");
$(".header_user_top").css("top", "initial");
$(".header_user_top").css("right", "60px");
$(".header_user_top").css("z-index", "1");
}
} else {
$(".header-bottom").addClass("scroll-menu");
if ($(window).width() > 991) {
var rightContainer = ($(window).width() - ($('#header div.header-bottom div.container').offset().left + $('#header div.header-bottom div.container').outerWidth()));
$(".header_user_top").css("position", "fixed");
$(".header_user_top").css("top", "-22px");
$(".header_user_top").css("right", rightContainer+60+"px");
$(".header_user_top").css("z-index", "99");
}
}
});
});
It's working but if I resize browser window the script doesn't reload.
If I refresh the page it's working.
I have add window.onresize = function(){ location.reload(); }to my script to fix this problem but I'm looking for a better solution.
Any idea?
Use on function to call multiple event:
$(window).on("load resize scroll",function(e){
// do something
}
Call function which is handling size on windows.resize also
function handleSize(){
// You code to handle size
}
window.resize=handleSize();
I have two menus that fade in and out on scroll. But when I resize the window I want to stop this event. I've tried plenty of stuff, searched a lot but nothing worked. I'm missing something. Here's what I have:
var scrollHandler = $(window).scroll(function() {
var top = $(window).scrollTop();
if (top > 0) {
$('.menu').fadeOut('fast', function() {
$('.second-menu').fadeIn('fast');
});
} else {
$('.second-menu').fadeOut('fast', function() {
$('.menu').fadeIn('fast');
});
}
})
scrollHandler;
if ($(window).width() < 768) {
$(window).off("scroll", scrollHandler);
}
Any help would be great, thanks!
The $(window).width() is only evaluated at runtime (i.e. the width of the viewport when the script is executed). It is not reactive in the sense that it will be updated on-the-fly when the viewport is resized.
Therefore, if you want to listen to changes in the width, you will have to place the logic within the window resize event callback:
$(window).resize(function() {
if ($(window).width() < 768) {
$(window).off('scroll');
}
});
Moreover, there are several issues with your code.
The scrollHandler should reference/define the function, not the outcome of the binding
Calling scrollHandler does not do anything. If you make the changes as per #1, then you can simply bind the logic using $(window).on('scroll', scrollHandler);
The .off() method does not accept a second parameter, this is enough: $(window).off('scroll')
After refactoring, your code will look something like this:
var scrollHandler = function() {
var top = $(window).scrollTop();
if (top > 0) {
$('.menu').fadeOut('fast', function() {
$('.second-menu').fadeIn('fast');
});
} else {
$('.second-menu').fadeOut('fast', function() {
$('.menu').fadeIn('fast');
});
}
};
// Bind scrollHandler firing to scroll event
$(window).on('scroll', scrollHandler);
$(window).resize(function() {
if ($(window).width() < 768) {
$(window).off('scroll');
}
});
Note:
If you want to get the best performance out of this, you should throttle the resize event so that the callback function is not fired too frequently. Lodash/Underscore.js have utility functions for that (_.throttle()), and there is also a jQuery plugin available.
In Lodash/Underscore.js:
$(window).resize(_.throttle(function() {
if ($(window).width() < 768) {
$(window).off('scroll');
}
}, 100));
Using Ben Alman's jQuery plugin:
$(window).resize($.throttle(100, function() {
if ($(window).width() < 768) {
$(window).off('scroll');
}
}));
(first question so be nice :) )
I'm trying to disable scroll, animate a div, then re-enable scrolling. So far I have accomplished the first two parts of this incredible quest, but alas, I cannot seem to get it to scroll again.
I am using lockScroll() and unlockScroll() functions defined by JeanValjean on How to programmatically disable page scrolling with jQuery
Any help would be much appreciated. Please see demo http://jsfiddle.net/Chris_James/1xxL5dnp/6/
jQuery(document).ready(function(){
$(window).scroll(function(){
var p = $( ".testi" );
var offset = p.offset();
if ($(this).scrollTop() > offset.top - $(window).height()/2) {
lockScroll();
$('.testi').addClass( 'testishow' );
setTimeout(function(){
$('.testimonial').fadeIn('fast');
unlockScroll();
},700);
}
})
});
jQuery(document).ready(function(){
$(window).scroll(function(){
var p = $( ".testi" );
var offset = p.offset();
if ($(this).scrollTop() > offset.top - $(window).height()/2) {
lockScroll();
$('.testi').addClass( 'testishow' );
setTimeout(function(){
$('.testimonial').fadeIn('fast', function() {
unlockScroll();
});
},700);
}
})
Like Good.luck recommended, you can you use callbacks for unlocking (Well, I was a few seconds to late...). I think you don't have to declare a function just unlockScroll.
The lock/unlockScroll() methods seems to a bit to be overweight.
I would recommend cubbius answer with an "overflow: hidden" style for the html element.
Make a function out of your current scroll event and unlock it with:
$(window).off("scroll touchmove mousewheel", function () {
$(window).on("click", yourScrollMethod);
})
Solution - adding a class (scrolllocked) to if statement, and checking for it (with &&). Simples. http://jsfiddle.net/Chris_James/1xxL5dnp/6/
if ($(this).scrollTop() > offset.top - $(window).height()/2 && !p.hasClass("scrollLocked")) {
lockScroll();
p.addClass("scrollLocked");
$('.testi').addClass( 'testishow' );
You can use function callbacks for this e.g.
$('.testimonial').fadeIn('fast', function(){
unlockScroll();
});
In this case function unlockScroll() will execute only after fadeIn finished it's animation.
UPD: Added Fiddle
I'm extremely new to JavaScript so I apologize in advance. I'm trying to create a one page html document for a school project using a list of links for navigation that change when the anchor is scrolled to. I've tried various different methods found on Jfiddle and through stackoverflow. This is the method I am trying now: http://jsfiddle.net/m2zQE/
var topRange = 200, // measure from the top of the viewport to X pixels down
edgeMargin = 20, // margin above the top or margin from the end of the page
animationTime = 1200, // time in milliseconds
contentTop = [];
$(document).ready(function () {
// Stop animated scroll if the user does something
$('html,body').bind('scroll mousedown DOMMouseScroll mousewheel keyup', function (e) {
if (e.which > 0 || e.type == 'mousedown' || e.type == 'mousewheel') {
$('html,body').stop();
}
});
// Set up content an array of locations
$('#nav').find('a').each(function () {
contentTop.push($($(this).attr('href')).offset().top);
});
// Animate menu scroll to content
$('#nav').find('a').click(function () {
var sel = this,
newTop = Math.min(contentTop[$('#nav a').index($(this))], $(document).height() - $(window).height()); // get content top or top position if at the document bottom
$('html,body').stop().animate({
'scrollTop': newTop
}, animationTime, function () {
window.location.hash = $(sel).attr('href');
});
return false;
});
// adjust side menu
$(window).scroll(function () {
var winTop = $(window).scrollTop(),
bodyHt = $(document).height(),
vpHt = $(window).height() + edgeMargin; // viewport height + margin
$.each(contentTop, function (i, loc) {
if ((loc > winTop - edgeMargin && (loc < winTop + topRange || (winTop + vpHt) >= bodyHt))) {
$('#nav li')
.removeClass('selected')
.eq(i).addClass('selected');
}
});
});
});
I'm still not having any luck. I've already searched to see if I could debug the problem and have tried changing the order of the code as well as the order of calling jquery.
Here is a link to the site: https://googledrive.com/host/0BwvPQbnPrz_LMlZDeGlFY2Yydmc/index.html
I used html5boilerplate as a starting point.Thank you in advance.
Don't have much time to look into your code, but when I input the line
Math.min(contentTop[$('#nav a').index($(this))], $(document).height() - $(window).height())
into the console of developer tools, it return NaN.
So I guess the problem is you don't have your scrollTop correctly set.
I suggest you give each element an id and try:
$('html, body').animate({
scrollTop: $("#elementID").offset().top
}, 2000);
or if you insist not giving id,
$('html, body').animate({
scrollTop: $("#container-fulid:nth-child(2)").offset().top
}, 2000);
but notice that this is not working on all browser as the nth-child selector is a CSS3 selector.
Or, if you know how to correctly use other's work, you may try to use bootstrap 3.0, where there is already a function named scrollspy included, which do exactly the thing you are doing.
http://getbootstrap.com/javascript/#scrollspy
I've got a simple piece of code like this
http://jsfiddle.net/QTa2c/
and all I want is, when user click on some of the last elements in list to show the content,
$('a.showMeThis').click(function() {
$(this).next('.content').slideToggle('fast', function() {
// there's go all the magic
});
});
and it goes outside the viewport (partly or completely) - scroll of the height of div, so he can see all of the content.
I was looking a lot for some logic for this, playing around with position().top, window.innerHeight and more, but it never goes in the way I want…
Hope you guys will help me, take care and have a nice day!
Use .animate() and .offset()
$('a.showMeThis').click(function () {
var $this = $(this);
$this.next('.content').slideToggle('fast', function () {
$('html,body').animate({
scrollTop: $this.offset().top
}, 'slow');
});
});
Fiddle Demo
Updated after OP's comment
Updated Fiddle Demo
$('a.showMeThis').click(function () {
var $this = $(this);
$this.next('.content').slideToggle('fast', function () {
if ($this.position()) {
if ($this.position().top + $this.height() > $(window).scrollTop() + (window.innerHeight || document.documentElement.clientHeight)) {
$('html,body').animate({
scrollTop: $this.position().top - (window.innerHeight || document.documentElement.clientHeight) + $this.height() + 15 + $this.next('.content').height()
}, 100);
}
}
});
});
With condition it looks like this: http://jsfiddle.net/QTa2c/1/
if ($(this).parent().offset().top + $(this).height() > window.innerHeight + $(window).scrollTop())
{
var a = $(this)
$('html,body').animate({scrollTop: $(a).parent().offset().top})
}
I think, this code is enough to understand the logic =)
UPD: note, that you should insert return false; into .click event to prevent jumping to # anchor.