转载自:http://blog.csdn.net/z787326/article/details/8069874 模块(Modules) 我们将Dojo中可以单独被反复调用的代码块称之为模块。那么如何区分不同的模块,我们就像使用一个文件路径来定位文
转载自:http://blog.csdn.net/z787326/article/details/8069874
模块(Modules)
我们将Dojo中可以单独被反复调用的代码块称之为模块。那么如何区分不同的模块,我们就像使用一个文件路径来定位文件一样来获取不同的模块。比如 my/modules/id 是Dojo中一个模块的id,那么其实这个id是对应到一个相应的js文件的。这意味着什么呢,如果你要载入模块“my/module/id”,那么程序会载入定义在my/moduls/id.js 这个文件中所有的模块。
√这是基本的模式,也有一些其他的更复杂的模式,来描述文件和模块之间的关系,我们将在后面进行介绍。
为了你能够在你的程序中定义和调用模块,有两个全局函数是必须定义的。一个是 request(),它用来加载模块;另一个是 define(),它用来定义模块。这两个函数通常需要两个参数,一个是一个包含MID的列表,MID即module identifier,模块的id也是模块的标示符;另一个参数是一个执行一次的回调函数。
我们来用一个例子说明一下
myModule.js
//这个js文件的文件路径为modules/myModule.js,意味着我定义了一个MID为modules/myModule的模块 define([ //这是放置你会调用的Dojo模块 "dojo/dom" ],function(){ //当上一个参数中的所有模块被加载后,开始执行以下的代码,开始绘制我们定义的模块 var oldText = {}; return{ setText : function(id,text){ var node = dom.byId(id); oldText[id] = node.innerHTML; node.innerHTML = text; }, restoreText : function(id){ var node = dom.byId(id); node.innerHTML = oldText[id]; delete oldText[id]; } }; });我们定义的这个模块,它依赖于 “dojo/dom”,它的值被定义成一个对象,并且包含 setText() 和 restoreText() 两个方法。
如果你在开始的时候是使用CDN的模式载入Dojo的话,这个时候如果你想顺利的调用我们定制的模块,你必须要修改dojoConfig了。因为定义的模块式在本地,而Dojo因为CDN的缘故,会去CDN上加载,那就出错了。解决:
<script> var dojoConfig = { async: true, packages: [{ name: "modules", location: location.pathname.replace(/\/[^/]+$/, '') }] }; </script>如果你已经跟我一样,把Dojo的下载到了本地,这个步骤就可以跳过了。
好了,既然已经定义好了,那我们就在试着调用我们定义的模块吧。
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>Hello Dojo!</title> <link rel="stylesheet" href="demo.css"> </head> <body> <h1 id="greeting">Hello</h1> <!-- load dojo and provide config via data attribute --> <script src="dojo/dojo.js" data-dojo-config="isDebug:1, async:1"></script> <script> //调用模块 require(["modules/myModule"],function(myModule){ //改变greeting的text myModule.setText("greeting","Hello Dojo!!!!!!!!!!"); //延时3s后恢复文本 setTimeout(function(){ myModule.restoreText("greeting"); },3000); }); </script> </body> </html>好了,如果你看见 <h1 id="greeting">Hello</h1> 这个元素的值从“Hello”变成了“Hello Dojo!!!!!!!”,并且三秒后又恢复了原样,说明你成功了。这是最简单的模块定义与调用。
等待DOM
有一件事你必须保证的是,那就是确保DOM在你的代码执行之前载入完成。在Dojo 1.7以后的版本里,你使用异步模式时,用AMD实现的模块我们习惯称之为插件,这些插件你可以像调用其他模块一样来调用,唯一不同的只是,通过在MID的末尾加上一个符号。对于DOM载入的事件,Dojo提供了一个 “dojo/domReady” 插件,你要做的很简单,只要在 request() 或 define() 函数中,把他作为依赖项引入,那么回调函数就在DOM载入完成之前就不会执行了。require(["dojo/dom", "dojo/domReady!"], function(dom){ var greeting = dom.byId("greeting"); greeting.innerHTML += " from Dojo!"; });上面的例子很简单,就是在DOM,这里是一个id为“greeting”的元素加载完成后,向它添加一些文字内容。但是你需要注意到的是,第一行代码中 domReady后面的感叹号:!如果没有这个感叹号,那么就会Dojo就会把它当成普通的模块来处理了。
简单的动画
现在我们可以给加入一些简单的动画效果,一个页面可以通过加载“dojo/fx”来实现动画效果。现在我们用“dojo/fx”中的 sildeTo() 方法给 greeting 这个元素添加一个滑动的动画。代码如下
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>Hello Dojo!</title> <link rel="stylesheet" href="demo.css"> </head> <body> <h1 id="greeting">Hello</h1> <!-- load dojo and provide config via data attribute --> <script src="dojo/dojo.js" data-dojo-config="isDebug:1, async:1"></script> <script> require(["dojo/dom", "dojo/fx", "dojo/domReady!"], function(dom, fx){ var greeting = dom.byId("greeting"); greeting.innerHTML += " from Dojo!"; fx.slideTo({ top: 100, left: 200, node: greeting }).play(); }); </script> </body> </html>上面的程序中,我们通过添加“dojo/fx”的依赖,在id为 greeting 的元素上添加了一个滑动的动画。但你刚刚接触AMD这种模式的时候,你可能会错误的认为包含MID的数组( ["dojo/dom", "dojo/fx", "dojo/domReady!"])和回调函数的参数列表( dom, fx )没有什么关联,但是事实并非如此:当回调函数将被调用的时候,这些模块根据先前的顺序组成数据。因为 “dojo/domReady!” 没有一个有意义的返回值,所以我们不需要为他添加一个参数。同时你不要以为,因为你不需要用到某一个模块的返回值,你就可以不用将他添加到参数列表里,这也是错误的。还有,如果一个模块如果它的返回值是未使用的,那就把它放在MID列表的最后。
下面这样做就有问题了
require(["dojo/dom", "dojo/domReady!", "dojo/fx"], function(dom, fx){ });上面的这种情况 fx 这个参数对应的是 “dojo/domReady”,这显然就是有问题的了!