2013-12-09 74 views
2

我有一個div,我使用淘汰賽的綁定。例如,jquery刪除函數是否也刪除淘汰賽的綁定?

<div id='my_div'> 
    <span data-bind="text: dialog_body"></span> 
</div> 

所以,淘汰賽綁定:

var viewmodel=function(){ 
this.dialog_body = 'Some text'; 
}; 
ko.applyBindings(new viewmodel(),$("#my_div")[0]); 

現在的問題是:如果我叫$('#my_div').remove();會,這也拆卸的擋板結合或者我應該擔心內存泄漏?

+1

jQuery不知道KO和KO不關心jQuery。看到[cleanNode在這裏討論](http://stackoverflow.com/questions/15063794/can-cleannode-be-used-to-clean-binding)或[這裏](http://stackoverflow.com/questions/10048485 /如何對透明除去可見的 - 綁定 - 在基因敲除-JS?LQ = 1)。但是,如果您將DOM構建爲僅從KO綁定(如果/ foreach/template/views-in-Durandal)被修改爲可觀察對象,則所有內容都應該自動清除。 – user2864740

+0

謝謝,我無法使cleanNode工作。 html和viewmodel都是由jquery-ui動態生成的。所以,我試圖在綁定之前清理節點,但是如果沒有綁定,它會拋出錯誤。 – faisal

回答

0

jQuery有無關淘汰賽。它可以刪除節點 - 但這不會清除任何綁定的KO可觀察對象。在給定的情況下,這意味着有一個輕微的內存泄漏,因爲KO通過內部集合維護數據(請參閱ko.utils.domData),只需使用jQuery刪除節點即可。

兩個後本身在KO用於清理傳統方法是cleanNoderemoveNode(但是也不會除去結合事件!)根據需要應該使用哪個..使用cleanNode(經由KO結合的節點上)是最小需要清理數據。


然而,我不認爲這是一個合適的地方人工清理KO!如果使用正確,標準綁定將已經處理清理。

而是編寫如下的代碼。 (見Creating custom bindings that control descendant bindingswithProperties;你還必須要make it virtual-element compatible下面使用。)

<div id='my_div'> 
    <!--ko 'if': someObservable--> 
    <!--ko withProperties: { data: someObservable() }--> 
     <span data-bind="text: data.dialog_body"></span> 
    <!--/ko--> 
    <!--/ko--> 
</div> 

然後只需將觀察到的東西來創建節點..

someObservable(myVm) 

..或undefined來清除它..

someObservable(undefined) 

畢竟,一個一般不會真的$('#my_div').remove()而是要$('#my_div').dialog('close')。實際上,刪除節點也會起作用,只要稍後爲新對話框添加相同的元素即可。

someObservable值可能來自「根」視圖模型 - 我建議有一個根視圖模型! - 或者它可能來自一個窗口屬性,爲那些感覺hackish:

window.someObservable = ko.observable() 
+0

擁有全局可觀察值對我來說不是一種選擇,因爲我在一個非常大的項目中工作,全局變量可能會搞砸了一些事情。但是,如果我可以從一個id獲得當前綁定,那麼我可以更改該綁定上的observable。也許'ko.dataFor'或者'ko.contextFor'會有幫助。 – faisal

+0

@faisal這聽起來像是一個大項目需要一些愛!而且我會*推薦上述方法 - 但是將其作爲包含模型的可觀察部分。你有沒有看過使用[Durandal](http://durandaljs.com/)?它可以很容易地將模型應用於不同的「視圖」。 (雖然它支持SPA,但它不需要用作SPA。) – user2864740

+0

好的,我將介紹一下Durandal。謝謝。我會試驗它並讓你知道。 – faisal

0

您不應該需要從DOM中刪除跨度。只需修改您的KO跨度以包含可見布爾值的「可見」綁定。然後,當你想「隱藏」你的跨度時,只需將布爾值設置爲false即可。

<span data-bind="text: dialog_body, visible: show_span"></span> 
在KO代碼

然後,讓你的布爾觀察到:

var viewModel = { 
    show_span: ko.observable(true); 
} 

而當你準備好隱藏跨度:

viewModel.show_span(false); 
+0

我的問題比我給出的例子更復雜。我試圖在jquery-ui對話框上綁定knockout模板。 – faisal