2012-02-27 78 views
0

我有一個backbone.js應用程序,其視圖具有多個狀態,這些狀態彼此之間有很大不同(「視圖」,「編輯」等)。每個視圖至少有2個不同的模板。還行吧。我的問題是與JS視圖管理代碼。用複雜狀態管理視圖

我依賴於initalize-thin-render-thick方法(我認爲這很糟糕),其中render方法是邏輯發生的80%-90%。當我想更改狀態時,我只需使用特定參數(「view」,「edit」)調用render方法即可。在此基礎上,視圖決定要展示什麼,不知道什麼,要綁定哪些事件等。

我認爲這是不好的,因爲一方面它會在渲染過程中造成瓶頸,另一方面,這不是合適的狀態機,這意味着我沒有進行可能以前被綁定的回調。當我收到視圖時,我只是清理視圖,就是這樣。我還觀察到,我沒有使用骨幹提供的委託事件系統,我認爲這是另一個減號,因爲我認爲它很好地實現(順便說一句,它是否確保解除綁定回調,何時某個DOM元素被刪除?)

我想我需要一些嚴重的重構。請幫助一些建議,以確定多態Backone視圖的最佳方法。

回答

2

我對這些情況傾向於做一個頂層視圖,管理每個單獨狀態(索引,顯示,編輯等)的子視圖。當用戶動作被調用時,例如「編輯此用戶」,「刪除此用戶」,「保存我的更改」,活動狀態視圖通知路由器(直接或通過超鏈接),路由器將通知頂層視圖更新其狀態。

繼續用戶編輯器的例子,假設我有一個名爲UserEditorView的頂級視圖。它呈現用戶編輯器的基本容器(標題欄等),然後默認情況下,實例化並呈現該容器內的Users.IndexView。

Users.IndexView呈現用戶列表。每個用戶旁邊都有一個編輯圖標,它是「#users/555/edit」的鏈接。所以,當用戶點擊它時,那個事件會發送到路由器,它告訴UserEditorView,「嘿,我想編輯用戶#555」。然後UserEditorView將刪除IndexView(通過調用它的.remove()方法),爲相應的用戶模型實例化Users.EditView,並將EditView放入容器中。

當用戶完成編輯用戶時,她點擊「保存」,然後EditView保存模型。現在我們需要回到IndexView。 EditView調用window.router.navigate('users',{trigger:true}),所以URL被更新並且路由器被調用。路由器然後調用UserEditorView上的.showIndex(),並且UserEditorView將該交換從EditView切換回IndexView。

0

在一個管理事件卸載的簡單方法中,我找到了this article on zombie views quite useful

基本上,我沒有頂層視圖,但我使用視圖處理程序來處理給定容器的視圖,從而渲染所有視圖。

爲了使您的渲染器更薄,我建議使用路線。它們很容易設置,並且您可以爲每條路線提供不同的視圖。或者,我習慣做的只是擁有不同的模板。使用一般Backbone.View覆蓋:

Backbone.View = Backbone.View.extend({ 
    initialize: function(attrs) { 
     attrs = attrs || {} 
     if(!_.isUndefined(attrs.template)) { 
     this.template = attrs.template; 
     } 
    } 
}); 

我注意到,我的看法重用有兩種方式:1 。編輯視圖僅在底層模型和模板中有所不同,但不是相關的邏輯(點擊提交驗證並保存模型) 2.同一視圖可以在具有不同模板的多個位置重用(比如用戶列表作爲排名或你的賬戶)

通過上面的擴展,我可以將{template:'/ my/current/template /}傳遞給視圖,並且它將被渲染爲我想要的。與路線一起,我終於得到了一個靈活的,易於理解和精簡的設置。