Fork me on GitHub

李可

导航

requirejs:研究笔记

模块化历史
模块化异步加载方式
后期维护 查找问题 复用代码
防止全局变量的污染

http://requirejs.cn/
http://requirejs.org/

我的目录结构

总体步骤

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>无标题文档</title>
<!--一、主入口,data-main属性。main.js不带后缀名-->
<!--二、引入require.js库-->
<script data-main="js/main" src="js/require.js"></script>
<!-- 三、使用模块
1,调用模块 require()
2,定义模块 define()
3,配置模块 requireconfig()
-->
</head>

<body>
<div id="demo">1</div>
</body>
</html

一、require()引入模块

/*
require()3个参数
1,依赖的模块:不依赖的时候也要写上[]
2,回调:调用模块好之后的回调函数
3,配置:检查错误的
一般用前两个
*/

方式1 不带后缀名。moduleA是以main.js为相对路径来找moduleA.js文件

//main.js
require(['moduleA'],function(modA){
	console.log('MAIN函数');
	modA.aFuntion();
})
/*
注意报错中的路径:a/moduleA.js是以当前页面为相对路径来找moduleA.js文件的

错误 file:///C:/Users/Administrator/Desktop/a/moduleA.js net::ERR_FILE_NOT_FOUND

require(['moduleA.js'],function(modA){
	console.log('MAIN函数');
	modA.aFuntion();
})
*/

方式2 带后缀名。moduleA.js是以当前页面为相对路径来找moduleA.js文件,需要些相对index.htm的全路径

//main.js
require(['js/moduleA.js'],function(modA){
	console.log('MAIN函数');
	modA.aFuntion();
	
})

二、define()定义模块

/**
定义模块
参数:2个参数
1,依赖的模块:依赖先运行,可以确定运行顺序!!
2,回调,在回调中定义此模块向外暴露的接口
*/

define通过requirejs自带的r.js合并之后,在2个参数前面生成模块的名字。作为第一个参数。这个请看下文章。

三、执行顺序,加载过程

//解释
/*执行顺序,加载过程
一、模块的公用方法何时调用:异步加载的过程中,会走模块的公用方法。例如:moduleA的aNoPubFn方法

二、暴露的方法何时调用:法异步模块加载完毕,才会走回调函数,调用暴露的法
	当引入多个模块时候,看这几个模块是否有依赖关系,判断执行顺序。
	1,如果moduleA和moduleB没有依赖关系。谁先加载好,就先执行谁。
	2,如果moduleA和moduleB有依赖关系。被依赖模块先执行,依赖模块后执行

*/

一、模块的公用方法何时调用:异步加载的过程中,会走模块的公用方法。例如:moduleA的aNoPubFn方法

//main.js
require(['js/moduleA.js'],function(modA){
	console.log('MAIN函数');
	modA.aFuntion();
})
//moduleA.js
define(function(){
	console.log('A')
	console.log(aNoPubFn());
	function aNoPubFn(){
		return '不符合模块化的方法被暴露,';
	}
	function aFn(){
		console.log('我是A模块');
	}
	//在seajs中,暴露模块的(变量、函数)方式:exports
	//在requirejs中,暴露模块的(变量、函数)方式:return
	return {
		aFuntion:aFn
	}
})

二、暴露的方法何时调用:法异步模块加载完毕,才会走回调函数,调用暴露的法

1,如果moduleA和moduleB没有依赖关系
require(['js/moduleA.js','js/moduleB.js'],function(modA,modB){
	console.log('MAIN函数');
	modA.aFuntion();
	modB.bFuntion();
})
// moduleA.js
define(function(){
	console.log('A');
	function aFn(){
		console.log('我是A模块');
	}
	//在seajs中,暴露模块的(变量、函数)方式:exports
	//在requirejs中,暴露模块的(变量、函数)方式:return
	return {
		aFuntion:aFn
	}
})
//moduleB.js
define(function(){
	console.log('B')
	function bFn(){
		console.log('我是B模块');
	}
	//在seajs中,暴露模块的接口方式:export()
	return {
		bFuntion:bFn
	}
})

2,如果moduleA和moduleB有依赖关系。被依赖模块先执行,依赖模块后执行
//moduleA.js依赖moduleB.js
define(['js/moduleB.js'],function(modB){
	modB.bFuntion();
	console.log('A');
	function aFn(){
		console.log('我是A模块');
	}
	//在seajs中,暴露模块的(变量、函数)方式:exports
	//在requirejs中,暴露模块的(变量、函数)方式:return
	return {
		aFuntion:aFn
	}
})

四、require.config()配置函数

1,baseUrl属性

//moduleC.js
define(function(){
	console.log('C');
	function cFn(){
		console.log('我是C模块');
	}
	//在seajs中,暴露模块的接口方式:export()
	return {
		cFuntion:cFn
	}
})
//main.js
require.config({

	//baseUrl:"aaa",
	// file:///C:/Users/Administrator/Desktop/a/aaa/moduleA.js
	//采取没后后缀名的基准文件夹(开始、结束都没有斜杠),require的模块引入不要带后缀,
	baseUrl:"js/libs"
})
require(['moduleC'],function(modC){
	console.log('MAIN函数');
	modC.cFuntion();
})

2,paths属性

//main.js
require.config({
	//对于路径很长的模块,为了简写:例如require(['js/libs/angular.js'],
	/*这里面都是相对main.js的路径*/
	paths:{
		/*错误://file:///C:/Users/Administrator/Desktop/a/js/js/libs/moduleC.js */
		//modc:'js/libs/moduleC',

		//ng:['js/libs/angular.js','cdn...']//数组,当请求第一个路径不到的话,会请求第二个.这样可以将第二个路径指向cdn
		'modc':'libs/moduleC',
		'moda':'moduleA'
	}
})
require(['moda','modc'],function(modA,modC){
	console.log('MAIN函数');
	console.log('a'+modA);
	console.log('c'+modC);
	modA.aFuntion();
	modC.cFuntion();
})
//moduleA.js
define(function(){
	console.log('A');
	function aFn(){
		console.log('我是A模块');
	}
	//在seajs中,暴露模块的(变量、函数)方式:exports
	//在requirejs中,暴露模块的(变量、函数)方式:return
	return {
		aFuntion:aFn
	}
})
//moduleC.js
define(function(){
	console.log('C');
	function cFn(){
		console.log('我是C模块');
	}
	//在seajs中,暴露模块的接口方式:export()
	return {
		cFuntion:cFn
	}
})

baseUrl和paths共同使用 也是下面截图

/******************************************/
// require.config({
	
// 	//baseUrl:"jsa",/*错误file:///C:/Users/Administrator/Desktop/a/jsa/moduleA.js */
// 	baseUrl:"js",  //这里有木有都一样
// 	paths:{
// 		//modc:'js/libs/moduleC',/*错误://file:///C:/Users/Administrator/Desktop/a/js/js/libs/moduleC.js */
// 		//ng:['js/libs/angular.js','cdn...']//数组,当请求第一个路径不到的话,会请求第二个.这样可以将第二个路径指向cdn
// 		'modc':'libs/moduleC',
// 		'moda':'moduleA'
// 	}
// })
// require(['moda','modc'],function(modA,modC){
// 	console.log('MAIN函数');
// 	console.log('a'+modA);
// 	console.log('c'+modC);
// 	modA.aFuntion();
// 	modC.cFuntion();
// })

3,shim属性{ 插件1:{deps:[],export:''},插件2{deps:[],export:''}}.垫片的意思

/********************shim待证明************************************/

 require.config({
	baseUrl:"js",
	paths:{
		'modc':'libs/moduleC',
		'moda':'moduleA'
	},
	//垫片:处理不是模块化js插件的模块
	shim{
	     pop:{//pop插件不是模块化
	     	deps:['jquery'],//pop插件依赖的库 比如基于jquery  或者dojo
            export:"pop"//exports值(输出的变量名)
	     },
	     modal:{//模态框插件不是模块化
	     	deps:['jquery'],
	     	export:"modal"
	     },
	     easyui:{
			deps:['jquery'],
			export:"easyui"
	     }
	}
})
require(['moda','modc'],function(modA,modC){
	console.log('MAIN函数');
	console.log('a'+modA);
	console.log('c'+modC);
	modA.aFuntion();
	modC.cFuntion();
})

六、引入jquery

jquery源码异步代码

/*jquery已经是amd的模块化,名字应经定死了,叫做jquery*/
require.config({
	paths:{
		//不带后缀
		//前面jquery
		'jquery':'libs/jquery-2.1.3.min'//
		}
})
 //引入jquery
require(['jquery'],function($){
	console.log($);
	console.log($("#demo").html());
})

输出结果

7、基于requirejs内置的r.js进行代码合并、压缩

//减少http请求次数。代码明天写

requirejs插件

posted on 2016-06-16 01:17  李可在江湖  阅读(534)  评论(0编辑  收藏  举报