Knockoutjs "with" Binding Before Model Is Available
I have an ASP.NET MVC4 SPA web application using KnockoutJS, which is a bit awkward because, as I understand it, when the page initially loads in an SPA there is generally no data
Solution 1:
I have implemented a custom bindIf
binding handler that improved our results significantly by postponing binding logic until the observable has a valid value inside it:
ko.bindingHandlers.bindIf = {
'init': function (element, valueAccessor) {
return { 'controlsDescendantBindings': true };
},
'update': function (element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
if (!$(element).data("bindIfPassed") && valueAccessor()) {
$(element).data("bindIfPassed", true);
ko.applyBindingsToDescendants(bindingContext, element);
}
}
}
Applied to a high level node like this:
<div data-bind="bindIf: myObservable()">
Solution 2:
I can see reasons why you would not want the DOM inside a with-bound element to disappear, but they are very few. Pretty much all of them involve DOM manipulation that requires certain timing. For example, setting the focus to the first input field when a view is shown. Sometimes, the workaround for such problems isn't pretty, in which case a binding like yours would definetly help a lot.
In general,
- I suppose this is somewhat of a common problem. You mention a few problems: Scripts relying on the presence of those elements: in general, I would respond that your scripts are wrong. Now that's a bit harsh, but I do feel it's a bit of a code smell that your scripts would come crashing down if a certain DOM element isn't available. Second, you feel that parts of the dom disappearing and reappearing is not such a good thing. In this case, maybe you should 'reset' the observable in your with binding to something else than 'null'. Create a 'blank' instance of whatever object normally goes into the observable, and use that instead of null, so your DOM remains intact. If this is not an option, then your scenario is not really a use case for the with-binding (and your own binding would indeed be a helpful one for such scenarios).
- I'm not entirely sure. I tried to look into the with-binding, but for some reason I can't spot it in the Knockout code. It's tested easily though, just set up an event binding within the with binding, then change the observable's value a few times. It does seem a bit worrying that you never update the with-binding when the value is undefined/null though: I can imagine this can easily lead to binding errors further down the DOM.
- There are certainly good reasons for this, especially in a Single Page Application. I'm doing a pretty huge application with Knockout as an SPA. By proper use of the with-binding and cleaning up my viewmodels when a view is unloaded, I can manage memory (of which DOM nodes are a big part) pretty easily, even though views are cached on the frontend. The application would run extremely slowly if we didn't have a mechanism for unloading DOM nodes when the relevant data is not present. This is a data-driven approach I really enjoy: the parts of the DOM that are shown are the parts that are relevant, because the data is there.
Post a Comment for "Knockoutjs "with" Binding Before Model Is Available"