Back to blog home

Magento jQuery lazyload extension

Hello to everybody, my name in Raffaele Pannisco and today I’m here to guide you through a new magento extension implementation. This is the first blog post so at the beginning we are going to start with something that is pretty simple but at the same time very useful.

In fact we are going to cover several basic aspects:

  • basic magento module creation
  • module system config for backend
  • module helper
  • template override
  • custom frontend xml layout

But now let’s start.

1. Requirements

Write a module that enable lazyload jQuery plugin (see here) on catalog list page. The module must have a backend configuration that allows to disable/enable this feature.

2. Module implementation:

First of all we need to create our module config. As namespace we use Namespace and as modulename we use Lazyload.

<!-- app/etc/modules/Namespace_Lazyload.xml -->
<?xml version="1.0"?>
<config>
    <modules>
        < Namespace_Lazyload>
            <active>true</active>
community
        </ Namespace _Lazyload>
    </modules>
</config>

 

Now it’s time to create folder structure. Please create these folders/files:

  • app/code/community/Namespace/Lazyload/
  • app/code/community/Namespace/Lazyload/Helper/Data.php
  • app/code/community/Namespace/Lazyload/etc/config.xml
  • app/code/community/Namespace/Lazyload/etc/system.xml

 

As you can see we are going to create an helper and all needed xml configs.

The first one to take care of is config.xml

<!-- app/code/community/Namespace/Lazyload/etc/config.xml -->
<?xml version="1.0"?>
<config>
    <modules>
        <Namespace_Lazyload>
            <version>1.0.0</version>
        </Namespace_Lazyload>
    </modules>
    <global> 
       <!--here we are telling to magento that this module has an helper -->
        <helpers>
            <lazyload>
                <class>Namespace_Lazyload_Helper</class>
            </lazyload>
        </helpers>
         <!-- end  -->
    </global>
    <frontend>
        <layout>
            <!--here we are declaring that we are going to use a custom xml layout file -->
            <updates>
                <lazyload>
                    <file>namespace/lazyload.xml</file>
                </lazyload>
            </updates>
            <!-- end  -->
        </layout>
    </frontend>
    <default>
        <!-- here we set the default module config for backend   -->
        <lazyload>
            <general>
                <!-- we want to enable it manually so we set jqueryEnabled and lazyloadEnabled to 0. These tags come from the system.xml config-->
    <jqueryEnabled>0</jqueryEnabled>
                <lazyloadEnabled>0</lazyloadEnabled>
                 <!-- end  -->
            </general>
        </lazyload>
        <!-- end  -->
    </default>
    <adminhtml>
        <!-- here we are declaring the module permissions. Without acl the backend configuration section will throw an access denied error. -->
        <acl>
            <resources>
                <admin>
                    <children>
                        <system>
                            <children>
                                <config>
                                    <children>
                                        <lazyload>
                                            <title>Lazyload Library</title>
                                        </lazyload>
                                    </children>
                                </config>
                            </children>
                        </system>
                    </children>
                </admin>
            </resources>
        </acl>
        <!-- end  -->
    </adminhtml>
</config>

 

If you need an official reference for the admin configuration you can find it here.

By the way in system.xml we declared where to find our module backoffice configuration section.
jqueryEnabled and lazyloadEnabled are our two boolean config that we will use for enable/disable jQuery library and lazy load plugin.

Now it's time to create our helper class and a method we use to check if the lazy load config is enabled or not. We need this because we have to include in our template file a javascript call and if we don't put a control the page will throw a javascript error.

<!-- app/code/community/Namespace/Lazyload/Helper/Data.php -->
<?php
class Namespace_Lazyload_Helper_Data extends Mage_Core_Helper_Abstract {
    
    public function isEnabled() {
        
        return Mage::getStoreConfig('lazyload/general/lazyloadEnabled');
    }
}

Mage::getStoreConfig() is a method that returns the value of config path sections/groups/fields.

OK, the module now has configs and helper, it's time to prepare the frontend part.

First of all we need to place our javascript files(query lib,query no conflict and lazyload).

  • js/Namespace/Jquery/jquery-1.9.1.min.js
  • js/Namespace/Jquery/jquery.conflict.js
  • js/Namespace/Jquery/jquery.lazyload.js

and we are going also to add a css file that we can use to put all lazyload related style customization.

/*
* skin/frontend/default/default/css/namespace/lazyload/lazyload.css
* use this to customized lazyload related style
*/
.catalog-category-view .page .col-main .category-products .products-grid li a.product-image {
    background-image: url('../../../images/opc-ajax-loader.gif');
    background-repeat: no-repeat;
    background-position: 50%;
}

 

I added a small style rule to set the magento default loading gif. It will be visible during image loading.
We need also to add a small transparent 1x1px gif used as placeholder.

skin/frontend/default/default/images/namespace/lazyload/loading.gif

Ok now it's time to prepare our custom template file, this because we have to modify the product image html with additional attributes needed by lazyload lib. Basically the image expected html code is:

<img class="lazyload" data-original="product_image_url" src="transparent_gif_1x1" width="135" height="135" alt="description" >

 

We need also to add a javascript plugin call:

jQuery("img.lazyload").lazyload();

OK let's copy app/design/frontend/base/default/template/catalog/product/list.phtml to app/design/frontend/default/default/template/namespace/catalog/product/list-custom.phtml.

Change


<img src="<?php echo $this->helper('catalog/image')->init($_product, 'small_image')->resize(135); ?>" width="135" height="135" alt="<?php echo $this->stripTags($this->getImageLabel($_product, 'small_image'), null, true) ?>" />
1
	
<img src="<?php echo $this->helper('catalog/image')->init($_product, 'small_image')->resize(135); ?>" width="135" height="135" alt="<?php echo $this->stripTags($this->getImageLabel($_product, 'small_image'), null, true) ?>" />

to

<img class="lazyload" data-original="<?php echo $this->helper('catalog/image')->init($_product, 'small_image')->resize(135); ?>" src="<?php echo $this->getSkinUrl('images/lazyload/loading.gif') ?>" width="135" height="135" alt="<?php echo $this->stripTags($this->getImageLabel($_product, 'small_image'), null, true) ?>" />

 

and at the end add


PHP
<?php if (Mage::helper('lazyload')->isEnabled() == 1): ?> <script type="text/javascript"> jQuery("img.lazyload").lazyload(); </script> <?php endif; ?>
1
2
3
4
5
	
<?php if (Mage::helper('lazyload')->isEnabled() == 1): ?>
    <script type="text/javascript">
        jQuery("img.lazyload").lazyload();
    </script>
<?php endif; ?>

We changed list-custom.phtml to generate the needed html code.
We also added a control that checks if lazyload is enabled from backoffice using our helper method isEnabled.

Ok, there is a last missing thing to do. Actually we have a module, we have a custom template, we have js, css in place but magento is not able to see that we want to use our custom phtml template file instead of the default one (list.phtml) and we have also to include our js/css files in the catalog list page.

So let's create our custom xml layout file

<!-- app/design/frontend/default/default/layout/namespace/lazyload.xml -->
<?xml version="1.0"?>
<layout version="0.1.0">
    <default>
        <reference name="head">
            <!-- if jqueryEnabled == 1 we include jquery lib -->
            <action method="addJs" ifconfig="lazyload/general/jqueryEnabled">
                <script>Namespace/Jquery/jquery-1.9.1.min.js</script>
            </action>
            <!-- if jqueryEnabled == 1 we include jquery no conflict -->
            <action method="addJs" ifconfig="lazyload/general/jqueryEnabled">
                <script>Namespace/Jquery/jquery.conflict.js</script>
            </action>   
            <!-- if lazyloadEnabled == 1 we include lazyload plugin -->         
            <action method="addJs" ifconfig="lazyload/general/lazyloadEnabled">
                <script>Namespace/Jquery/jquery.lazyload.js</script>
            </action>
            <!-- if lazyloadEnabled == 1 we include lazyload css -->  
            <action method="addItem" ifconfig="lazyload/general/lazyloadEnabled">
                <type>skin_css</type>
                <name>css/namespace/lazyload/lazyload.css</name>
            </action>
        </reference>
    </default>
    
    <catalog_category_layered>
        <reference name="product_list">
            <!-- if lazyloadEnabled==1 we override list.phtml with our list-custom.phtml. This is not really needed as we already put an if condition to check if the module is enabled but avoiding to load a custom template when the module is disabled is a better idea -->
            <action method="setTemplate" ifconfig="lazyload/general/lazyloadEnabled">
                <template>magespot/lazyload/catalog/product/list-custom.phtml</template>
            </action>
        </reference>
    </catalog_category_layered>
</layout>

 

We finally finished our module.
Under System / Configuration / Namespace Extensions / Lazyload extension / Lazyload library we can enable and disable our module.

Do you want to make a new exercise? Try to create a new module that include a js lib following this tutorial, it's easy!

See you on the next tutorial!