Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Calling Knockout function from outside ViewModel

In my specific example, there are several different widgets that have their own encapsulated ViewModel. I need a global Save button that saves each individual ViewModel. I can't seem to figure out how to call functions on the individual ViewModels.

Example - how can I call the Save function on each ViewModel: http://jsfiddle.net/sNSh2/4/

var ViewModel1 = function() {
    var self = this;
    self.firstName = ko.observable('');
    self.lastName = ko.observable('');

    self.firstName('John');
    self.lastName('Doe');

    self.Save = function () {
        alert(ko.toJSON(self));
    };
};
ko.applyBindings(new ViewModel1(), document.getElementById("person"));

var ViewModel2 = function() {
    var self = this;
    self.subscriptionLevel = ko.observable('');

    self.subscriptionLevel('premier');

    self.Save = function () {
        alert(ko.toJSON(self));
    };
};
ko.applyBindings(new ViewModel2(), document.getElementById("subscription"));

$('#save').on('click', function() {

});
like image 798
Mike Cole Avatar asked Mar 18 '14 21:03

Mike Cole


People also ask

Is knockout JS Mvvm?

Yes, knockout. js does apply the MVVM pattern. It's explained in the documentation: A model: your application's stored data.

What is applyBindings in knockout?

applyBindings do, The first parameter says what view model object you want to use with the declarative bindings it activates. Optionally, you can pass a second parameter to define which part of the document you want to search for data-bind attributes. For example, ko.

How to Bind click event in Knockout?

The function you want to bind to the element's click event. You can reference any JavaScript function - it doesn't have to be a function on your view model. You can reference a function on any object by writing click: someObject. someFunction .

What is knockout ViewModel JS?

A ViewModel can be any type of JavaScript variable. In Example 1-3, let's start with a simple JavaScript structure that contains a single property called name .


2 Answers

I don't understand your problem, why not simply hold a reference of your model object?

$(function() {
  ...
  var m1 = new ViewModel1();
  ko.applyBindings(m1, document.getElementById("person"));

  ...
  var m2 = new ViewModel2();
  ko.applyBindings(m2, document.getElementById("subscription"));

  $('#save').on('click', function() {
    m1.Save();
    m2.Save();
  });
});

If you really have problem to get references of all model objects (maybe defined in isolated js files), ko provided way to get context object out from associated DOM object. You can still do this:

ko.contextFor(document.getElementById("person")).$data.Save();
ko.contextFor(document.getElementById("subscription")).$data.Save();
like image 145
huocp Avatar answered Oct 21 '22 03:10

huocp


Knockout has basic pub/sub functionality. try this on for size jsFiddle

var postbox = ko.observable();

var ViewModel1 = function() {
    var self = this;
    self.firstName = ko.observable('');
    self.lastName = ko.observable('');

    self.firstName('John');
    self.lastName('Doe');

    self.Save = function () {
        alert(ko.toJSON(self));
    };
    postbox.subscribe(function(newValue){
        self.Save();
    }, self, 'save');
};
ko.applyBindings(new ViewModel1(), document.getElementById("person"));

var ViewModel2 = function() {
    var self = this;
    self.subscriptionLevel = ko.observable('');

    self.subscriptionLevel('premier');

    self.Save = function () {
        alert(ko.toJSON(self));
    };

    postbox.subscribe(function(newValue){
        self.Save();
    }, self, 'save');
};
ko.applyBindings(new ViewModel2(), document.getElementById("subscription"));

$('#save').on('click', function() {
    postbox.notifySubscribers(null, "save");
});
like image 42
Nathan Fisher Avatar answered Oct 21 '22 05:10

Nathan Fisher