Isotope with pagination, filters, lazyloading

Obada Qawwas
in - Javascript

Isotope with pagination

Today I’d like to share with you some experimental Isotope functions from a recent project I was working on, where we had to use Isotope with pagination functionality with filtering and lazy loading.

The idea was that we want to take each image and calculate its width and height from the original image file and reduce it to fit in its container and make some calculations to preserve the aspect ratio for images, after the images have been loaded we will init Isotope with its other functions.

Having several functions working in the same harmony could some time be such a pain, we can achieve a variety of dynamic work that can be controlled from HTML attributes and concerned about resizing and screens sizes.

I’m assuming for the sake of this post that you know Javascript not just familiar with it, but if there are any questions marks in your head, let me know and I can do a follow-up post 🙂

Attention: I didn’t have the time to check this functions on all browsers.

Features:

Isotope pagination.
Select filter, multi-select filter, and supports normal buttons filter.
Lazyloading and imagesloaded.
Function to calculate images’ width and height and type put it on img attributes.
Loader for images.
Define items per page and items per page for small screens from HTML attributes.
True false debugging function, instead of normal console.log.
Isotope with venobox modal popup image.
Dynamic pagination calculation.
Most of what I wrote is commented.
Multiple item types (Image, video, PDF) defined in CSS.
Ready to use.

Screenshots:
Isotope with pagination, filters, lazyloading
Isotope with pagination, filters, lazyloading
The HTML structure for an image element:

<!-- Gallery item -->
<div class="col-lg-4 col-md-4 col-sm-6 col-12 gallery-item-outer" data-filter="2017">
	<div class="gallery-item press">
		<a href="images/gallery/emre-gencer-62624.jpg" class="venobox" data-gall="Press">
			<img src="assets/images/blank.gif" data-original="images/gallery/thumbs/emre-gencer-62624.jpg" alt="">
		</a>
	</div>
</div>
<!-- /Gallery item -->
Change the number of showed images:

<div class="row gallery-items onyx-pagination" items-count="6" items-count-resp="4">

Chagne the ‘items-count’ attr’s value to whatever you want.

Some Javascript:

imagesToLoad: function(){
	var container = $(Onyx.isotopeGalleryPagination.selector),
		imagesToLoad = container.find("img"),
		imagesLength = imagesToLoad.length,
		count = 1;

	imagesToLoad.each(function () {

		var url = $(this).attr("data-original"), // Get image URL
			$this = $(this), // Refer to this
			img = new Image(), // Create a new image in memory
			imgWidth,
			imgHeight;

		// Start doing stuff when image is loaded
		img.onload = function(){
			imgWidth = this.width; // Assign image width
			imgHeight = this.height; // Assign image height

			// Start the resizing procedures
			var maxWidth = $this.parent().outerWidth(), // Max width for the image, and its responsive by the parent width... :D
				ratio = 0;  // Specify aspect ratio


			// Check if the current width is larger than the max
			if(imgWidth >= maxWidth){
				ratio = maxWidth / imgWidth; // get ratio value to scale image
				$this.attr("width", maxWidth); // Set new width
				$this.attr("height", imgHeight * ratio); // Scale height based on ratio
				imgHeight = imgHeight * ratio; // Reset height to match scaled image
				imgWidth = imgWidth * ratio; // Reset width to match scaled image
			}


			Onyx.log("Image width => "   this.width   ", Image height => "   this.height);

			/*
			 * Start Isotope magic after setting width and height for images
			 */
			var itemsInPage = (container.attr('items-count'))?parseInt(container.attr('items-count'), 10):15;
			if( count == imagesLength ) {
				Onyx.log("Items in page => "   itemsInPage);
				Onyx.isotopeGalleryPagination.initIsotope();
			}

			// Counter to fire Isotope after all images has been loaded
			count  ;

		}, img.onerror = function(){

			// If an image is missing this will increase the counter to fire Isotope functions
			count  ;

			// Obada - Debugging
			Onyx.log("This image has some error, and it may cause to pause the whole images loading => "   img.src);
		}

		img.src = url;

	});

},
References and Credits:

Photos by Emre Gencer on Unsplash
https://unsplash.com/photos/29sybIGm3-4
https://unsplash.com/photos/FxPfLIkEXHQ
https://unsplash.com/photos/2FdriJbrC5k
https://unsplash.com/photos/U0QuVfaipgo
https://unsplash.com/photos/YWzgBsbUKjE
https://unsplash.com/photos/3YQIQP0_R04
https://unsplash.com/photos/NZMeJsrMC8U
https://unsplash.com/photos/IyFGR2VdpFg
https://unsplash.com/photos/ou-8_lYwgh0
https://unsplash.com/photos/349fg_1XmzY
https://unsplash.com/photos/MTFPt08LoDQ
https://unsplash.com/photos/yZ5v4ZI0Ogc
https://unsplash.com/photos/153_VPk1NZQ
https://unsplash.com/photos/_ZUbtdWgOCc
https://unsplash.com/photos/mnwsyi4m3fc
https://unsplash.com/photos/8dEcwK1OIDY
https://unsplash.com/photos/88-VygK3gh0
https://unsplash.com/photos/1xaCkTx0liA
https://unsplash.com/photos/afMW77PAK_g
https://unsplash.com/photos/f5sdPmHPf5Q
https://unsplash.com/photos/XSM7TRzgvyg
https://unsplash.com/photos/UdqXIzwnwr4

Isotope
Ionicons
VenoBox
imagesLoaded

Comments (19)
  • mapi
    Wrote
    February 5, 2018 at 2:33 pm

    nice work thank you… im trying to implement it on a theme that uses newer jquery script v1.12.4, but when i change jquery from jour version (1.10.2) it just loads endlessly…
    so i order not to load two versions of jquery can you please show me how to do it for this new jquery version?
    thank you in advance
    mario

    • admin
      Replied to mapi
      February 5, 2018 at 6:29 pm

      I’m glad you liked my post.
      I don’t think the problem is from the jQuery version, I tried the version that you used and it’s working.
      I will send you the new one by e-mail and try to take a look at the console in Chrome Dev Tools to see if there is an error, if you found an error tell me and maybe I can help you.

      Regards

  • mapi
    Wrote
    February 10, 2018 at 8:43 am

    You˙re right, it must be something else, some other scripts on my site…Thank you for your time… 🙂

  • Hamid
    Wrote
    April 6, 2018 at 7:32 am

    Hey, you did good man but I m stuck in the integration of this code in my WordPress theme.I want buttons instead of select and each button represents post of archive

    • admin
      Replied to Hamid
      April 6, 2018 at 10:01 pm

      I’m glad you liked my nugget 🙂
      Actually, I didn’t get exactly what you want to achieve, but I think you can’t integrate this with WordPress, it’s a different concept, in WordPress you can’t show too many posts in a single page because it’s gonna be very heavy, maybe you can handle it with Ajax calls and get more posts.
      Take a look at this pen https://codepen.io/desandro/pen/JEojz they made filters combinations with buttons.
      Send me your project link and maybe I can give you some help…

      Regards

  • Hamid
    Wrote
    April 25, 2018 at 6:42 am

    Sorry for late reply. I was busy you are right about WordPress can’t handle too many posts on a single page because its gonna be very heavy.But I want pagination in isotope and buttons of different galleries instead of the drop-down.

    • admin
      Replied to Hamid
      May 2, 2018 at 6:36 am

      If the problem that you’re facing is just the buttons, so the link that I’ve sent will handle your request 🙂
      Wish you the best with your site

  • abu
    Wrote
    May 7, 2018 at 7:08 pm

    Hi,
    Thank you for your effort. i really like this functionality. how to change number of items per page. i think now 6 items per page. please let me know solution.

    • admin
      Replied to abu
      May 17, 2018 at 7:50 am

      Hi, You can change it from the HTML file, by changing the attr items-count to the number you want to show… take a look at the screenshot https://goo.gl/QjDMJw

  • Iansky
    Wrote
    July 16, 2018 at 10:56 am

    Hi Sir, do you have example for two filters with pagination? by the way thank you for this plugins!

    • admin
      Replied to Iansky
      July 16, 2018 at 11:20 am

      Hello,
      I’m glad you like it.
      Unfortunately, I didn’t prepare a version with two filters and pagination, but I will try my best to do it as soon as possible.
      Regards

  • Nello Carnevale
    Wrote
    February 20, 2019 at 4:30 pm

    Hi, Thank you for your effort. i really like this functionality, but i have a problem in the mobile version.
    When I scroll the page on mobile device (smartphone) the pagination is reset and always shows page 1.
    You can see the effect here:
    https://www.aisveneto.it/video2.html

    • admin
      Replied to Nello Carnevale
      February 21, 2019 at 7:07 am

      Hi Nello,
      I’m glad you liked my article…
      you applied it very well on your website but I didn’t see something wrong with it, if you opened it on a big screen and then changed the size of the screen, of course, it will reset to the first page because it’s pagination with Javascript and this is the expected behavior, but, if you opened it directly from mobile and tried to change the pages it works fine, is there anything I’m missing?
      please correct me if I got you wrong…

  • Ciceron
    Wrote
    March 23, 2019 at 4:12 pm

    Awesome ! Works Perfectly. Thank you soooo much. Would it be possible to have an example with two filters and pagination ? Thanks again

    • admin
      Replied to Ciceron
      May 2, 2019 at 12:43 pm

      Hey Ciceron,

      I’ll consider adding this feature in a future update, have a nice day

  • Yuri Peixoto
    Wrote
    March 25, 2020 at 4:13 pm

    Hi master. Great tutorial, and awesome example. I have a doubt, because of my lack of js knowledge: how could I use it with “a” button elements, instead of a selector?

  • Pavel
    Wrote
    April 25, 2020 at 7:11 pm

    Hello. How do you add buttons back and forth in pagination? Example ” [Back] [1] [2] [3] [4] [Next]” Thanks in advance!

    • admin
      Replied to Pavel
      June 26, 2020 at 7:52 am

      Sorry but I don’t have the time to develop it more, but, you may find examples on Codepen that can help you with it.

Please enable Javascript in order to post comments.