在Ember中路由和模板的執(zhí)行都是有一定順序的,它們的順序為:主路由->子路由1->子路由2->子路由3->……。模板渲染的順序與路由執(zhí)行順序剛好相反,從最后一個模板開始解析渲染。
注意:模板的渲染是在所有路由執(zhí)行完之后,從最后一個模板開始。關(guān)于這一點下面的代碼會演示驗證,官網(wǎng)教程有介紹,點擊查看。
比如有一路由格式為application/posts/detail/comments/comment
,此時路由執(zhí)行的順序為:application/posts
-> detail
-> comments
-> comment
,application
是項目默認(rèn)的路由,用戶自定義的所有路由都是application
的子路由(默認(rèn)情況下),相對應(yīng)的模板也是這樣,所有用戶自定義的模板都是application.hbs
的子模板。如果你要修改模板的渲染層次你可以在route
中重寫renderTemplate
回調(diào)函數(shù),在函數(shù)內(nèi)使用render
方法指定要渲染的模板(如:render('other')
,渲染到other
這個模板上)更多有關(guān)信息請查看這里。并且它們對應(yīng)的文件模板結(jié)構(gòu)如下圖:
路由與模板是相對應(yīng)的,所以模板的目錄結(jié)構(gòu)與路由的目錄結(jié)構(gòu)是一致的。 你有兩種方式構(gòu)建上述目錄:
comment.js
使用命令:ember generate route posts/detail/comments/comment
,Ember CLI會自動為我們創(chuàng)建目錄和文件。創(chuàng)建好目錄結(jié)構(gòu)之后我們添加一些代碼到每個文件。運行項目之后你就會一目了然了……。 下面我按前面講的路由執(zhí)行順序分別列出每個文件的內(nèi)容。
// app/routes/posts.js
import Ember from 'ember';
export default Ember.Route.extend({
model: function() {
console.log('running in posts...');
return { id: 1, routeName: 'The route is posts'};
// return Ember.$.getJSON('https://api.github.com/repos/emberjs/ember.js/pulls');
}
});
import Ember from 'ember';
export default Ember.Route.extend({
model: function(params) {
console.log('params id = ' + params.post_id);
console.log('running in detail....');
return { id: 1, routeName: 'The route is detail..' };
}
});
// app/routes/posts/detail.js
import Ember from 'ember';
export default Ember.Route.extend({
model: function(params) {
console.log('params id = ' + params.post_id);
console.log('running in detail....');
return { id: 1, routeName: 'The route is detail..' };
}
});
// app/routes/posts/detail/comments.js
import Ember from 'ember';
export default Ember.Route.extend({
model: function() {
console.log('running in comments...');
return { id: 1, routName: 'The route is comments....'};
}
});
// app/routes/posts/detail/comments/comment.js
import Ember from 'ember';
export default Ember.Route.extend({
model: function(params) {
console.log('params id = ' + params.post_id);
console.log('running in comment...');
return { id: 1, routeName: 'The route is comment...'};
}
});
下面是模板各個文件的內(nèi)容。其列出才順序與路由的順序一致。
{{model.routeName}} >> {{outlet}}
{{model.routeName}} >> {{outlet}}
{{model.routeName}} >> {{outlet}}
{{model.routeName}} >> {{outlet}}
下圖是路由執(zhí)行的順序,并且在執(zhí)行的過程中渲染路由對應(yīng)的模板。
從上圖中可用清楚的看到當(dāng)你運行一個URL時,與URL相關(guān)的路由是怎么執(zhí)行的。
application
),此時進入到路由的model
回調(diào)方法,并且返回了一個對象{ id: 1, routeName: 'The route is application...' }
,執(zhí)行完回調(diào)之后繼續(xù)轉(zhuǎn)到子路由執(zhí)行直到最后一個路由執(zhí)行完畢,所有的路由執(zhí)行完畢之后開始渲染頁面。detail.js
和
comments.js
。在代碼中加入一個模擬休眠的操作。
// app/routes/posts/detail.js
import Ember from 'ember';
export default Ember.Route.extend({
model: function(params) { console.log('params id = ' + params.post_id); console.log('running in detail....');
// 執(zhí)行一個循環(huán),模擬休眠 for (var i = 0; i < 10000000000; i++) {
}
console.log('The comment route executed...');
return { id: 1, routeName: 'The route is detail..' }; } });
```javascript
// app/routes/posts/detail/comments.js
import Ember from 'ember';
export default Ember.Route.extend({
model: function(params) {
console.log('params id = ' + params.post_id);
console.log('running in comment...');
// 執(zhí)行一個循環(huán),模擬休眠
for (var i = 0; i < 10000000000; i++) {
}
return { id: 1, routeName: 'The route is comment...'};
}
});
刷新頁面,注意查看控制臺輸出信息和頁面顯示的內(nèi)容。 新開一個窗口,執(zhí)行URL:http://localhost:4200/posts/2/comments。
控制臺輸出到這里時處理等待(執(zhí)行for
循環(huán)),此時已經(jīng)執(zhí)行了兩個路由application
和posts
,并且正在執(zhí)行detail
,但是頁面是空白的,沒有任何HTML元素。
在detail
路由執(zhí)行完成之后轉(zhuǎn)到路由comments
。然后執(zhí)行到for
循環(huán)模擬休眠,此時頁面仍然是沒有任何HTML元素。然后等到所有route
執(zhí)行完畢之后,界面才顯示model
回調(diào)里設(shè)置的信息。
每個子路由設(shè)置的信息都會渲染到最近一個父路由對應(yīng)模板的{{outlet}}
上面。
comment
得到的內(nèi)如為:“comment
渲染完成”comment
最近的父模板comments
得到的內(nèi)容為:“comment
渲染完成 comments
渲染完成”comments
最近的父模板detail
得到的內(nèi)容為:“comment
渲染完成 comments
渲染完成 detail
渲染完成”detail
最近的父模板posts
得到的內(nèi)容為:“comment
渲染完成 comments
渲染完成 detail
渲染完成 posts
渲染完成”posts
最近的父模板application
得到的內(nèi)容為:“comment
渲染完成 comments
渲染完成 detail
渲染完成 posts
渲染完成 application
渲染完成”
只要記住一句話:子模板的都會渲染到父模板的{{outlet}}
上,最終所有的模板都會被渲染到application
的{{outlet}}
上。
博文完整代碼放在Github(博文經(jīng)過多次修改,博文上的代碼與github代碼可能又出入,不過影響不大?。?,如果你覺得博文對你有點用,請在github項目上給我點個star
吧。您的肯定對我來說是最大的動力??!
更多建議: