我正在尝试掌握可插拔模块的概念,就像jQuery使用插件一样。 我的目标是将我的模块拆分成不同的文件,并在dom准备就绪后根据jQuery正确初始化。
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript" src="my_library.js"></script>
<script type="text/javascript" src="modules.js"></script>
<!-- Could be more -->
我现在正在做的方法是在设置模块之后在jquery函数内调用MY_LIBRARY.init()。
// my_library.js
var MY_LIBRARY = {
init: function() {
var _self = this,
modules = _self.modules;
if (modules) {
for (var i in modules){
modules[i].init();
}
}
},
modules: {}
}
// modules.js
MY_LIBRARY.modules.MyModule1 = {
init: function(){
// initialize stuff
return this;
}
};
MY_LIBRARY.modules.MyModule2 = {
init: function(){
// initialize stuff
return this;
}
};
$(function(){
MY_LIBRARY.init();
});
问题是如何在dom准备就绪时自行调用MY_LIBRARY和模块,而不使用:
$(function(){
MY_LIBRARY.init();
});
我一直在努力解决这个问题,尝试复制jquery这样做的方式,所以我做了this piece of code。而不是使用'$',我使用'X $'作为我的自定义全局对象,所以我可以做类似的事情:
X$( 'MyModule1', { init: function(){}, doStuff: function(){} });
或
X$('MyModule1').doStuff();
我认为这种模式适合我。 目前,我唯一无法复制的是使用类似的东西:
X$.core.myCoreFunction() { return true; }; // plugin function yay!
X$.myCoreFunction(); // alerts X$.myCoreFunction is not a function
由于jQuery使用插件执行此操作,这有点奇怪。 对此有何看法?
答案 0 :(得分:2)
我尝试在模块定义周围使用函数包装器,特别是因为除了init
函数之外,您可能会发现模块之间存在很多共性。
例如,我在这里定义了一个lib
函数,它可以帮助您声明一个新库,并自动将init
函数绑定到document.ready
:
function lib(module) {
$(function() {
if (module.init) {
module.init();
}
});
return module;
}
var MYLIB = lib(function() {
return {
init: function() {
// ...
}
};
}());
您可以在同一模式上使用其他变体,但它将使您无需添加大量额外代码,并允许您以相同方式管理所有库。例如,你可以让lib
在最初调用时返回一个虚拟对象,在document.ready
之后它应用传入的函数来生成真实对象,这样可以避免显式完全init
:
function lib(moduleMaker) {
var module = {};
$(function() {
moduleMaker(module);
});
return module;
}
var MYLIB = lib(function(mylib) {
mylib.foo = function() {/*...*/};
// other init stuff, we've already waited for document.ready
});