Designed for everything
Lazy supports images and backgrounds by default or any other content by plugins and custom loaders you like to implement.
A lightweight but powerful delayed content, image and background lazy-loading plugin for jQuery & Zepto
Lazy is a fast, feature-rich, extensible and lightweight delayed content loading plugin for jQuery & Zepto. It's designed to speed up page loading times and decrease traffic to your customers and users by only loading the content in view.
Lazy supports images and backgrounds by default or any other content by plugins and custom loaders you like to implement.
Lazy will decrease your development time and save traffic and loading times for your users and customers.
You can use Lazy in all vertical and horizontal scroll ways, it will only load the elements in threshold.
Lazy works well on every tested mobile devices so far and supports retina and other high density displays as well.
Lazy delivers a mighty configuration, many callbacks, public functions and custom loaders for full control on everything.
All sources are available on GitHub. Feel free to report bugs, ask for new features or even contribute to Lazy by yourself there!
First of all, you will need a copy of jQuery or Zepto to use Lazy successfully in your project. If you get this you can install Lazy by different ways. Select your favorite below.
Download and save one of two available files to include Lazy to your page, either the development or the minified version beside of jQuery.
<script type="text/javascript" src="jquery.lazy.min.js"></script>
Lazy and all Plugins are available over cdnjs and jsDelivr CDN and can be directly included to every page.
<!-- jsDeliver -->
<script type="text/javascript" src="//cdn.jsdelivr.net/jquery.lazy/1.7.9/jquery.lazy.min.js"></script>
<script type="text/javascript" src="//cdn.jsdelivr.net/jquery.lazy/1.7.9/jquery.lazy.plugins.min.js"></script>
<!-- cdnjs -->
<script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/jquery.lazy/1.7.9/jquery.lazy.min.js"></script>
<script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/jquery.lazy/1.7.9/jquery.lazy.plugins.min.js"></script>
The basic usage of Lazy ist pretty easy. Just prepare your elements and add a little snippet to your page.
Prepare the elements you want to lazy load. By default add a data-src attribute to elements containing the loadable image or a data-loader attribute to elements witch shall use a plugin or custom loaders.
<!-- load images the lazy way -->
<img class="lazy" data-src="path/to/image.jpg" />
<!-- load background images of other element types -->
<div class="lazy" data-src="path/to/image.jpg"></div>
Start using Lazy by calling it after page load. Try to use a most exact jQuery selector as possible for better performance.
$(function() {
$('.lazy').Lazy();
});
Lazy comes with a bunch of easy to use configuration options by default, to control nearly every behavior as you like. The following parameters are available on every instance:
Name | Type | Default | Description |
---|---|---|---|
name | string | lazy | Internal name, used for namespaces and bindings. |
chainable | boolean | true | By default Lazy is chainable and will return all elements. If set to false Lazy will return the created plugin instance itself for further use. |
autoDestroy | boolean | true | Will automatically destroy the instance when no further elements are available to handle. |
bind | string | load | If set to load Lazy starts working directly after page load. If you want to use Lazy on own events set it to event. |
threshold | integer | 500 | Amount of pixels below the viewport, in which all images gets loaded before the user sees them. |
visibleOnly | boolean | false | Determine if only visible elements should be load. |
appendScroll | object | window | An element to listen on for scroll events, useful when images are stored in a container. |
scrollDirection | string | both | Determines the handles scroll direction. Possible values are both, vertical and horizontal. |
imageBase | string | null | If defined this will be used as base path for all images loaded by this instance. |
defaultImage | string | blank image | Base64 image string, set as default image source for every image without a predefined source attribute. |
placeholder | string | null | Base64 image string, set a background on every element as loading placeholder. |
delay | integer | -1 | If you want to load all elements at once after page load, then you can specify a delay time in milliseconds. |
combined | boolean | false | With this parameter, Lazy will combine the event driven and delayed element loading. |
Name | Type | Default | Description |
---|---|---|---|
attribute | string | data-src | Name of the image tag src attribute, where the image path is stored. |
srcsetAttribute | string | data-srcset | Name of the image tag srcset attribute, where the source set is stored. |
sizesAttribute | string | data-sizes | Name of the image tag sizes attribute, where the size definition for source set is stored. |
retinaAttribute | string | data-retina | Name of the image tag attribute, where the path for optional retina image is stored. |
loaderAttribute | string | data-loader | Name or the element attribute, where the identifier of the plugin or customer loader is sored. |
imageBaseAttribute | string | data-imagebase | Name ot the image tag element, where the specific image base is stored. This will overwrite the global imageBase config. |
removeAttribute | boolean | true | Determine if the attribute should be removed from the element after loading. |
handledName | string | handled | Name of the element tag data attribute, to determine if element is already handled. |
loadedName | string | loaded | Name of the element tag data attribute, to determine if element is already loaded. |
Name | Type | Default | Description |
---|---|---|---|
effect | string | show | Function name of the effect you want to use to show the loaded images, like show or fadein. |
effectTime | integer | 0 | Time in milliseconds the effect should use to view the image. |
Name | Type | Default | Description |
---|---|---|---|
enableThrottle | boolean | true | Throttle down the loading calls on scrolling event. |
throttle | integer | 250 | Time in milliseconds the throttle will use to limit the loading calls. |
Name | Type | Default | Description |
---|---|---|---|
beforeLoad | function | undefined | Callback function, which will be called before the element gets loaded. Has current element and response function as parameters. this is the current Lazy instance. |
afterLoad | function | undefined | Callback function, which will be called after the element was loaded. Has current element and response function as parameters. this is the current Lazy instance. |
onLoad | function | undefined | Callback function, which will be called if the element could not be loaded. Has current element and response function as parameters. this is the current Lazy instance. |
onFinishedAll | function | undefined | Callback function, which will be called after all elements was loaded or returned an error. This callback has no parameters. this is the current Lazy instance. |
Configure your Lazy instances with an initial configuration object:
$('.lazy').Lazy({
// your configuration goes here
scrollDirection: 'vertical',
effect: 'fadeIn',
visibleOnly: true,
onError: function(element) {
console.log('error loading ' + element.data('src'));
}
});
Or read and change the configuration live at runtime with the public config function. Please note the chainable parameter!
var lazy = $('.lazy').Lazy({ chainable: false });
var attributeName = lazy.config('attribute'); // get
lazy.config('effect', 'show'); // set
Lazy comes with a bunch of callbacks and events you can assign to. Just add them by initialization configuration to your instances
An list of all callbacks available by default:
Name | Parameters | Trigger |
---|---|---|
beforeLoad | {object} element | before an element is about to be handled |
afterLoad | {object} element | after an element was handled successfully |
onError | {object} element | whenever an element could not be handled |
onFinishedAll | none | after all items in this instance was handled or returned an error |
Simply attach a function to all callbacks you want to use by initialisation. The element parameter is already an jQuery or Zepto object, so you can use it directly like element.addClass('handled').
$(".lazy").Lazy({
beforeLoad: function(element) {
// called before an elements gets handled
},
afterLoad: function(element) {
// called after an element was successfully handled
},
onError: function(element) {
// called whenever an element could not be handled
},
onFinishedAll: function() {
// called once all elements was handled
}
});
this is the current Lazy instance itself, so you can access everything like public function or configuration directly.
$(".lazy").Lazy({
onFinishedAll: function() {
if( !this.config("autoDestroy") )
this.destroy();
}
});
Lazy supports multiple parallel instances. Just initialize them with different selectors and possible different configurations.
An list of all available public functions:
Name | Parameter | Description |
---|---|---|
config | {string} entryName[, {string} newValue] | get or set an configuration entry |
addItems | {string|object} items | add new items to current instance |
getItems | none | get all unhandled items left of current instance |
update | [{boolean} useThrottle] | loads all elements in current viewport |
force | {string|object} items | force loading of specific items ignoring the viewport |
loadAll | none | loads all remaining available elements from this instance |
destroy | none | unbinds all events and stop execution directly |
To access an instances public functions you can initialize them in an object oriented manner or grab the instance bind to every element by default.
// object oriented way, note the chainable parameter
var instance = $('.lazy').Lazy({ chainable: false });
// grab from elements
// only works well if you use same selector or a single instance overall
$('.lazy').Lazy();
var instance = $('.lazy').data("plugin_lazy");
The public functions config and addItems has some multiple functionality.
// 'config' can receive entries or set them to a new value
var value = instance.config('attribute');
instance.config('attribute', 'data-new-attribute');
// 'addItems' works with an jQuery object or any selector
// so these two lines have the exact same result
instance.addItems('img.new-items');
instance.addItems($('img.new-items'));
With the custom loaders option there is a powerful solution to load every contents the Lazy way. The plugin will handle everything, you just create a loading method witch got triggered whenever the element hits the visibility threshold. It's still possible to load images and custom loaders in the same Lazy instance.
To use a custom loader just define a name and function inside the Lazy initialisation. The first parameter is always a jQuery or Zepto DOM object, representing the element you want to lazy load.
$('.lazy').Lazy({
customLoaderName: function(element) {
element.html('element handled by "customLoaderName"');
element.load();
},
asyncLoader: function(element, response) {
setTimeout(function() {
element.html('element handled by "asyncLoader"');
response(true);
}, 1000);
}
});
Pass the loader name you want to use for this element to the data-loader attribute of those who should be lazy loaded. You can mix custom loaders and images in the same Lazy instance as well.
<div class="lazy" data-loader="customLoaderName"></div>
<img class="lazy" data-src="path/to/image.jpg" />
<div class="lazy" data-loader="customLoaderName"></div>
<div class="lazy" data-loader="asyncLoader"></div>
Custom loaders can respond it's state back to the plugin. This is highly necessary when you want to use one of the callbacks afterLoad, onError or onFinishedAll beside of your loaders.
Therefor you can either use jQuery's build-in functions load and error, or the response function, given as second parameter to your custom loaders. Both ways do exactly the same, so you only had to choose one of them.
Note: Zepto could not use the function load and may throw errors in the console. Use the response function instead, if you're working with Zepto.
// jQuery's build-in functions
$('.lazy').Lazy({
successLoader: function(element) {
element.load();
},
errorLoader: function(element) {
element.error();
}
});
// response callback function
// best use for working with Zepto
$('.lazy').Lazy({
successLoader: function(element, response) {
response(true);
},
errorLoader: function(element, response) {
response(false);
}
});
The loader plugins for Lazy can be used whenever you want to extend the basic functionality by default or globally for many instances of Lazy.
Just add the plugins you want to use or a combined file, containing all plugins, to your page and all instances can use the plugins from now on.
<!-- as single plugin files -->
<script type="text/javascript" src="jquery.lazy.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.ajax.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.av.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.iframe.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.noop.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.picture.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.script.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.vimeo.min.js"></script>
<script type="text/javascript" src="plugins/jquery.lazy.youtube.min.js"></script>
<!-- or combined in one plugin file -->
<script type="text/javascript" src="jquery.lazy.min.js"></script>
<script type="text/javascript" src="jquery.lazy.plugins.min.js"></script>
Using a plugin on an element is just the same as with custom loaders. Add the attribute data-loader (by default) with the plugin name to the specific elements.
<!-- element will be handled by 'ajax' plugin -->
<div data-loader="ajax" data-src="file.html"></div>
If you create or use a plugin witch is set to specific html element types by default, like our AV plugin, there is no need to add a data-loader attribute.
<!-- this element will automatically be handled by the 'av' plugin -->
<audio>
<data-src src="file.ogg" type="audio/ogg"></data-src>
<data-src src="file.mp3" type="audio/mp3"></data-src>
<data-src src="file.wav" type="audio/wav"></data-src>
</audio>
A list of all available plugins, created by the Lazy developers. For more details about the single plugins, take a look in the plugin folder inside the Lazy GitHub repository.
Name | Aliases | Parameter | Default For |
---|---|---|---|
AJAX | ajax, get, post | data-src, data-method, data-type | - |
AV | av, audio, video | data-src, data-poster | <audio>, <video> |
iFrame | frame, iframe | data-src, data-error-detect | <iframe> |
NOOP | noop, noop-success, noop-error | - | - |
Picture | pic, picture | data-src, data-srcset, data-media, data-sizes | <picture> |
Script | js, javascript, script | data-src | <script> |
Vimeo | vimeo | data-src | - |
YouTube | yt, youtube | data-src | - |
If you want to, you can easily create own loader plugins. Just use jQuery or Zepto's public function Lazy to create and register them.
The first parameter is the name of your plugin as string, or an array of names / aliases. Second parameter is the loader function, witch is the same as in custom loaders. Best practice is to wrap everything by an IIFE.
(function($) {
$.Lazy('pluginName', function(element, response) {
// add your whole logic here
// 'this' is the current instance of Lazy
// so it's possible to access all public functions, like:
var imageBase = this.config('imageBase');
});
})(window.jQuery || window.Zepto);
The optional second parameter gives you the ability to register a plugin by default to html element types. When you do this, there is no need to set the data-loader attribute on each element you want to use this loader on.
But keep in mind, if you register an plugin on often used elements, like <div>, Lazy will try to handle each of them, every time! If you want to do so anyway, use a most specific selector for jQuery or Zepto.
(function($) {
$.Lazy('av', ['audio', 'video'], function(element, response) {
// this plugin will automatically handle '<audio>' and '<video> elements,
// even when no 'data-loader' attribute was set on the elements
});
})(window.jQuery || window.Zepto);
Working with Zepto has a little special behavior. Zepto could not use the function load on elements and may throw errors in the console. Use the response function instead, if you're working with Zepto or writing a plugin for publicity.
(function($) {
$.Lazy('pluginName', function(element, response) {
if( loaded ) {
// is the same as 'element.load();'
response(true);
}
else {
// is the same as 'element.error();'
response(false);
}
});
})(window.jQuery || window.Zepto);
I hope you will find this plugin useful.
Feel free to get in touch with me if you have any questions or suggestions.