It was suggested that I read on AMD and maybe rethink my library setup. For the moment I've coded all of it the IIFE way, hiding all the small components from the global scope.
But when I saw how easy it is to just define()
things in AMD, I wanted to try it out!
But I ran into a couple of problems and I can't seem to understand where it starts and how things are loaded in. Now, be aware that I've read a lot on the subject and I searched for answers, but I think it's more a misconception on my part that blocks me from understanding what I read haha.
So I will ask as I understand it! :)
So let's start with a simple example ( by the way I don't want to create a nodeJS module, but a standard library for websites ), let's say I have this code :
//----------------------------------------------
// main.js
//----------------------------------------------
var myLib = {}
//----------------------------------------------
// hello.js
//----------------------------------------------
myLib.hello = function() { console.log("hello"); }
//----------------------------------------------
// bye.js
//----------------------------------------------
myLib.bye = function() { console.log("bye"); }
I would like to turn it into something like :
//----------------------------------------------
// main.js
//----------------------------------------------
define("myLib", ["hello". "bye"], function( hello, bye ){
return {
hello: hello,
bye: bye
};
});
//----------------------------------------------
// hello.js
//----------------------------------------------
define(function(){
return function() { console.log("hello");
})
//----------------------------------------------
// bye.js
//----------------------------------------------
define(function() {
return function() { console.log("bye"); }
});
myLib
to the window object ( what I found ) ? Can you please provide me an example that works with myLib
?<script ... scr="loadMyLib.js"></script>
? For many reasons:
(function(){...})()
.Ok, so I finally got it down. Here is how I did :
- Download requireJS.
As I understood, AMD is a specification for the programming language JavaScript. It defines an application programming interface (API) that defines code modules and their dependencies, and loads them asynchronously if desired. - Wikipedia
RequireJS implements AMD.
- Create your project setup.
Let's create the following project :
./
|-- js
| |-- lib
| | |-- jquery.js
| | |-- babana.js // Whatever that is.
| | |-- require.js // requireJS (YES).
| |
| |-- src
| | |-- methods
| | | |-- hello.js
| | | |-- bye.js
| | |
| | |-- core.js // Core of our library.
| |
| |-- app.js // Important
|
|-- index.html
- Create your index.html file and insert the requireJS script like so :
<script data-main="js/app" src="js/lib/require.js"></script>
There are some important things going on here :
data-main
attribute. See this file as the entry point to your library's code. In this case: app.js. This can seem confusing as of how it all comes together, but no worries, we are getting there soon enough. :)
- Set requireJS configurations and require our library.
You remember how we specified the source file in the data-main
attribute of the script tag? Let's add all we need in there :
//------------------------------
// js/app.js
//------------------------------
// Config
requirejs.config({
baseUrl: 'js/src',
paths: {
pixi: '../lib/pixi',
jquery: '../lib/jquery',
banana: '../lib/banana'
}
});
// Load our library.
requirejs(['core'], function( MyLib) {
// Set it to the global scope.
window.MyLib = MyLib;
});
There is a lot going on, so I'll provide some explanations.
js/src
as most of our files are located there.../
, this is because it starts from the baseUrl
.core
and the parameter that provides it is myLib
.
- Define the
core
and the rest of your library.
There is, of course, a lot of ways to create your library structure. This is one way of doing it. Check jQuery's setup for some inspirations.
//------------------------------
// js/src/core.js
//------------------------------
define( [
"./methods/hello",
"./methods/bye"
], function( hello, bye ) {
"use strict";
var
version = "1.0",
MyLib = function() { }; // Define a local copy of MyLib
MyLib.fn = MyLib.prototype = {
constructor: MyLib,
// Loaded functions
hello: hello,
bye: bye
};
return MyLib;
});
//------------------------------
// js/src/methods/hello.js
//------------------------------
define( function() {
return function() {
console.log("hello");
};
} );
//------------------------------
// js/src/methods/bye.js
//------------------------------
define( function() {
return function() {
console.log("bye");
};
} );
Well, I won't explain how all of this works together, because this answer is already to long haha. But you get the idea.
- Use your library in the browser!
Your library should now be available like so :
MyLib.fn.hello()
or MyLib.fn.bye()
.