Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Custom Binding Handlers With Knockout and RequireJS

I'm having an issue applying custom binding handlers when using knockout with requireJS. Basically, in the past I've included a global binding-handler js file that contains all my custom bindings. Now that I'm using requireJS to enforce dependencies, I'm not sure how to access these custom bindings.

I used to do create the global functions with

function KOCustomBindings() {
// Custom Bindings
ko.bindingHandlers.returnKey = {
//handler code
}
}

Now that I'm using require, I feel as if I should have a define statement

define(['jquery', 'knockout'],
    function($, ko)){
// Custom Bindings
return KOCustomBindings;
}
});

However, I don't believe the bindings will execute unless specifically called, perhaps in a shim? Does anyone have any ideas on this?

Thanks for your help,

like image 345
Tui Popenoe Avatar asked Jul 10 '13 15:07

Tui Popenoe


2 Answers

Since custom bindings modify the ko object, they only need to be loaded once, and their modules do not need to return anything. If you have a main/entry/app section as the first step in your app, simply requiring your custom bindings and extenders is all you need to do.

define(['jquery', 'knockout'], function($, ko)){
    // Custom Bindings
    ko.bindingHandlers.returnKey = { ... }

    //NO return needed
});

Then, in your startup section, just

require('lib/custom-ko-bindings');
like image 193
Kyeotic Avatar answered Sep 29 '22 21:09

Kyeotic


An easy way to do this is to define your custom binding as an AMD module and require it from your parent viewmodel. Example -

Bindings.js

define(, function () {
    ko.bindingHandlers.Date = {
        update: function (element, valueAccessor) {
            var value = valueAccessor();
            var date = moment(value());
            var strDate = date.format('MM-DD-YYYY');
            $(element).text(strDate);
        }
    };
});

Your viewmodel -

define(['jquery', 'knockout', 'bindings'],
    function($, ko, bindings)){
});

This will give any element in your DOM access to the Knockout binding handler of 'Date' for example. (My example is one that I have used with moment.js)

In any child views or views that require your parent view model now you should be able to use

<span data-bind="Date: myDate" />
like image 32
PW Kad Avatar answered Sep 29 '22 20:09

PW Kad