當你的應用啓動的時候,路由器就會匹配當前的URL到你定義的路由上。而後按照定義的路由層次逐個加載數據、設置應用程序狀態、渲染路由對應的模板。css
在app/router.js的map方法裏定義的路由會映射到當前的URL。當map方法被調用的時候方法體內的route方法就會建立路由。html
下面使用Ember CLI命令建立兩個路由:npm
ember generate route about ember generate route favorites
命令執行完以後你可在你的項目目錄app/routes下面看到已經建立好的兩個路由文件已經app/templates下面路由對應的模板文件。bootstrap
此時在app/router.js的map方法中已經存在了剛剛建立的路由配置。這個是Ember CLI自動爲你建立了。api
// app/router.js import Ember from 'ember'; import config from './config/environment'; var Router = Ember.Router.extend({ location: config.locationType }); Router.map(function() { this.route('about'); this.route('favorites'); }); export default Router;
如今分別修改app/templates下面的兩個模板文件以下:瀏覽器
<!-- app/templates/about.hbs --> 這個是about模板!<br> {{outlet}}
<!-- app/templates/favorites.hbs --> 這個是favorites模板!<br> {{outlet}}
而後訪問http://localhost:4200/about或者http://localhost:4200/favorites,若是你的程序沒有問題你也會獲得以下顯示結果:app
若是你以爲favorites這個路由名字太長是否能夠修改爲其餘名字呢?答*案是確定的,你只要修改router.js中map方法的配置便可。框架
Router.map(function() { this.route('about'); // 注意:訪問的URL能夠寫favs可是項目中若是是使用route的地方仍然是使用favorites this.route('favorites', { path: '/favs' }); });
此時訪問:http://localhost:4200/favs,界面顯示的結果與以前是同樣的。ide
說明:默認狀況下訪問的URL與路由名字是一致的,好比「this.route('about')」與「this.route('about', { path: ‘/about’ })」是同一個路由,若是URL與路由不一樣名則須要使用{path: ‘/xxx’}設置映射的URL。工具
在handlebars模板中可使用{{link-to}}助手在不一樣的路由間切換,使用時須要在link-to助手內指定路由名稱。好比下面的代碼使用link-to助手實如今about和favs兩個路由間切換。
爲了頁面能美觀一點引入bootstrap,使用npm命令安裝:bower install bootstrap,若是安裝成功你能夠在bower_components目錄下看到bootstrap相關的文件。安裝成功以後引入到項目中,修改chapter3_routes/ember-cli-build.js。在return語句前加入以下兩行代碼(做用就是引入bootstrap框架):
app.import("bower_components/bootstrap/dist/css/bootstrap.css"); app.import("bower_components/bootstrap/dist/js/bootstrap.js");
修改application.hbs,增長一個導航菜單。
<!-- //app/templates/application.hbs --> <nav class="navbar navbar-inverse navbar-fixed-top"> <div> <div href="#"> <!-- <a href="#">Blog</a> --> {{#link-to 'index'}}Home{{/link-to}} </div> <ul class="nav navbar-nav"> <li>{{#link-to 'about'}}about{{/link-to}}</li> <li>{{#link-to 'favorites'}}favorites{{/link-to}}</li> </ul> <ul class="nav navbar-nav navbar-right"> <li><a href="#">Login</a></li> <li><a href="#">Logout</a></li> </ul> </div> </nav> <div style="margin-top: 70px;"> <!-- 項目中其餘全部的模板都是application的子模板,因此其餘模板都會渲染到這裏的 outlet上 --> {{outlet}} </div>
若是看到頁面沒有bootstrap效果請從新啓動項目。若是運行項目後再瀏覽器控制檯出現以下錯誤。
請在config/environment.js的APP後面添加以下內容:
, contentSecurityPolicy: { 'default-src': "'none'", 'script-src': "'self' 'unsafe-inline' 'unsafe-eval' use.typekit.net connect.facebook.net maps.googleapis.com maps.gstatic.com", 'font-src': "'self' data: use.typekit.net", 'connect-src': "'self'", 'img-src': "'self' www.facebook.com p.typekit.net", 'style-src': "'self' 'unsafe-inline' use.typekit.net", 'frame-src': "s-static.ak.facebook.com static.ak.facebook.com www.facebook.com" }
而後重啓項目再運行就不會報上面的錯誤了!!
若是你的程序沒有其餘錯誤那麼你也會獲得以下圖的結果界面:
而後點擊「about」會獲得以下界面
能夠看到瀏覽器地址欄的URL變爲about了,而且頁面顯示的內容也是about模板的內容。同理你點擊「favorites」地址欄就變爲http://localhost:4200/favs而且顯示的內容是favorites的(爲何URL是favs而不是favorites呢,由於前面已經修改了route和URL的映射關係,路由favorites對應的URL是favs)。
上述演示的就是路由的切換!!!
還記得在前面的《Ember.js 入門指南——{{link-to}} 助手》這篇文章的內容嗎?在這篇文章中比較詳細的介紹了路由的嵌套與怎麼使用嵌套的路由。不妨回過頭去看看。在這裏打算就不講了……若是有不明白的請看官網的教程。
application路由是默認的路由,是程序的入口,全部其餘自定義的路由都先進過application纔到自定義的路由。而且application路由對應的application.hbs模板是全部自定義模板的父模板,全部自定義的模板都會渲染到application.hbs模板的{{outlet}}上。有關於路由的執行順序以及模板的渲染順序在前面的《Ember.js 入門指南——{{link-to}} 助手》也講過了,在此也不打算在作過多的介紹了。你能夠回頭看以前的文章或者到官網查看。
對於全部的嵌套的路由,包括最頂層的路由Ember會自動生成一個訪問URL爲「/」對應路由名稱爲「index」的路由。
好比下面的兩種路由設置是等價的。
// app/router.js // …… Router.map(function() { this.route('about'); // 注意:訪問的URL能夠寫favs可是項目中若是是使用route的地方仍然是使用favorites this.route('favorites', { path: '/favs' }); }); export default Router;
// app/router.js // …… Router.map(function() { this.route('index', { path: '/' }); this.route('about'); // 注意:訪問的URL能夠寫favs可是項目中若是是使用route的地方仍然是使用favorites this.route('favorites', { path: '/favs' }); }); export default Router;
index路由會渲染到application.hbs模板的{{outlet}}上。這個是Ember默認設置。當用戶訪問「/about」時Ember會把index模板替換爲about模板。
對於路由嵌套的狀況也是如此。
// app/router.js // …… Router.map(function() { this.route('posts', function() { this.route('new'); }); }); export default Router;
// app/router.js // …… Router.map(function() { this.route('index', { path: '/' }); this.route('posts', function() { this.route('index', { path: '/' }); this.route('new'); }); });
兩種設置方式都會獲得以下圖的路由表。打開瀏覽器的「開發者工具」點開「Ember」選項卡,在點開「/#Routes」你就能夠看到以下路由表(顯示是順序有可能跟你的不同)。
注:loading和error這兩個路由是ember自動生成的,他們的用法會在後面的文章介紹。
當用戶訪問「/posts」時實際進入的路由是posts.index對應的模板是posts/index.hbs,可是實際中我並無建立這個模板,由於Ember默認把這個模板渲染到posts.hbs的{{outlet}}上。因爲這個模板不存在也就至關於什麼都沒作。固然你也能夠建立這個模板。使用命令:ember generate template posts/index而後在這個模板中添加如下顯示的內容:
<!-- app/templates/posts/index.hbs --> <h2>這裏是/posts/index.hbs。。。</h2>
再此訪問http://localhost:4200/posts,是否是能夠看到增長的內容了。
你能夠這麼理解對於每個有子路由的路由都有一個名爲index的子路由而且這個路由對應的模板爲index.hbs,若是把有子路由的路由當作一個模塊看待那麼index.hbs就是這個模塊的首頁。特別是作過一些信息系統的朋友應該是很熟悉的,基本上沒個子模塊都會有一個首頁,這個首頁現實的內容就是一進入這個模塊時就顯示的內容。既然是子模板固然也不會例外它也會渲染到父模板的{{outlet}}上。好比上面的例子當用戶訪問http://localhost:4200/posts實際進入的是http://localhost:4200/posts/(後面多了一個「/」,這個「/」對應的模板就是index),當用戶訪問的是http://localhost:4200/posts/new,那麼進入的就是posts/new.hbs這個模板(也是渲染到posts.hbs的{{outlet}}上)。
關於動態段在前面的《Ember.js 入門指南——{{link-to}} 助手》也介紹過了,在這裏就再簡單補充下。
路由最主要的任務之一就是加載model。
例如對於路由this.route(「posts」);會加載項目中全部的posts下的model。可是當你只想加載其中一個model的時候怎麼處理呢?並且大多數狀況咱們是不須要一次性加載徹底部數據的,通常狀況都是加載其中一小部分。這個時候就須要動態段了!
動態段以「:」開頭,而且後面接着model的id屬性。
// app/router.js // …… Router.map(function() { this.route('about'); // 注意:訪問的URL能夠寫favs可是項目中若是是使用route的地方仍然是使用favorites // this.route('favorites', { path: '/favs' }); this.route('posts', function() { this.route('post', { path: '/:post_id'}); }); }); export default Router;
此時你能夠訪問http://localhost:4200/posts/1,不過咱們還沒建立model因此會報錯。這個咱們暫時無論,後面會有一章是介紹model的。如今只要知道你訪問http://localhost:4200/posts/1就至關於獲取id值惟一的model。
Ember也一樣運行你使用「*」做爲URL通配符。有了通配符你能夠設置多個URL訪問同一個路由。
this.route('about', { path: '/*wildcard' });
而後訪問:http://localhost:4200/wildcard或者訪問http://localhost:4200/2423432ffasdfewildcard或者http://localhost:4200/2333都是能夠進入到about這個路由,可是http://localhost:4200/posts仍然進入的是posts這個路由。由於能夠匹配到這個路由。
在有路由嵌套的狀況下,通常狀況咱們訪問URL的格式都是「父路由名/子路由名」,Ember提供了一個「resetNamespace:true」選項能夠用戶重置子路由的命名空間,使用這個設置的路由能夠直接這樣訪問「/子路由名」,不須要寫父路由名。
this.route('posts', function() { this.route('post', { path: '/:post_id'}); this.route('comments', { resetNamespace: true}, function() { this.route('new'); }); });
此時若是你想問的new這個路由你能夠直接不寫comments。直接訪問http://localhost:4200/posts/new,而不須要這樣訪問http://localhost:4200/posts/comments/new,不過模板渲染的順序沒變,new模板仍然是渲染到comments的{{outlet}}上。
不過我的以爲仍是不使用這個設置比較好,特別是在開發的時候你能夠看到訪問的URL的層次,對你調試代碼仍是頗有幫助的。
以上的內容就是定義路由的所有內容。都是很是重要的知識,但願你能好好掌握,對於路由的嵌套請看以前的文章。若是有疑問請給我留言或者訪問官網看原教程。