How to clear/remove observable bindings in Knockout.js? How to clear/remove observable bindings in Knockout.js? javascript javascript

How to clear/remove observable bindings in Knockout.js?


Have you tried calling knockout's clean node method on your DOM element to dispose of the in memory bound objects?

var element = $('#elementId')[0]; ko.cleanNode(element);

Then applying the knockout bindings again on just that element with your new view models would update your view binding.


For a project I'm working on, I wrote a simple ko.unapplyBindings function that accepts a jQuery node and the remove boolean. It first unbinds all jQuery events as ko.cleanNode method doesn't take care of that. I've tested for memory leaks, and it appears to work just fine.

ko.unapplyBindings = function ($node, remove) {    // unbind events    $node.find("*").each(function () {        $(this).unbind();    });    // Remove KO subscriptions and references    if (remove) {        ko.removeNode($node[0]);    } else {        ko.cleanNode($node[0]);    }};


You could try using the with binding that knockout offers:http://knockoutjs.com/documentation/with-binding.htmlThe idea is to use apply bindings once, and whenever your data changes, just update your model.

Lets say you have a top level view model storeViewModel, your cart represented by cartViewModel,and a list of items in that cart - say cartItemsViewModel.

You would bind the top level model - the storeViewModel to the whole page. Then, you could separate the parts of your page that are responsible for cart or cart items.

Lets assume that the cartItemsViewModel has the following structure:

var actualCartItemsModel = { CartItems: [  { ItemName: "FirstItem", Price: 12 },   { ItemName: "SecondItem", Price: 10 }] }

The cartItemsViewModel can be empty at the beginning.

The steps would look like this:

  1. Define bindings in html. Separate the cartItemsViewModel binding.

          <div data-bind="with: cartItemsViewModel">      <div data-bind="foreach: CartItems">        <span data-bind="text: ItemName"></span>        <span data-bind="text: Price"></span>      </div>    </div>  
  2. The store model comes from your server (or is created in any other way).

    var storeViewModel = ko.mapping.fromJS(modelFromServer)

  3. Define empty models on your top level view model. Then a structure of that model can be updated withactual data.

          storeViewModel.cartItemsViewModel = ko.observable();    storeViewModel.cartViewModel = ko.observable(); 
  4. Bind the top level view model.

    ko.applyBindings(storeViewModel);

  5. When the cartItemsViewModel object is available then assign it to the previously defined placeholder.

    storeViewModel.cartItemsViewModel(actualCartItemsModel);

If you would like to clear the cart items: storeViewModel.cartItemsViewModel(null);

Knockout will take care of html - i.e. it will appear when model is not empty and the contents of div (the one with the "with binding") will disappear.