KnockoutJS 3.X API 第四章 數據綁定(5) 控制流component綁定

本節目錄:

  • 一個例子
  • API
  • 備註1:僅模板式的component
  • 備註2:component虛擬綁定
  • 備註3:傳遞標記到component綁定
  • 內存管理

一個例子

First instance, without parameters

Second instance, passing parameters

UI源碼:app

<h4>First instance, without parameters</h4>
<div data-bind='component: "message-editor"'></div>
 
<h4>Second instance, passing parameters</h4>
<div data-bind='component: {
    name: "message-editor",
    params: { initialText: "Hello, world!" }
}'></div>

視圖模型源碼:函數

ko.components.register('message-editor', {
    viewModel: function(params) {
        this.text = ko.observable(params && params.initialText || '');
    },
    template: 'Message: <input data-bind="value: text" /> '
            + '(length: <span data-bind="text: text().length"></span>)'
});
 
ko.applyBindings();

這只是一個很是簡單的例子,在開發中,通常都是將View Model和Template寫成單獨外部文件,而後經過ko的components.register方法註冊他們,在之後的KO高級應用系列中將會進一步講解。this

API

使用component綁定有兩種綁定語法spa

1. 快速語法:

只傳遞一個字符串做爲組件名稱,比提供任何參數。例如:prototype

<div data-bind='component: "my-component"'></div>

若是你以爲這種寫法有些死板的話,也能夠傳遞一個監控屬性,用其值做爲組件名稱。待之後組件名變化的時候,直接修改監控屬性值便可:code

<div data-bind='component: observableWhoseValueIsAComponentName'></div>

2.完整語法:

提供完整的組件參數,參數以下:component

  • name - 注入組件的名稱。可以使用字符串或是監控屬性。
  • params - 一組參數對象。一般,這是一個包含多個參數的鍵值對。

例如:對象

<div data-bind='component: {
    name: "shopping-cart",
    params: { mode: "detailed-list", items: productsList }
}'></div>

備註1:僅模板式的component

一般的component綁定具備ViewModel和Template,可是這並非必須的,有些時候一個component可能只包含一個Template。例如:blog

ko.components.register('special-offer', {
    template: '<div class="offer-box" data-bind="text: productName"></div>'
});

可使用注入的方式,將視圖模型注入給Template:ip

<div data-bind='component: {
     name: "special-offer-callout",
     params: { productName: someProduct.name }
}'></div>

在或者使用客戶元素(之後的高級章節講解)進行注入視圖模型。

<special-offer params='productName: someProduct.name'></special-offer>

如上例子,HTML標記爲模板名稱,其屬性params中注入視圖模型。

備註2:component虛擬綁定

如同以前章節的虛擬綁定同樣,一樣是使用<!-- ko --><!-- /ko -->這種方式實現虛擬綁定,來達到不更改DOM元素的目的

<!-- ko component: "message-editor" -->
<!-- /ko -->

傳參的例子:

<!-- ko component: {
    name: "message-editor",
    params: { initialText: "Hello, world!", otherParam: 123 }
} -->
<!-- /ko -->

備註3:傳遞標記到component綁定

<div data-bind="component: { name: 'my-special-list', params: { items: someArrayOfPeople } }">
    <!-- Look, here's some arbitrary markup. By default it gets stripped out
         and is replaced by the component output. -->
    The person <em data-bind="text: name"></em>
    is <em data-bind="text: age"></em> years old.
</div>

如上例子中,既有component綁定,也有一些DOM元素,當綁定後,my-special-list組件將會和這些DOM元素組成一個新的UI界面。在將來高級章節中,咱們將會提到一個帶有DOM標記的自定義companent綁定的例子。盡情期待。先賣個關子~。

內存管理(瞭解便可,切勿鑽牛角尖)

您的視圖模型類可能有一個dispose函數。若是得以運行,KO將調用這個函數在內存中刪除組件,並從DOM中刪除。

在一下狀況,您必須使用dispose以釋放垃圾收回資源。例如:

  • setInterval 回調後,須要明確清除。
    • 使用clearInterval(handle)去清除他們,不然視圖模型在內存常駐。
  • ko.computed 回調後,直到明確設置成從它們的依賴接收通知。
  • 若是一個依賴關係是外部的對象,那麼必定要使用.dispose()來釋放計算監控屬性,不然(也可能你的視圖模型)將在內存常駐。另外,能夠考慮使用一個pureComputed,以免人工處理的需求。
  • Subscriptions 回掉後,須要明確清除。
    • 若是您已經預訂到外部觀察時,必定要使用.dispose(),不然回調(也可能您的視圖模型)將在內存中常駐。

例如:

var someExternalObservable = ko.observable(123);
 
function SomeComponentViewModel() {
    this.myComputed = ko.computed(function() {
        return someExternalObservable() + 1;
    }, this);
 
    this.myPureComputed = ko.pureComputed(function() {
        return someExternalObservable() + 2;
    }, this);
 
    this.mySubscription = someExternalObservable.subscribe(function(val) {
        console.log('The external observable changed to ' + val);
    }, this);
 
    this.myIntervalHandle = window.setInterval(function() {
        console.log('Another second passed, and the component is still alive.');
    }, 1000);
}
 
SomeComponentViewModel.prototype.dispose = function() {
    this.myComputed.dispose();
    this.mySubscription.dispose();
    window.clearInterval(this.myIntervalHandle);
    // this.myPureComputed doesn't need to be manually disposed.
}
 
ko.components.register('your-component-name', {
    viewModel: SomeComponentViewModel,
    template: 'some template'
});
相關文章
相關標籤/搜索