原文地址:http://bubkoo.com/2014/01/02/angular/ui-router/guide/url-routing/
在你的應用中大多數狀態都有與其相關聯的 url,路由控制不是設計完成 state 之后的事后想法,而是開始開發時就應該考慮的問題。
這里是如何設置一個基本url。
$stateProvider
.state('contacts', {
url: "/contacts",
templateUrl: 'contacts.html'
})
當我們訪問index.html/contacts時, 'contacts'狀態將被激活,同時index.html中的ui-view將被'contacts.html'填充。或者,通過transitionTo('contacts')方法將狀態轉變到'contacts'狀態,同時 url 將更新為index.html/contacts。
URL參數
基本參數
通常,url動態部分被稱為參數,有幾個選項用於指定參數。基本參數如下:
$stateProvider
.state('contacts.detail', {
// 這里設置了url參數
url: "/contacts/:contactId",
templateUrl: 'contacts.detail.html',
controller: function ($stateParams) {
// If we got here from a url of /contacts/42
expect($stateParams).toBe({contactId: 42});
}
})
或者,你也可以使用花括號的方式來指定參數:
// 與前面的設置方法等效
url: "/contacts/{contactId}"
示例:
'/hello/'- 只匹配'/hello/'路徑,沒有對斜杠進行特殊處理,這種模式將匹配整個路徑,而不僅僅是一個前綴。'/user/:id'- 匹配'/user/bob'、'/user/1234!!!',甚至還匹配'/user/',但是不匹配'/user'和'/user/bob/details'。第二個路徑段將被捕獲作為參數"id"。'/user/{id}'- 與前面的示例相同,但使用花括號語法。
含正則表達式的參數
使用花括號的方式可以設置一個正則表達式規則的參數:
// 只會匹配 contactId 為1到8位的數字
url: "/contacts/{contactId:[0-9]{1,8}}"
示例: - 與
'/user/{id:[^/]*}''/user/{id}'相同
'/user/{id:[0-9a-fA-F]{1,8}}'- 與前面的示例相似,但只匹配1到8為的數字和字符'/files/{path:.*}'- 匹配任何以'/files/'開始的URL路徑,並且捕獲剩余路徑到參數'path'中。'/files/*path'- 與前面相同,捕獲所有特殊的語法。
警告:不要把捕獲圓括號寫進正則表達式,ui-router 的 UrlMatcher 將為整個正則表達式添加捕獲。
Query Parameters
可以通過?來指定參數作為查詢參數
url: "/contacts?myParam" // 匹配 "/contacts?myParam=value"
如果你需要不止一個查詢參數,請用&分隔:
url: "/contacts?myParam1&myParam2"
// 匹配 "/contacts?myParam1=value1&myParam2=wowcool"
嵌套狀態的路由控制
附加的方式(默認)
在嵌套狀態的路由控制中,默認方式是子狀態的 url 附加到父狀態的 url 之后。
$stateProvider
.state('contacts', {
url: '/contacts',
...
})
.state('contacts.list', {
url: '/list',
...
});
路由將成為:
'contacts'狀態將匹配"/contacts"'contacts.list'狀態將匹配"/contacts/list"。子狀態的url是附在父狀態的url之后的。
絕對路由(^)
如果你使用絕對 url 匹配的方式,那么你需要給你的url字符串加上特殊符號"^"。
$stateProvider
.state('contacts', {
url: '/contacts',
...
})
.state('contacts.list', {
url: '^/list',
...
});
路由將成為:
'contacts'狀態將匹配"/contacts"'contacts.list'狀態將匹配"/list"。子狀態的url沒有附在父狀態的url之后的,因為使用了^。
$stateParams 服務
之前看到的$stateParams服務是一個對象,包含 url 中每個參數的鍵/值。$stateParams可以為控制器或者服務提供 url 的各個部分。
注意:$stateParams服務必須與一個控制器相關,並且$stateParams中的“鍵/值”也必須事先在那個控制器的url屬性中有定義。
// 如果狀態中 url 屬性是:
url: '/users/:id/details/{type}/{repeat:[0-9]+}?from&to'
// 當瀏覽
'/users/123/details//0'
// $stateParams 對象將是
{ id:'123', type:'', repeat:'0' }
// 當瀏覽
'/users/123/details/default/0?from=there&to=here'
// $stateParams 對象將是
{ id:'123', type:'default', repeat:'0', from:'there', to:'here' }
只有當狀態被激活並且狀態的所有依賴項都被注入時,$stateParams對象才存在。這代表你不能再狀態的resolve函數中使用$stateParams對象,可以使用$state.current.params來代替。使用$stateParams的兩個陷阱
$stateProvider.state('contacts.detail', {
resolve: {
someResolve: function($state){
//*** 不能在這里使用 $stateParams , the service is not ready ***//
//*** 使用 $state.current.params 來代替 ***//
return $state.current.params.contactId + "!"
};
},
// ...
})
- 在狀態控制器中,
$stateParams對象只包含那些在狀態中定義的參數,因此你不能訪問在其他狀態或者祖先狀態中定義的參數。
$stateProvider.state('contacts.detail', {
url: '/contacts/:contactId',
controller: function($stateParams){
$stateParams.contactId //*** Exists! ***//
}
}).state('contacts.detail.subitem', {
url: '/item/:itemId',
controller: function($stateParams){
$stateParams.contactId //*** 注意! DOESN'T EXIST!! ***//
$stateParams.itemId //*** Exists! ***//
}
})
$urlRouterProvider
$urlRouterProvider負責處理在狀態配置中指定的url路由方式之外的 url 請求的路由方式。$urlRouterProvider負責監視$location,當$location改變后,$urlRouterProvider將從一個列表,一個接一個查找匹配項,直到找到。所有 url 都編譯成一個UrlMatcher對象。
$urlRouterProvider有一些實用的方法,可以在module.config中直接使用。
when() for redirection 重定向
參數:
whatString | RegExp | UrlMatcher,你想重定向的傳入路徑handlerString | Function 將要重定向到的路徑
handler 作為 String
如果handler是字符串,它被視為一個重定向,並且根據匹配語法決定重定向的地址。
app.config(function($urlRouterProvider){
// when there is an empty route, redirect to /index
$urlRouterProvider.when('', '/index');
// You can also use regex for the match parameter
$urlRouterProvider.when('/aspx/i', '/index');
})
函數可以返回:handler 作為 Function
如果handler是一個函數,這個函數是注入一些服務的。如果$location匹配成功,函數將被調用。你可以選擇性注入$match。
- falsy 表明規則不匹配,
$urlRouter將試圖尋找另一個匹配 - String 該字符串作為重定向地址並且作為參數傳遞給
$location.url() - nothing或者任何為真的值,告訴
$urlRouterurl 已經被處理
示例:
$urlRouterProvider.when(state.url, ['$match', '$stateParams', function ($match, $stateParams) {
if ($state.$current.navigable != state || !equalForKeys($match, $stateParams)) {
$state.transitionTo(state, $match, false);
}
}]);
參數:otherwise() 無效路由
pathString | Function 你想重定向url路徑或者一個函數返回url路徑。函數可以包含$injector和$location兩個參數。
app.config(function($urlRouterProvider){
// 在配置(狀態配置和when()方法)中沒有找到url的任何匹配
// otherwise will take care of routing the user to the specified url
$urlRouterProvider.otherwise('/index');
// Example of using function rule as param
$urlRouterProvider.otherwise(function($injector, $location){
... some advanced code...
});
})
參數:rule() 自定義url處理
handlerFunction 一個函數,包含$injector和$location兩個服務作為參數,函數負責返回一個有效的路徑的字符串。
app.config(function($urlRouterProvider){
// Here's an example of how you might allow case insensitive urls
$urlRouterProvider.rule(function ($injector, $location) {
var path = $location.path(), normalized = path.toLowerCase();
if (path != normalized) return normalized;
});
})
$urlMatcherFactory 和 UrlMatchers
定義了url模式和參數占位符的語法。$urlMatcherFactory是在幕后被$urlRouterProvider調用,來緩存編譯后的UrlMatcher對象,而不必在每次 location 改變后重新解析url。大多數用戶不需要直接使用$urlMatcherFactory方法,但是在狀態配置中非常實用,可以使用$urlMatcherFactory方法來生成一個UrlMatcher對象,並在狀態配置中使用該對象。
var urlMatcher = $urlMatcherFactory.compile("/home/:id?param1");
$stateProvider.state('myState', {
url: urlMatcher
});

