JavaScript Tutorial Newsletter Do you want to learn how to write code? This is an independent code programming tutorial website. All tutorials are written and distributed for free to whosoever wishes to sign up. There are no ads. Please support us by subscribing to LearnjQuery.org free tutorial updates newsletter.



Join other 5 subscribers

Creating jQuery Plugins

TABLE OF CONTENTS - In This Edition:

Introduction

Do you want to learn how to develop your own, custom jQuery plug-ins? This edition of my newsletter is designed to help you out.

This tutorial assumes at least basic knowledge of Javascript. A lot of people get into jQuery development too quickly, without learning some of the most important things about Javascript first.

One of those things is the concept of an object. I am sure you have heard about objects before, but if you haven't, I strongly recommend doing a Google search on the subject. Objects are fundamental blocks of Object-Oriented Programming (OOP) which has its roots in other languages.

In order to really understand plugin development, you need to know how Javascript objects work.

When you learn plug-in development, it is a good idea to do a great deal of your own experiments. Don't copy and paste source code from examples written by others. Instead, make an attempt to really understand how it works by writing your own code from scratch.

The image below explains two possible ways of developing plug-ins, by either creating a stand-alone object that will use jQuery library in its implementation, or by extending the existing jQuery object. How you choose to do it is a matter of approach.

Possible jQuery plug-in models, they simply extend existing objects or you can create a stand-alone plug-in object.

Creating a jQuery plug-in is nothing more than extending functionality of Javascript objects. You can create your own stand-alone plug-in object, or you can extend the main jQuery object by implementing your own functions, event handlers and other user interface behavior. Everything in Javascript is an object so, your plug-in and jQuery itself are objects too.

At the very least you will need to know what a Javascript object is. A few examples of objects would be String, Date and Array. There are others.

Understanding Javascript objects

You may already be used to creating and calling Javascript functions. Functions are objects in Javascript. This is an incredibly important concept you'll want to understand. Even if you know objects from other languages such as C++, Javascript objects are slightly different in how they operate.

Because functions are objects, we can create handles to functions. These handles will be named whatever we want our object to he named. We can later extend this object. Let's see how we can create a custom object:

var myObject = function(param1, param2) { /* Do something */ };

You have just created your own object called myObject. Notice the semicolon at the end of this definition.

At the core of any Javascript library, there lies the main object. This object is created in the same exact way as you just created myObject.

Main jQuery library object

Now, let's take a look at the definition of the main jQuery object:

var jQuery = window.jQuery = window.$ = function(selector, context) { /* Do something */ };

Of course, the /* Do something */ part contains the definitions of the entire jQuery library, containing popular functions such as css(), click() and animate(). We will get to these in the upcoming episodes of this newsletter and analyze them in more detail.

The great thing about objects in any language is that it is possible to extend them, add our own variables and functions to them. jQuery is an extension of Javascript. You can think of jQuery itself as a plug-in for Javascript!

Notice that in the definition above, jQuery also equals window.jQuery and window.$. This means that one object is created and can be accessed using any of the 3 variable names. When we use the main library object by its name: jQuery(), it is the same as using $(), window.$() or window.jQuery(). Remember that in Javascript the keyword "window" is a pre-created object that refers to the global scope of the Javascript application you are writing. Every time you create a variable such as x = 1, it automatically becomes accessible through its equivalent window.x

The same holds true for the dollar sign. The dollar sign is just a variable name. It just looks weird. If jQuery library was assigned to the variable with the name x, we would be calling jQuery commands using the x, as in: x('#div').hide(). But because this variable was assigned to the dollar sign character (which is a valid variable name in Javascript) that's what we use: $('#div').hide();

Try it yourself in a blank Javscript file. Assign var $ = 1; and display it with an alert box as in: alert($). You will see that the dollar sign is nothing more than just a variable name, just like any others. It is not special at all. It can even be used in combination with other characters, for example: var Dollar$ = 10; It just looks odd when the variable name consists of just the dollar sign ($) by itself, but there really isn't a difference between it and any other regular variable. Many beginners seem to be confused by it. Now you know what it means.

So why did people at jQuery decide to use it? Well, sometimes you want to use jQuery with other libraries. By using an incredibly unique name for the library the creators avoid conflicts with other libraries or functions you may want to use together with jQuery. Generally, if you are planning on using other libraries that you have not written, the dollar sign ($) will prevent conflicts with other things. If everyone named their Javascript libraries "my_library", then variable names would clash, making it impossible to use together. The dollar sign prevents that from happening. This is also why you should never create your own variables and name them dollar sign.

Think the dollar sign was weird? Javascript allows a number of obscure characters to be used in variable names. Surprisingly, the following are all valid definitions that will compile and execute correctly:

var func1 = function() { alert("hello from func1"); } func1.func2 = function() { alert("hello from func1.func2"); }; var _ = function() { alert("hello from _"); } var \\u0024 = function() { alert("hello from $ defined as \u0024"); } var Ø = function() { alert("hello from Ø"); } var $$$$$ = function() { alert("hello from $$$$$"); } func1(); func1.func2(); _(); $(); Ø(); $$$$$();

If you want to see other odd characters Javascript allows us to use in variable names, visit my article: jQuery and the Dollar Sign, where you will find many examples at the bottom of the page.

Now let's get back to the jQuery object creation example.

var jQuery = window.jQuery = window.$ = function(selector, context)

Notice that parameters selector and context are passed to the jQuery object that has just been created. The selector parameter is the CSS selector. We pass a text string that asks jQuery to select an element. When that happens, this function will return a handle to the selected element, or its location in computer memory.

Let's take a look at a practical example of what this jQuery object allows us to do:

jQuery("div").hide();

The above function will find all DIV elements on the page and hide them. The jQuery function hide() itself is sort of like a mini plug-in. It hides elements by applying the CSS style code "display:none", that I am sure you have already seen and used yourself in your own CSS code.

You can extend jQuery functionality by adding your own function that hides an element in your own way. For example, you could add a function called hideitmyway(); that could hide an element by applying "visibility: hidden", instead of "display:none", like the original function. And this is what's at the essence of developing jQuery plug-ins. You extend its functionality by adding your own functions.

These plug-ins you will write are not limited to a single function. You can create an entire image gallery plug-in that turns DIV elements into scrollable blocks containing images passed as parameters to your plug in. For example:

var ImageGallery = function(target_container, image_list) { ... };

And you could initialize this plug-in by writing the following code:

ImageGallery("#container", "myimage.jpg, anotherone.png, mycat.gif");

Okay, so this will just call a function you assigned to an object. What's next?

Knowing how to assign a function to an object, we are one step closer to truly understanding how jQuery plug-ins work. Let's discover what code patterns are available to us in order to make our first plug-in.

Where does plug-in code really begin execution?

As explained in my jQuery plug-in pattern tutorial for beginners, there are two common code patterns you can use to develop functionality you are looking for.

You can stick to the pattern names as I explain them in my article on my website: pattern A and B. But in this tutorial I will focus more on the pattern B, because it is the simpler one from the two.

Before we can tackle any plug-in development pattern, let's see where the entry point of our plug-in is.

Remember from a few paragraphs above I talked about window.x being the same as var x? Well, not only variables but also objects are defined in the same way in Javascript. And there are a few objects that already exist. For example, you are already familiar with the HTML body tag's onload attribute:

<body onload = "alert('Hello!')">...

Well, this isn't the only way to add code on the event of page load. The Javascript way of doing this would be:

// Override the body tag onload event window.onload = function() { /* The page finished loading. Do something... */ }

Remember that part in your HTML page that says BODY ONLOAD = "..."? Assigning window.onload to a brand new function like in the example above, is the same as placing Javascript code into BODY ONLOAD = "...here...". Just make sure that you are calling window.onload from SCRIPT tag, somewhere in the HEAD tag of your webpage.A lot of people don't know that the word "onload" in the body tag is officially called an attribute of the body tag. If you want to take jQuery development seriously, remember that these names are called attributes, and not just things inside an HTML tag. I know it sounds like a simple thing, but jQuery has a function called attr() that looks up the value of that attribute. So, it's important to know what attributes are, and continue refering to them by their names.

Important: If you have some Javascript code in your HTML within the "onload" attribute of the body tag, that code will overwrite your window.onload function! And your window.onload code will not execute. So, be careful about using windown.onload together with body onload to avoid this conflict. Usually, you want to avoid using the onload attribute by all means, however, I have encountered a few cases where I had no choice but to use it. But the general rule is that if you can, avoid using it. Override the javascript.load with your own function instead.

What came first: egg or chicken?

I mean, HTML's body "onload" attribute or window.onload? Which one will execute first? You can add your own window.onload function, but as was just discussed above, the code in your body's "onload" attribute will overwrite it.

Well, guess what? In the greater scope of things, neither egg nor chicken came first. In this instance, to initialize jQuery plug-ins, we use a completely different type of an egg.

I am talking about the "on document load" function. It executes before both body "onload" code and window.onload. So what is this "on document load" then? This is the place where we initialize our plug-in. The "on document load" function is defined below, among other functions we have just discussed. Let's see the order in which things will execute:

<html> <head> <script type = "text/javascript" src = "https://ajax.googleapis.com/ajax/libs/jquery/1.5.2/jquery.min.js"></script> <script type="text/javascript"> window.onload = function() { alert("window"); // Will not execute (overwritten by body onload below!) }; $(document).ready(function() { alert("document ready"); // 1st to execute }); </script> </head> <body onload = "alert('I just overwrote window.onload')"> <!-- 2nd to execute //-->

The reason I wanted to put it together like this is to show you the spider web of execution flow, which many people might get confused about, if they don't fully understand it. If you remove onload attribute from the body tag from the example above, then window.onload will start to execute again, because it will no longer be overwritten (or overridden, as is the case with objects).

But anyway, we initialize our plug in inside document on ready function, presented to us as part of the jQuery library.

Why did developers of jQuery create Document Ready?

Well, "Document Ready" functionality already exists in various browsers. The problem is that in order to take advantage of it, you have to write code that looks different for each browser. Unless you are using jQuery.

Why do we even need Document Ready? Can't we just use the popular onload event as an attribute of the body tag, or as a window.onload function? We can, but it is not desired.

In order to understand this, you need to know what DOM is. DOM is the Document Object Model. I am sure you are already familiar with the concept known as HTML tag nesting, which simply means that some tags must be defined inside other tags, and so forth.

Well, the DOM is the model that keeps track of all of the elements as a tree of data. Mostly for internal processing, but in recent years the knowledge of DOM has significantly gained popularity with the advent of jQuery and dynamic web applications, especially ones that are built as graphic user interfaces, also known as GUI, or simply UI.

Respect the DOM

As an example of DOM, consider DIV A, B and C. If DIV B is inside DIV A, that means DIV B is a "branch" of DIV A, which is the "parent". But if DIV C is also a branch of DIV A, then DIV B and DIV C are neighboring children.

But children can also be parents of their own children. Just like in real life?

Here is a diagram showing a basic DOM structure using simple HTML elements.

You get the point, DOM is the tree-like structure that contains the data of your entire HTML document.

You need to understand that the DOM is loaded before everything else, even before the page is rendered in your browser. So, DOM data already exists while the page is still loading. Why not use that to our advantage and begin initializing our plug in at that time? Who wants to wait for onload or while the visual part of the GUI has finished loading anyway? After all, onload will wait for things like images and some images can take forever to load. We don't have to wait for all that to initialize our plug-in.

So why did the developers of jQuery develop $(document).ready(...) function? Because it is a cross-browser way of executing code just in time when DOM finishes loading. Remember... that different browsers require different Javascript to check when DOM has loaded, but with jQuery, we get one neat function. This is where we initialize our plug-in.The $(document)ready() function is not used exclusively for initializing plug-ins. Use it to initialize all of your Javascript variables or objects, even if you are not developing a plug-in.

How do we create a plug-in, initialize and run it?

The easiest way to create your own plug in, is to follow the pattern depicted in the blue code block below.

Let's pretend we are creating an Image Slideshow Plug-in. I won't go into the actual details of developing a full-blown slideshow plug-in. This example only explains one way to construct a plug-in from scratch, initialize it, and run it.

The code below would go into a separate file like "slideshow.js" and be externally included from your HTML page inside the HEAD tag in a SCRIPT statement. You can treat the following code as a blank starting point for your future plug-in development.

// Plugin, default parameters storage (can be overridden during initialization) // This is also the definition of the order in which you will pass parameters to the init function // The initialize() function itself is missing argument definitions, on purpose function options() { this.params = { data : Array ("monalisa.jpg", // [0] image path "#container" // [1] plugin container ) }; }; // Define the main plug-in object, it's empty, and that's ok. $.Slideshow = function() { } // Initializes plug-in (missing argument definitions on purpose) $.Slideshow.initialize = function() { // Here, I do an interesting thing that begs an explanation. // I generally use the options.params.data array storage so it can persist between // the two functions of this plug-in: plugin.initialize and plugin.run // Note that we don't define arguments of this function, // Even though we expect them to be passed, we just collect them in the following way. // We can get options from the argument list of this function, // They are in the default "arguments" array of every function. $.options = new options(); for(var i = 0; i < arguments.length; i++) $.options.params.data[ i ] = arguments[ i ]; } // Runs the plug-in $.Slideshow.run = function() { // Write code here that executes this plug-in // Do something to "#plugin_container" stored in object's "container" var // Using parameters stored in object's "params" var // Let's paste the image passed as a parameter to the plug-in container DIV element. // Notice, that parameters passed to initialize function are now accessible through: // $.options.params.data[ X ] where X is the index of the parameter you need to access. // The order is defined by the order in which these parameters were passed to the initialize() function $($.options.params.data[ 1 ]).html('<img src = "' + $.options.params.data[ 0 ] + '"/>'); // Of course, this is the part where you can get creative and do whatever you need };

Could you store the parameters in the Slideshow object itself? Yes, but I decided to store them in a separate options object and make them globally accessible. This is by far not the only way to create a plug-in and store its options/parameters, but it's one possible way. I just wanted to break it down to simple blocks. As you learn more about Javascript, objects and variables, you will discover different ways of doing the same thing.

What is going on in the example above? When you say $.Slideshow = function() { ... } you attach a new function to the jQuery library ($) object, effectively extending its functionality. We will call this new plug-in Slideshow. Once your function is attached, you can now begin using it as $.Slideshow(); Of course you can add parameters to this function, this is just an example.

When you are ready to test your plug-in, you want to run $.Slideshow.initialize() from your "on document ready" function, and then call the member function run(), as follows:

$(document).ready(function() { $.Slideshow.initialize("image.jpg", "#plugin_container"); $.Slideshow.run(); });

Note that you can pass as many arguments to the function as you need. They are not explicitly defined in the initialize function. But the initialize function enumerates them automatically. Remember that each function is actually an object? And functions are the kinds of objects that have the arguments array attached to them, soon as a function is created. We don't even have to define these arguments in the function definition. But if you need to be strict, for whaetver reason, by all means, use distinct argument definitions.

#plugin_container is the DIV element somewhere on the page, that you want this plug-in to use as the main container. Call it anything you want. But this is where things will happen. It is simply a selector, and you can select any element you want. This is where the visuals (if any) of your plug in would be displayed. For example, you can take the first parameter "image.jpg" and display it in that container by running the following command:

$.Slideshow.run = function() { $($.options.params.data[ 1 ]).html('<img src = "' + $.options.params.data[ 0 ] + '"/>'); }

Remember that $.options.params.data[ 0 ] contains the image location "image.jpg", and the $.options.params.data[ 1 ] contains the ID of the plug-in container DIV.

Code above is the simplest slideshow plug-in. It takes the image as a parameter and simply "pastes" it into the target DIV container. It couldn't be simpler. To continue extending this plug-in, you could pass more than one image, and write your own slideshow animation code. Animation will be covered in Episode 5 of this newsletter series.

Bonus: Example of using "sortable" extension from jQuery UI

Notice that in the example below, I added jquery and jquery-ui directly from Google API page. This may not work for everyone, but if you are experimenting with small demos and don't want to bother downloading jQuery, uploading it to your hosting account or on your hard disk... and typing in the paths to it all the time, then this is a great way to speed up your development.

This example will display the Table of Contents from this newsletter and turn it into a "sortable" list. You can rearrange the items on the list by clicking on them and dragging them up or down the list.

© 2014 Copyright LearnjQuery.org.