JSFiddle - React, Tailwind, and code Playground
HTML
<script src="http://ajax.aspnetcdn.com/ajax/knockout/knockout-3.3.0.js"></script>
<div class="container">
<div class="m-col-6" id="ko-input-1" data-bind="with: deliveryViewModel">
<h1>Input 1</h1>
<input type="number" data-bind="value: messageForVM2, valueUpdate:'keyup'" />
</div>
<div class="m-col-6" id="ko-output-1" data-bind="with: deliveryViewModel">
<p data-bind="text:message"></p>
</div>
<div class="m-col-6" id="ko-input-2">
<ul>
<li data-bind="with: productViewModel">
<h1>ProductName 1</h1>
<p>ProductId 1</p>
<input type="checkbox" data-bind="init, checked: productClip"/>
<label>has pump clips</label>
<input type="number" data-bind="init, value: productQty"/>
<button data-bind="init, click: addItem">add to list</button>
</li>
<li data-bind="with: productViewModel">
<h1>ProductName 2</h1>
<p>ProductId 2</p>
<input type="checkbox" data-bind="init, checked: productClip"/>
<label>has pump clips</label>
<input type="number" data-bind="init, value: productQty"/>
<button data-bind="init, click: addItem">add to list</button>
</li>
</ul>
</div>
<div class="m-col-6" id="ko-output-2" data-bind="with: productViewModel">
<ul data-bind="foreach: items">
<li>
<h2 data-bind="text: productTitle"></h2>
<label data-bind="if: productClip">has clip</label>
<label data-bind="ifnot: productClip">does not have clip</label>
<input type="number" data-bind="value: productQty" />
<button data-bind="click: $parent.removeItem">Remove</button>
</li>
</ul>
</div>
...
JavaScript
var binding = {
init: function(){
this.deliveryController();
this.productController();
this.masterViewMOdel();
},
masterViewMOdel: function(){
var self = this;
self.shouter = new ko.subscribable();
self.masterVM = (function(){
this.deliveryViewModel = new self.deliveryViewModel(),
this.productViewModel = new self.productViewModel()
})();
ko.applyBindings(self.masterVM);
},
deliveryController: function(){
var self = this;
self.deliveryViewModel = function() {
var vm1 = this;
vm1.messageForVM2 = ko.observable("");
vm1.message = ko.computed(function(){
return "Output 1 = " + vm1.messageForVM2();
})
};
},
productController: function(){
this.productViewModel = function() {
var self = this;
self.items = ko.observableArray();
self.productQty = ko.observable('1');
self.productClip = ko.observable();
//self.productTitle = ko.observable();
self.addItem = function(item, event){
ptitle = $(event.currentTarget).prev('h3').text();
self.items.push({
productQty: self.productQty(),
productClip: self.productClip(),
productTitle: ptitle
});
}
self.removeItem = function(item, event) {
self.items.remove(item);
}
};
}
};
// http://jsfiddle.net/THJE3/22/
$(document).ready(function(){
binding.init();
});