I have the code duplication problem in the next case. On my page I have a lot of blocks that I need to show / hide by clicking to link:
<div>
<a data-bind="click: showHiddenFirst, visible: isVisibleFirst"href="#">Show first</a>
<div data-bind="visible: !isVisibleFirst()" style="display:none">
hidden content first
</div>
</div>
<div>
<a data-bind="click: showHiddenSecond, visible: isVisibleSecond"href="#">Show second</a>
<div data-bind="visible: !isVisibleSecond()" style="display:none">
hidden content second
</div>
</div>
And my JS
var vm = function(){
this.isVisibleFirst = ko.observable(true);
this.showHiddenFirst = function(){
this.isVisibleFirst(false)
};
this.isVisibleSecond = ko.observable(true);
this.showHiddenSecond = function(){
this.isVisibleSecond(false)
};
};
ko.applyBindings(new vm());
Here is jsfiddle example http://jsfiddle.net/sstude/brCT9/2/
Question is how to avoid all this show / visible duplication? Maybe I need some custom binding where I put id of my hidden block or smth. else? Any patterns that you can suggest?
To read the observable's current value, just call the observable with no parameters. In this example, myViewModel. personName() will return 'Bob' , and myViewModel. personAge() will return 123 .
The $data variable is a built-in variable used to refer to the current object being bound. In the example this is the one of the elements in the viewModel.
To apply bindings for the whole HTML document, it can be done using the Knockout function applyBindings() with passing the view model as the first and the only parameter: ko. applyBindings(viewModel); To apply Knockout for a part of the HTML document, pass the DOM element as a second parameter: ko.
Knockout. js defines an important role when we want to detect and respond to changes on one object, we uses the observable. An observable is useful in various scenarios where we are displaying or editing multiple values and require repeated sections of the UI to appear and disappear as items are inserted and deleted.
Here was a thought at encapsulating this functionality completely in an observable for your specific scenario:
ko.bindingHandlers.clickVisible = {
init: function(element) {
var visible = ko.observable(true),
opposite = ko.computed(function() { return !visible(); }),
clickHandler = visible.bind(null, false);
//apply bindings to anchor
ko.applyBindingsToNode(element, { click: clickHandler, visible: visible });
var sibling = element.nextSibling;
//find the div (as text nodes, etc. will show up in nextSibling)
while (sibling && sibling.nodeType != 1) {
sibling = sibling.nextSibling;
}
//apply bindings to div
if (sibling) {
ko.applyBindingsToNode(sibling, { visible: opposite });
}
}
};
It could be tweaked further, as necessary, if maybe the value passed into the binding should matter.
Example: http://jsfiddle.net/rniemeyer/gCgy5/
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With