Masonry and Infinite Scroll breaking layout when scrolling at certain speed - javascript

I have a fluid width theme and I am using jQuery Masonry and Infinite Scroll. The Problem is that if you scroll at a certain speed (not too fast and not too slow) the page it can cause a break in the grid. I have only seen this with two columns and in Firefox:
Anyone know why this is happening? I know it could be a number of things but if anyone has had experience with this and knows what is going on it would help greatly.
UPDATE:
The break happens right after the last post on the page. The ones that come after are being generated by infinite scroll's callback.

Well, I can not see the link to your page to look at (and the image is not available) but from my past experiences with masonry, whenever there is a major change in the page size (re-sizing, scrolling, re-sized divs) you need to trigger it again:
jQuery(document).ready(function() {
jQuery("#somediv").click(function() {
jQuery('#leftcol').toggle(700); //div resizing start here
jQuery('#somediv2').toggleClass("minside");
jQuery('#somediv').toggleClass("full"); // evoke again after change..
jQuery('#container').masonry({
itemSelector : '.item',
columnWidth : 240
});
});
});

Add this as callback for infinite scrolls and your problem will be gone... at least works for me:
// trigger Masonry as a callback
function (newElements) {
// hide new items while they are loading
var $newElems = $(newElements).css({ opacity: 0 });
// ensure that images load before adding to masonry layout
$newElems.imagesLoaded(function () {
// show elems now they're ready
$newElems.animate({ opacity: 1 });
$container.masonry('appended', $newElems, true);
});
});
Check the $container just in case you've changed it.

Related

Javascript focusing a large div with fixed header

I'm using a tiny library called '$.scrollTo' to animate a scroll to a div element in my html. at the top of my page I have a fixed navgation bar.
at the end of the animation, I would like to have that div focused (for accessibility). if my div is to large, at the end of the animation, the fact that it gets focus - simply sends it a bit off the screen.
This does not happen with small divs.
here is my code (check jsfiddle below):
$('#buttonid').on("click", function() {
//fixed nav bar height (to compensate when scrolling)
var fixed_navbar_height = $("#navbar-id").height();
//the element to scroll to
var $go_to_selector = $("#topic2");
$.scrollTo($go_to_selector, {
duration: 1000,
offset: -fixed_navbar_height,
onAfter: function() {
//if you comment out this .focus it works as intended.
$go_to_selector.focus();
}
});
});
here is a JSFIDDLE example:
https://jsfiddle.net/dy35obpq/3/
obviously the onAfter messes it up, but i would like both the animation and the focus. Any ideas on how to implement a focus on a large div without letting it change the scroll bar ? suggestions are more than welcome.
Try this.
onAfter: function() {
$go_to_selector.focus();
$(window).scrollTop($($go_to_selector).offset().top - fixed_navbar_height);
}
I have simply added this line in your onAfter callback.
$(window).scrollTop($($go_to_selector).offset().top - fixed_navbar_height);
and it seems to have fixed the problem while still retaining focus. You might want to use css to disable the focus blue highlight.

Remove item transition for window resize, but keep transition for filtering/showing/hiding items

I would like to remove the transition on the isotope items when the window resizes (so that the items do not animate their position or size), but still maintain the scaling/opacity/position transitions that happen when filtering/hiding/showing items.
Using the following code, however:
$container.isotope({transitionDuration: 0});
Removes both the window resize transition and the hide/show transition.
How can I just remove the window resize transition?
Thanks!
I can guarantee there's a better / more efficient way to do this, and I welcome any suggestions, but here's is how I've done it in the past:
Initialization:
// No transitions
$('.grid').isotope({
itemSelector: '.grid-item',
transitionDuration: 0,
isResizeBound: false
});
// Handle Resize
$(window).resize(function () {
$('.grid').isotope('layout');
});
Within the filter/click event:
// Add transition & filter
$('.grid').isotope({
transitionDuration: '0.4s',
filter: selector
});
// Remove transition
$('.grid').isotope({
transitionDuration: 0
});
The key is giving transitionDuration a value before the filter, and setting it back to 0 after the filter. How you do that shouldn't make a difference.
First of all, here is your fiddle,
url: https://jsfiddle.net/eugensunic/so1axnup/18/
Second
Here are the two pieces of code which are important in order to achieve such thing:
the property isResizeBound: false, should have the value false (by default it is true) so your elements no more have the transition applied on them.
Here is what the official documentation has to say on that:
Adjusts sizes and positions when window is resized. Enabled by default
isResizeBound: true
The other piece of code is important in order for your elements to STILL move when you trigger the resize event.
Here is an example:
$(window).resize(function(){
isotope.isotope('layout');
});
});
Once you start resizing your window, because of this code, the elements will start to re-position themselves ( you will have that "instant bootstrap effect" and no more "isotope animation effect").
If you decide not to use the "window resize code event", you won't have the element re-positioning occurring (it will sort of gain the effect of an absolute positioned item).
One more thing, be sure to use the V2 isotope js library.
url: https://cdnjs.cloudflare.com/ajax/libs/jquery.isotope/2.2.1/isotope.pkgd.min.js
EDIT as I'm exploring a little bit more, there is also this piece of code which allows you to get your effect
percentPosition: true,
masonry: {
columnWidth: '.grid-sizer'
}
see the codepen example: http://codepen.io/desandro/pen/mIkhq
As I can see, there is a lot more here, but playing with this three things mentioned will definitely get you where you want.

Change Height of Navbar on Scroll Jquery with Bootstrap3

Hello i have a problem with my navbar.
I want to animate it on scroll and change his height. When i scroll a bit down it should animate smaller and when im at the top of the page it should aniamte bigger. The standard height is 100px. The problem is when im at the top of the page it takes a delay, which i need to wait, until it animates. They delays gets longer if i scroll first to the bottom of the page and then back to the top. The has a height of 11000px. This is my code for it:
$(document).on("scroll",function(){
if($(document).scrollTop()>500)
{
$( ".navbar" ).animate({height: 50} ,{duration:100});
}
else if($(document).scrollTop()==0)
{
alert("dhsihsp");
$( ".navbar" ).animate({height: 100} ,{duration:100});
}
});
Maybe u can help me. I use Google Chrome and Bootstrap 3.
The problem you are having is that the "scroll" fires every single time the scrollbar moves. So every single time the scrollbar moves a pixel, it will do the IF checks. That's why you delay your animation for so long. The queue of things to run stacks up immensely if you move the scrollbar too much.
DEMO
The scroll event seems to fire a lot when you scroll so all the events get queued. So the event that actually changes you header seems to take a long time to appear.
I added a css transition on the height of a .navbar. for making this happen almost instantly. Are the events not still there? True, but changing css is a lot less demanding then adding animations (with a duration of 100ms). The transition does have a duration but it does not have to finish so an other event can come in at any time.
CSS
.navbar {
transition: height 0.1s;
}
Jquery
$(window).scroll(function () {
var scrollh = $(this).scrollTop();
if (scrollh == 0) {
$(".navbar").css({
'height':'100px',
});
} else {
$(".navbar").css({
'height':'50px',
});
}
});

Small gaps on intitial masonry load, go away after window resize

http://staging.isaidicanshout.com/isics2014/
There are small 2-3 pixel gaps between all my tiles when masonry loads the first time, but they go away after resizing the window. Any help is appreciated!
Also, is there a way to get masonry to actively re-shuffle as the window is resized, rather than waiting for the user to complete the action?
Thanks!
I ended up discovering that the gaps were due to rounding. My tiles were set to 50% width of the page, so when the page was an odd number of pixels, gaps were revealed.
Guy didn't come back to answer this. Looks like he sorted it out though. For the lazy or if the link above dies.
You are going to need the imagesLoaded plugin. You should already have it if you use images as masonry + images doesn't work well with WebKit.
The magic which solves the border issue is to reload masonry once the images are loaded.
$(window).load(function(){
$('.container').masonry({
transitionDuration: 0,
itemSelector: '.photo-box'
}).imagesLoaded(function() {
$('.container').masonry('reloadItems').masonry();
});
});
Interestingly the code below doesn't work.
var container = $('.content');
container.imagesLoaded( function() {
container.masonry({
transitionDuration: 0,
itemSelector: '.photo-box'
});
});
Now we know. Well done OP for figuring this out.
What i figured out is that the window isn't re-sizing on its own for some reason hence the small gaps . This did the trick in my case .
document.addEventListener("click", function(){
$(window).trigger('resize');
});

jQuery div autoscroll

I am looking for advice on how to create an autoscrolling effect using jQuery which would enable an entire div within a page to begin scrolling vertically upon loading at a constant slow speed. This would be a div with a large amount of content of which only a small amount was visible on the screen at any one time.
The scroll needs to be automatic, smooth and at a defined rate for example 10 pixels per second. Additionally when the scroll gets to the bottom of the page I need to be able to call a function.
I have tried a few different jQuery plugins but found nothing yet that worked reliably. Can anybody suggest an approach to take here?
Thanks
Simon
This can easily be done without jquery.
function init() {
var div = document.getElementById("myDiv");
// increase the scroll position by 10 px every 10th of a second
setInterval(function() {
// make sure it's not at the bottom
if (div.scrollTop < div.scrollHeight - div.clientHeight)
div.scrollTop += 10; // move down
}, 100); // 100 milliseconds
}
Try this technique
try this plugin : scrollTo
especially the onAfter

Categories