在AngularJS应用中,我们可以把一个完整的HTML页面拆分成多个视图,每个视图实际上就是一段HTML片段,路由机制就是在每个视图和URL之间建立映射关系,当通过AngularJS路由API访问URL时,页面中能够加载对应的视图内容
一、创建多视图应用
1.使用$routeProvider创建映射
1.1.
$routeProvider
是AngularJS的内置对象,该对象用于创建路由映射,提供了一个
when(path,route)
方法和
otherwise(params)
方法,能够帮助我们将控制器、视图模板、URL关联起来
when(path,route)
:
(1).
path
:string类型,路由路径(和$location.path相对应),如果$location.path路
径后有多余的"/"或者缺少"/",路由依然能匹配,并且$location.path会依据路由定义
删除多余的"/"或者增加"/"。除此之外,path中还可以使用占位符,需要使用":"分隔,
例如:/ShowOrders:Num
(2).
route
:Object类型,用于配置映射信息,具有以下属性
a.
controller
:{string|function}类型,用于指定控制器名称或控制器构造方法
b.
controllerAs
:string类型,通过控制器标识符名称引用控制器
c.
template
:{string|function}类型,用于指定视图模板,也可以是一个返回
HTML模板内容的方法
d.
templateUrl
:string类型,作用和template属性相同,不同的是,它用于指
定视图模板文件路径
e.
resolve
:Object类型,用于指定注入控制器中的内容
otherwise(params)
:
该方法接收一个string类型的参数,用于匹配路由中未定义的
URL
1.2.模块实例的
config()
方法会在模块加载时被执行,
主要用于对服务进行配置
1.3.AngularJS的路由模块作为一个单独的模块,模块名称为
ngRoute
,如果在自定义模块中使用,需要引入angular-route.js文件,并在声明Angular模块时添加
ngRoute
模块依赖
1.4.
ng-view
是AngularJS的一个内置指令,用于定义一个视口来加载创建的视图内容
<
ng-view
>
ng-view
> (IE不兼容)
------------------------------------------------angular/js/app.js----------------------------------------------
var routeModule=angular.
module
("routeModule",['
ngRoute
']);
routeModule.
controller
("AddOrderController",function($scope){});
routeModule.
controller
("ShowOrderController",function($scope){});
routeModule.
config
(['
$routeProvider
',
function(
$routeProvider
){
$routeProvider
.
when
('/addOrder',{
templateUrl
:'templates/add-order.html',
controller
:'AddOrderController'
}).
when
('/showOrders',{
templateUrl
:'templates/show-orders.html',
controller
:'ShowOrderController'
}).
otherwise
({
redirectTo
:'/addOrder'
});
}]);
-------------------------------------angular/templates/add-order.html-----------------------------------
-----------------------------------angular/templates/show-orders.html----------------------------------
-----------------------------------------------angular/index.html---------------------------------------------
ng-app
="routeModule">
angularJS
href="bootstrap/bootstrap-theme.min.css"/>
.mainDiv{
margin:25px 50px 75px 100px;
}
订单列表
新增订单
<
ng-view
>
ng-view
>
--------------------------------------------------------------------------------------------------------------------
二、通过URL向控制器传递参数
在路由定义时,可以在URL中增加一个参数orderId,用冒号隔开
为了获取URL中传递的参数,需要在控制器中注入
$routeParams
服务,通过
$routeParams
.orderId来获取
------------------------------------------------angular/js/app.js----------------------------------------------
var routeModule=angular.module("app",['
ngRoute
']);
routeModule.config(['
$routeProvider
',
function(
$routeProvider
){
$routeProvider
.
when('/showOrder/:
orderId
',{
templateUrl
:'templates/order-details.html',
controller
:'ShowOrderController'
})
}]);
routeModule.controller('ShowOrderController',function(
$scope
,
$routeParams
){
$scope
.order_id=
$routeParams
.
orderId
;
});
-----------------------------------angular/templates/orders-details.html--------------------------------
订号单 #{{order_id}}
此处为订单明细... #{{order_id}}
-----------------------------------------------angular/index.html---------------------------------------------
ng-app
="routeModule">
angularJS
href="bootstrap/bootstrap-theme.min.css"/>
.mainDiv{
margin:25px 50px 75px 100px;
}
--------------------------------------------------------------------------------------------------------------------
三、ng-template指令的使用
有时,视图内容比较少,希望把不同的视图继承到同一个页面中,或者要开发一个反页面应用(SPA),就可以使用
ng-template
指令来实现
注意,
templateUrl
为script标签的id
--------------------------------------------------------------------------------------------------------------------
ng-app
="templateModule">
template
var templateModule=angular.
module
('templateModule',['
ngRoute
']);
templateModule.
config
(['
$routeProvider
',
function(
$routeProvider
){
$routeProvider
.
when
('/view1',{
templateUrl
:'
/viewId1
'
}).
when
('/view2',{
templateUrl
:'
/viewId2
'
});
}]);
--------------------------------------------------------------------------------------------------------------------
四、$location服务
$location
服务是AngularJS中和浏览器地址栏URL相关的一个内置服务,始终和浏览器地址栏URL保持同步状态,浏览器地址栏发生改变时,
$location
服务会实时更新。使用
$location
服务可以获取地址栏URL,或者对地址栏URL进行修改,以达到访问不同路由的效果。其中一些属性只能获取而无法修改,如host、protocol、port等,有些是可以修改的,如path、search、hash等
以http://foo.com:8080/bar?bar=23#baz为例,URL主要由一下几个部分构成
(1).Protocal:协议名,通过
$location
.
protocal()
获取,会返回字符串http
(2).Host:主机名,通过
$location
.
host()
获取,返回foo.com
(3).Port:端口号,通过
$location
.
port()
获取,返回8080
(4).Path:AngularJs的
$location
服务支持两种URL模式,即HTML5模式和Hashbang
模式(默认)。HTML5模式下,
path
为端口之后,请求参数之前的部分,即/bar;
Hashbang模式下,path为第一个#后的内容,即baz。
$location
服务默认采用
Hashbang模式,可以通过
$locationProvider
对象进行模式设置
--------------------------------------------------------------------------------------------------------------------
routeModel.
config
(['
$locationProvider
',
function(
$locationProvider
){
$locationProvider
.
html5Mode
(true);
}
]);
--------------------------------------------------------------------------------------------------------------------
(5).Search:Search可以认为是URL中的请求参数,可以通过
$location
.
search()
获取
或设置:$location.search({key1:value1,key2:value2})
(6).Hash:用于把当前浏览器窗口定位于HTML的某一部位,通过
$location
.
hash()
获
取或设置
五、$location实现多视图切换
--------------------------------------------------------------------------------------------------------------------
ng-app
="app">
angularjs
ng-controller
="
ViewController
">
ng-click
="changeView1()">view1
ng-click
="changeView2()">view2
var appAngular=
angular
.
module
("app",['
ngRoute
']);
appAngular.config(['
$routeProvider
',function(
$routeProvider
){
$routeProvider
.
when
("/view1",{
templateUrl
:"/viewId1"
}).
when
("/view2",{
templateUrl
:"/viewId2"
});
}]);
appAngular.
controller
("
ViewController
",function(
$scope
,
$location
){
$scope
.changeView1=function(){
$location
.
path
('/view1');
}
$scope
.changeView2=function(){
$location
.
path
('/view2');
}
});
--------------------------------------------------------------------------------------------------------------------
六、路由事件
1.$location相关事件
$locationChangeStart
:该事件会在调用
$location
服务的一些方法改变浏览器地址栏之前触发,并会被传递到
$rootScope
作用域中
$locationChangeSuccess
:该事件在调用
$location
服务改变浏览器地址栏URL后触发,但如果监听
$locationChangeStart
事件并调用
preventDefault()
方法阻止事件的传播后,该事件将不会被触发
2.$route相关事件
$routeChangeStart
:该事件会在AngularJS开始改变路由时触发,也会被传递到
$routeScope
作用域中
$routeChangeSuccess
:该事件会在路由改变成功时触发,AngularJS的
ng-view
指令会监听该事件,接收到该事件时会实例化相应的控制器并渲染视图
$routeChangeError
:路由切换异常时触发,该事件同样会传递到
$rootScope
作用域
七、ng-include指令
ng-include
指令用于页面中包含其他HTML文件,可以通过属性形式或者作为HTML元素使用:
ng-include
="
'
./common/navbar.html
'
">
<
ng-include
src="
'
./common/navbar.html
'
">
ng-include
>
--------------------------------------------common/navbar.html--------------------------------------------
---------------------------------------------common/footer.html--------------------------------------------
----------------------------------------------------index.html---------------------------------------------------
ng-app
>
index
ng-include
="'./common/navbar.html'">
ng-include
="'./common/footer.html'">
--------------------------------------------------------------------------------------------------------------------
注意,在目前的HTML规范中还不支持HTML包含功能(火狐可以,谷歌不行不知道是不是因为这个)
八、UI Router框架使用
UI Router
是基于AngularJS的,用于编写单页面应用的路由框架,支持多试图嵌套和多个命名视图
AngularJS的
ngRouter
模块可以实现多视图切换效果,但有一些局限性-多视图之间不能进行嵌套,例如,通过
ng-view
指令加载了一个控制面板页面后,如果想在控制面板中添加一些子视图,
ngRoute
模块就不支持,因此需要使用
UI Router
框架
1.UI Router使用案例
(1).下载并引入angular-ui-router.js文件
(2).在自定义angular模块中添加
ui.route
模块依赖
(3).
$stateProvider
和
$urlRouteProvider
是UI Route框架提供的两个Provider对象,要使用这两个对象,首先需要在自定义模块总添加
ui.route
依赖
(4).通过模块实例的
config()
方法进行配置
a.调用
$urlRouteProvider
的
otherwise()
方法指定当我们请求不存在的状态名时跳
转到的页面,该方法接收一个string类型,指定视图页面
b.调用
$stateProvider
的
state()
方法定义状态,该方法接收两个参数,第一个参数
为状态名,第二个参数是一个对象,用于描述状态信息,其中
url
属性为状态对应的
URL,
templateUrl
属性指定路由切换时候加载的HTML视图,
controller
属性指定当前
视图对应的控制器
(6).主页面中使用UI Route内置的
ui-sref
指令指定一个状态名称
--------------------------------------------common/home.html--------------------------------------------
我的书籍
ng-repeat
="book in books">
--------------------------------------------common/about.html--------------------------------------------
关于页面
姓名:
{{name}}
--------------------------------------------common/contact.html--------------------------------------------
联系我:
--------------------------------------------------------app.js----------------------------------------------------
var appAngular=angular.
module
("app",["
ui.router
"]);
appAngular.
config
(function(
$stateProvider
,
$urlRouterProvider
){
$urlRouterProvider
.
otherwise
("/");
$stateProvider
.
state
("home",{
url
:"/home",
templateUrl
:"common/home.html",
controller
:function(
$scope
){
$scope
.books=['红楼梦','金瓶梅','石头记'];
}
});
$stateProvider
.
state
("about",{
url
:"/about",
templateUrl
:"common/about.html",
controller
:function($scope){
$scope
.name="蔡舜烽";
}
});
$stateProvider
.
state
("contact",{
url
:"/contact",
templateUrl
:"common/contact.html"
});
});
--------------------------------------------------index.html-----------------------------------------------------
ng-app
="app">
index
href="bootstrap-3.3.7-dist/css/bootstrap.min.css">
href="bootstrap-3.3.7-dist/css/bootstrap-theme.min.css">
@Jiang Rongbo,Blog:
http://blog.csdn.net/rongbo_j
--------------------------------------------------------------------------------------------------------------------