Browse files

Support for handling events from child bindings to address issue #5.

  • Loading branch information...
1 parent a52e67a commit fa785eee2e8d2f6615b9d1982238f772a8192a3d @rniemeyer committed Apr 18, 2012
View
97 build/knockout-kendo.js
@@ -1,5 +1,5 @@
//knockout-kendo v0.2.0 | (c) 2012 Ryan Niemeyer | http://www.opensource.org/licenses/mit-license
-(function(ko, $, undefined) {
+(function(ko, $, undefined) {
ko.kendo = ko.kendo || {};
ko.kendo.BindingFactory = function() {
@@ -14,7 +14,7 @@ ko.kendo.BindingFactory = function() {
var binding = {};
//the binding handler's init function
- binding.init = function(element, valueAccessor, allBindingsAccessor) {
+ binding.init = function(element, valueAccessor) {
//step 1: build appropriate options for the widget from values passed in and global options
var options = self.buildOptions(widgetConfig, valueAccessor);
@@ -33,12 +33,12 @@ ko.kendo.BindingFactory = function() {
binding.setup = function(element, options) {
var widget, $element = $(element);
- //step 2: add handlers for events that we need to react to for updating the model
- self.handleEvents(widgetConfig.events, options, function() { return $element.data(widgetConfig.name); });
-
- //step 3: initialize widget
+ //step 2: initialize widget
widget = self.getWidget(widgetConfig, options, $element);
+ //step 3: add handlers for events that we need to react to for updating the model
+ self.handleEvents(options, widgetConfig, element, widget);
+
//step 4: set up computed observables to update the widget when observable model values change
self.watchValues(widget, options, widgetConfig, element);
@@ -123,36 +123,36 @@ ko.kendo.BindingFactory = function() {
};
//write changes to the widgets back to the model
- this.handleEvents = function(events, options, widgetAccessor) {
- var prop, event;
+ this.handleEvents = function(options, widgetConfig, element, widget) {
+ var prop, event, events = widgetConfig.events;
+
if (events) {
for (prop in events) {
if (events.hasOwnProperty(prop)) {
event = events[prop];
- event = typeof event === "string" ? { value: event, writeTo: event } : event;
+ if (typeof event === "string") {
+ event = { value: event, writeTo: event };
+ }
+
if (ko.isObservable(options[event.writeTo])) {
- self.handleOneEvent(prop, event, options, widgetAccessor);
+ self.handleOneEvent(prop, event, options, element, widget, widgetConfig.childProp);
}
}
}
}
};
- //set on options for now, as using bind does not work for many events
- this.handleOneEvent = function(event, eventOptions, options, widgetAccessor) {
- var existing = options[event];
- options[event] = function() {
- var propOrValue = eventOptions.value,
- widget = widgetAccessor(),
- value = (typeof propOrValue === "string" && widget[propOrValue]) ? widget[propOrValue]() : propOrValue;
+ //bind to a single event
+ this.handleOneEvent = function(eventName, eventConfig, options, element, widget, childProp) {
+ widget.bind(eventName, function(e) {
+ var propOrValue, value;
- options[eventOptions.writeTo](value);
-
- //if they passed in a handler in addition to the handling that we need done
- if (existing) {
- existing.apply(this, arguments);
+ if (!childProp || !e[childProp] || e[childProp] === element) {
+ propOrValue = eventConfig.value;
+ value = (typeof propOrValue === "string" && this[propOrValue]) ? this[propOrValue](childProp && element) : propOrValue;
+ options[eventConfig.writeTo](value);
}
- };
+ });
};
};
@@ -180,6 +180,7 @@ var CLOSE = "close",
MAX = "max",
MIN = "min",
OPEN = "open",
+ RESIZE = "resize",
SEARCH = "search",
SELECT = "select",
SELECTED = "selected",
@@ -365,11 +366,21 @@ createBinding({
createBinding({
name: "kendoPanelItem",
parent: "kendoPanelBar",
- updateableOptions: [ENABLE],
watch: {
enabled: ENABLE,
expanded: [EXPAND, COLLAPSE]
},
+ childProp: "item",
+ events: {
+ expand: {
+ writeTo: EXPANDED,
+ value: true
+ },
+ collapse: {
+ writeTo: EXPANDED,
+ value: false
+ }
+ },
async: true
});
createBinding({
@@ -408,6 +419,18 @@ createBinding({
size: SIZE,
expanded: [EXPAND, COLLAPSE]
},
+ childProp: "pane",
+ events: {
+ collapse: {
+ writeTo: EXPANDED,
+ value: false
+ },
+ expand: {
+ writeTo: EXPANDED,
+ value: true
+ },
+ resize: SIZE
+ },
async: true
});
createBinding({
@@ -424,6 +447,13 @@ createBinding({
},
enabled: ENABLE
},
+ childProp: "item",
+ events: {
+ selected: {
+ writeTo: SELECTED,
+ value: true
+ }
+ },
async: true
});
createBinding({
@@ -451,10 +481,25 @@ createBinding({
watch: {
enabled: ENABLE,
expanded: [EXPAND, COLLAPSE],
- select: function(element, value) {
+ selected: function(element, value) {
this.select(value ? element : null);
}
},
+ childProp: "node",
+ events: {
+ collapse: {
+ writeTo: EXPANDED,
+ value: false
+ },
+ expand: {
+ writeTo: EXPANDED,
+ value: true
+ },
+ select: {
+ writeTo: SELECTED,
+ value: true
+ }
+ },
async: true
});
createBinding({
@@ -481,5 +526,5 @@ createBinding({
isOpen: [OPEN, CLOSE]
}
});
-
+
})(ko, jQuery);
View
2 build/knockout-kendo.min.js
@@ -1,2 +1,2 @@
//knockout-kendo v0.2.0 | (c) 2012 Ryan Niemeyer | http://www.opensource.org/licenses/mit-license
-(function(a,b,c){a.kendo=a.kendo||{},a.kendo.BindingFactory=function(){var c=this;this.createBinding=function(d){if(!b()[d.parent||d.name])return;var e={};e.init=function(a,b,f){var g=c.buildOptions(d,b);if(g.async===!0||d.async===!0&&g.async!==!1){setTimeout(function(){e.setup(a,g)},0);return}e.setup(a,g)},e.setup=function(e,f){var g,h=b(e);c.handleEvents(d.events,f,function(){return h.data(d.name)}),g=c.getWidget(d,f,h),c.watchValues(g,f,d,e),g.destroy&&a.utils.domNodeDisposal.addDisposeCallback(e,function(){g.destroy()})},e.options={},e.widgetConfig=d,a.bindingHandlers[d.bindingName||d.name]=e},this.buildOptions=function(b,c){var d=b.defaultOption,e=a.utils.extend({},a.bindingHandlers[b.name].options),f=a.utils.unwrapObservable(c());return typeof f!="object"||d&&!(d in f)?e[d]=c():a.utils.extend(e,f),e},this.getWidget=function(b,c,d){var e;if(b.parent){var f=d.closest("[data-bind*="+b.parent+":]");e=f.length?f.data(b.parent):null}else e=d[b.name](a.toJS(c)).data(b.name);return a.isObservable(c.widget)&&c.widget(e),e},this.watchValues=function(b,d,e,f){var g,h=e.watch;if(h)for(g in h)h.hasOwnProperty(g)&&a.isObservable(d[g])&&c.watchOneValue(g,b,d,e,f)},this.watchOneValue=function(c,d,e,f,g){a.computed({read:function(){var h=f.watch[c],i=a.utils.unwrapObservable(e[c]),j=f.parent?[g,i]:[i];b.isArray(h)?h=d[i?h[0]:h[1]]:typeof h=="string"&&(h=d[h]),h&&h.apply(d,j)},disposeWhenNodeIsRemoved:g})},this.handleEvents=function(b,d,e){var f,g;if(b)for(f in b)b.hasOwnProperty(f)&&(g=b[f],g=typeof g=="string"?{value:g,writeTo:g}:g,a.isObservable(d[g.writeTo])&&c.handleOneEvent(f,g,d,e))},this.handleOneEvent=function(a,b,c,d){var e=c[a];c[a]=function(){var a=b.value,f=d(),g=typeof a=="string"&&f[a]?f[a]():a;c[b.writeTo](g),e&&e.apply(this,arguments)}}},a.kendo.bindingFactory=new a.kendo.BindingFactory,a.kendo.setDataSource=function(b,c){b.dataSource.data(a.mapping?a.mapping.toJS(c):a.toJS(c))};var d=a.kendo.bindingFactory.createBinding.bind(a.kendo.bindingFactory),e="close",f="collapse",g="content",h="data",i="disable",j="enable",k="expand",l="enabled",m="expanded",n="isOpen",o="max",p="min",q="open",r="search",s="select",t="selected",u="size",v="title",w="value",x="values";d({name:"kendoAutoComplete",events:{change:w,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,search:[r,e],data:function(b){a.kendo.setDataSource(this,b)},value:w}}),d({name:"kendoCalendar",defaultOption:w,events:{change:w},watch:{max:o,min:p,value:w}}),d({name:"kendoComboBox",events:{change:w,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,isOpen:[q,e],data:function(b){a.kendo.setDataSource(this,b)},value:w}}),d({name:"kendoDatePicker",defaultOption:w,events:{change:w,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,max:o,min:p,value:w,isOpen:[q,w]}}),d({name:"kendoDropDownList",events:{change:w,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,isOpen:[q,e],data:function(b){a.kendo.setDataSource(this,b)},value:w}}),d({name:"kendoEditor",defaultOption:w,events:{change:w},watch:{enabled:j,value:w}}),d({name:"kendoGrid",defaultOption:h,watch:{data:function(b){a.kendo.setDataSource(this,b)}}}),d({name:"kendoListView",defaultOption:h,watch:{data:function(b){a.kendo.setDataSource(this,b)}}}),d({name:"kendoMenu",async:!0}),d({name:"kendoMenuItem",parent:"kendoMenu",watch:{enabled:j,isOpen:[q,e]},async:!0}),d({name:"kendoNumericTextBox",defaultOption:w,events:{change:w},watch:{enabled:j,value:w,max:function(a){this.options.max=a,this.value()>a&&this.value(a)},min:function(a){this.options.min=a,this.value()<a&&this.value(a)}}}),d({name:"kendoPanelBar",async:!0}),d({name:"kendoPanelItem",parent:"kendoPanelBar",updateableOptions:[j],watch:{enabled:j,expanded:[k,f]},async:!0}),d({name:"kendoRangeSlider",defaultOption:x,events:{change:x},watch:{values:x,enabled:[j,i]}}),d({name:"kendoSlider",defaultOption:w,events:{change:w},watch:{value:w,enabled:[j,i]}}),d({name:"kendoSplitter",async:!0}),d({name:"kendoSplitterPane",parent:"kendoSplitter",watch:{max:o,min:p,size:u,expanded:[k,f]},async:!0}),d({name:"kendoTabStrip",async:!0}),d({name:"kendoTab",parent:"kendoTabStrip",watch:{selected:function(a,b){this.select(b?a:null)},enabled:j},async:!0}),d({name:"kendoTimePicker",defaultOption:w,events:{change:w},watch:{max:o,min:p,value:w,enabled:j,isOpen:[q,e]}}),d({name:"kendoTreeView",async:!0}),d({name:"kendoTreeItem",parent:"kendoTreeView",watch:{enabled:j,expanded:[k,f],select:function(a,b){this.select(b?a:null)}},async:!0}),d({name:"kendoUpload",watch:{enabled:[j,i]}}),d({name:"kendoWindow",events:{open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{content:g,title:v,isOpen:[q,e]}})})(ko,jQuery)
+(function(a,b,c){a.kendo=a.kendo||{},a.kendo.BindingFactory=function(){var c=this;this.createBinding=function(d){if(!b()[d.parent||d.name])return;var e={};e.init=function(a,b){var f=c.buildOptions(d,b);if(f.async===!0||d.async===!0&&f.async!==!1){setTimeout(function(){e.setup(a,f)},0);return}e.setup(a,f)},e.setup=function(e,f){var g,h=b(e);g=c.getWidget(d,f,h),c.handleEvents(f,d,e,g),c.watchValues(g,f,d,e),g.destroy&&a.utils.domNodeDisposal.addDisposeCallback(e,function(){g.destroy()})},e.options={},e.widgetConfig=d,a.bindingHandlers[d.bindingName||d.name]=e},this.buildOptions=function(b,c){var d=b.defaultOption,e=a.utils.extend({},a.bindingHandlers[b.name].options),f=a.utils.unwrapObservable(c());return typeof f!="object"||d&&!(d in f)?e[d]=c():a.utils.extend(e,f),e},this.getWidget=function(b,c,d){var e;if(b.parent){var f=d.closest("[data-bind*="+b.parent+":]");e=f.length?f.data(b.parent):null}else e=d[b.name](a.toJS(c)).data(b.name);return a.isObservable(c.widget)&&c.widget(e),e},this.watchValues=function(b,d,e,f){var g,h=e.watch;if(h)for(g in h)h.hasOwnProperty(g)&&a.isObservable(d[g])&&c.watchOneValue(g,b,d,e,f)},this.watchOneValue=function(c,d,e,f,g){a.computed({read:function(){var h=f.watch[c],i=a.utils.unwrapObservable(e[c]),j=f.parent?[g,i]:[i];b.isArray(h)?h=d[i?h[0]:h[1]]:typeof h=="string"&&(h=d[h]),h&&h.apply(d,j)},disposeWhenNodeIsRemoved:g})},this.handleEvents=function(b,d,e,f){var g,h,i=d.events;if(i)for(g in i)i.hasOwnProperty(g)&&(h=i[g],typeof h=="string"&&(h={value:h,writeTo:h}),a.isObservable(b[h.writeTo])&&c.handleOneEvent(g,h,b,e,f,d.childProp))},this.handleOneEvent=function(a,b,c,d,e,f){e.bind(a,function(a){var e,g;if(!f||!a[f]||a[f]===d)e=b.value,g=typeof e=="string"&&this[e]?this[e](f&&d):e,c[b.writeTo](g)})}},a.kendo.bindingFactory=new a.kendo.BindingFactory,a.kendo.setDataSource=function(b,c){b.dataSource.data(a.mapping?a.mapping.toJS(c):a.toJS(c))};var d=a.kendo.bindingFactory.createBinding.bind(a.kendo.bindingFactory),e="close",f="collapse",g="content",h="data",i="disable",j="enable",k="expand",l="enabled",m="expanded",n="isOpen",o="max",p="min",q="open",r="resize",s="search",t="select",u="selected",v="size",w="title",x="value",y="values";d({name:"kendoAutoComplete",events:{change:x,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,search:[s,e],data:function(b){a.kendo.setDataSource(this,b)},value:x}}),d({name:"kendoCalendar",defaultOption:x,events:{change:x},watch:{max:o,min:p,value:x}}),d({name:"kendoComboBox",events:{change:x,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,isOpen:[q,e],data:function(b){a.kendo.setDataSource(this,b)},value:x}}),d({name:"kendoDatePicker",defaultOption:x,events:{change:x,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,max:o,min:p,value:x,isOpen:[q,x]}}),d({name:"kendoDropDownList",events:{change:x,open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{enabled:j,isOpen:[q,e],data:function(b){a.kendo.setDataSource(this,b)},value:x}}),d({name:"kendoEditor",defaultOption:x,events:{change:x},watch:{enabled:j,value:x}}),d({name:"kendoGrid",defaultOption:h,watch:{data:function(b){a.kendo.setDataSource(this,b)}}}),d({name:"kendoListView",defaultOption:h,watch:{data:function(b){a.kendo.setDataSource(this,b)}}}),d({name:"kendoMenu",async:!0}),d({name:"kendoMenuItem",parent:"kendoMenu",watch:{enabled:j,isOpen:[q,e]},async:!0}),d({name:"kendoNumericTextBox",defaultOption:x,events:{change:x},watch:{enabled:j,value:x,max:function(a){this.options.max=a,this.value()>a&&this.value(a)},min:function(a){this.options.min=a,this.value()<a&&this.value(a)}}}),d({name:"kendoPanelBar",async:!0}),d({name:"kendoPanelItem",parent:"kendoPanelBar",watch:{enabled:j,expanded:[k,f]},childProp:"item",events:{expand:{writeTo:m,value:!0},collapse:{writeTo:m,value:!1}},async:!0}),d({name:"kendoRangeSlider",defaultOption:y,events:{change:y},watch:{values:y,enabled:[j,i]}}),d({name:"kendoSlider",defaultOption:x,events:{change:x},watch:{value:x,enabled:[j,i]}}),d({name:"kendoSplitter",async:!0}),d({name:"kendoSplitterPane",parent:"kendoSplitter",watch:{max:o,min:p,size:v,expanded:[k,f]},childProp:"pane",events:{collapse:{writeTo:m,value:!1},expand:{writeTo:m,value:!0},resize:v},async:!0}),d({name:"kendoTabStrip",async:!0}),d({name:"kendoTab",parent:"kendoTabStrip",watch:{selected:function(a,b){this.select(b?a:null)},enabled:j},childProp:"item",events:{selected:{writeTo:u,value:!0}},async:!0}),d({name:"kendoTimePicker",defaultOption:x,events:{change:x},watch:{max:o,min:p,value:x,enabled:j,isOpen:[q,e]}}),d({name:"kendoTreeView",async:!0}),d({name:"kendoTreeItem",parent:"kendoTreeView",watch:{enabled:j,expanded:[k,f],selected:function(a,b){this.select(b?a:null)}},childProp:"node",events:{collapse:{writeTo:m,value:!1},expand:{writeTo:m,value:!0},select:{writeTo:u,value:!0}},async:!0}),d({name:"kendoUpload",watch:{enabled:[j,i]}}),d({name:"kendoWindow",events:{open:{writeTo:n,value:!0},close:{writeTo:n,value:!1}},watch:{content:g,title:w,isOpen:[q,e]}})})(ko,jQuery)
View
2 spec/knockout-kendo-bindingSpecFactory.js
@@ -36,7 +36,7 @@ var generateBasicTests = function(widgetConfig) {
it("should add an init function", function() {
expect(typeof ko.bindingHandlers[widgetConfig.name].init).toEqual("function");
- expect(ko.bindingHandlers[widgetConfig.name].init.length).toEqual(3);
+ expect(ko.bindingHandlers[widgetConfig.name].init.length).toEqual(2);
});
});
};
View
106 spec/knockout-kendo-core.spec.js
@@ -75,114 +75,86 @@ describe("knockout-kendo-core", function(){
describe("handleEvents", function() {
describe("when given an object with events as keys", function() {
- var options, events, widget;
+ var options, widgetConfig, widget;
beforeEach(function() {
options = {
optionOne: ko.observable("one value"),
optionTwo: "two value",
- optionSix: ko.observable("six value"),
- existingSix: function() {}
+ optionSix: ko.observable("six value")
};
- options.eventSix = function() { options.existingSix() };
-
- events = {
- eventOne: {
- writeTo: "optionOne",
- value: "methodOne"
- },
- eventTwo: {
- writeTo:"optionOne",
- value: "not a method"
- },
- eventThree: {
- writeTo: "optionOne",
- value: true
- },
- eventFour: {
- writeTo: "optionTwo",
- value: true
- },
- eventFive: {
- writeTo: "badOption",
- value: true
- },
- eventSix: {
- writeTo: "optionSix",
- value: true
+ widgetConfig = {
+ events: {
+ eventOne: {
+ writeTo: "optionOne",
+ value: "methodOne"
+ },
+ eventTwo: {
+ writeTo:"optionOne",
+ value: "not a method"
+ },
+ eventThree: {
+ writeTo: "optionOne",
+ value: true
+ },
+ eventFour: {
+ writeTo: "optionTwo",
+ value: true
+ },
+ eventFive: {
+ writeTo: "badOption",
+ value: true
+ },
+ eventSix: {
+ writeTo: "optionSix",
+ value: true
+ }
}
};
widget = {
+ bind: function(eventName, handler) {
+ widget.handlers[eventName] = widget.handlers[eventName] || [];
+ widget.handlers[eventName].push(handler);
+ },
+ handlers: {},
methodOne: function() {
return "methodOne value";
}
};
- ko.kendo.bindingFactory.handleEvents(events, options, function() { return widget; });
+ ko.kendo.bindingFactory.handleEvents(options, widgetConfig, null, widget);
});
describe("when writeTo corresponds to an observable", function() {
describe("when value is a string", function() {
describe("when value corresponds to a method on the widget", function() {
- it("should add a handler for this event to options", function() {
- expect(options.eventOne).toBeDefined();
- expect(typeof options.eventOne).toEqual("function");
- });
-
it("should update the observable by reading the value from the method", function() {
- options.eventOne();
+ console.log("widget", widget);
+ widget.handlers.eventOne[0].call(widget);
expect(options.optionOne()).toEqual("methodOne value");
});
});
describe("when value does not correspond to a method on the widget", function() {
- it("should add a handler for this event to options", function() {
- expect(options.eventTwo).toBeDefined();
- expect(typeof options.eventTwo).toEqual("function");
- });
-
it("should update the observable with literal value", function() {
- options.eventTwo();
+ widget.handlers.eventTwo[0].call(widget);
expect(options.optionOne()).toEqual("not a method");
});
});
});
describe("when value is a boolean", function() {
- it("should add a handler for this event to options", function() {
- expect(options.eventThree).toBeDefined();
- expect(typeof options.eventThree).toEqual("function");
- });
-
it("should update the observable with the boolean value", function() {
- options.eventThree();
+ widget.handlers.eventThree[0].call(widget);
expect(options.optionOne()).toEqual(true);
});
});
describe("when there is an existing handler for the event", function() {
it("should update the observable when the handler is called", function() {
- options.eventSix();
+ widget.handlers.eventSix[0].call(widget);
expect(options.optionSix()).toEqual(true);
});
-
- it("should call the existing handler when the handler is called", function() {
- spyOn(options, "existingSix");
- options.eventSix();
- expect(options.existingSix).toHaveBeenCalled();
- });
- });
- });
-
- describe("when writeTo corresponds to a non-observable", function() {
- it("should not add a handler for this event to options", function() {
- expect(options.eventFour).toBeUndefined();
- });
- });
-
- describe("when writeTo does not correspond to a property in the options", function() {
- it("should not add a handler for this event to options", function() {
- expect(options.eventFive).toBeUndefined();
});
});
});
View
1 src/knockout-kendo-constants.js
@@ -15,6 +15,7 @@ var CLOSE = "close",
MAX = "max",
MIN = "min",
OPEN = "open",
+ RESIZE = "resize",
SEARCH = "search",
SELECT = "select",
SELECTED = "selected",
View
44 src/knockout-kendo-core.js
@@ -12,7 +12,7 @@ ko.kendo.BindingFactory = function() {
var binding = {};
//the binding handler's init function
- binding.init = function(element, valueAccessor, allBindingsAccessor) {
+ binding.init = function(element, valueAccessor) {
//step 1: build appropriate options for the widget from values passed in and global options
var options = self.buildOptions(widgetConfig, valueAccessor);
@@ -31,12 +31,12 @@ ko.kendo.BindingFactory = function() {
binding.setup = function(element, options) {
var widget, $element = $(element);
- //step 2: add handlers for events that we need to react to for updating the model
- self.handleEvents(widgetConfig.events, options, function() { return $element.data(widgetConfig.name); });
-
- //step 3: initialize widget
+ //step 2: initialize widget
widget = self.getWidget(widgetConfig, options, $element);
+ //step 3: add handlers for events that we need to react to for updating the model
+ self.handleEvents(options, widgetConfig, element, widget);
+
//step 4: set up computed observables to update the widget when observable model values change
self.watchValues(widget, options, widgetConfig, element);
@@ -121,36 +121,36 @@ ko.kendo.BindingFactory = function() {
};
//write changes to the widgets back to the model
- this.handleEvents = function(events, options, widgetAccessor) {
- var prop, event;
+ this.handleEvents = function(options, widgetConfig, element, widget) {
+ var prop, event, events = widgetConfig.events;
+
if (events) {
for (prop in events) {
if (events.hasOwnProperty(prop)) {
event = events[prop];
- event = typeof event === "string" ? { value: event, writeTo: event } : event;
+ if (typeof event === "string") {
+ event = { value: event, writeTo: event };
+ }
+
if (ko.isObservable(options[event.writeTo])) {
- self.handleOneEvent(prop, event, options, widgetAccessor);
+ self.handleOneEvent(prop, event, options, element, widget, widgetConfig.childProp);
}
}
}
}
};
- //set on options for now, as using bind does not work for many events
- this.handleOneEvent = function(event, eventOptions, options, widgetAccessor) {
- var existing = options[event];
- options[event] = function() {
- var propOrValue = eventOptions.value,
- widget = widgetAccessor(),
- value = (typeof propOrValue === "string" && widget[propOrValue]) ? widget[propOrValue]() : propOrValue;
-
- options[eventOptions.writeTo](value);
+ //bind to a single event
+ this.handleOneEvent = function(eventName, eventConfig, options, element, widget, childProp) {
+ widget.bind(eventName, function(e) {
+ var propOrValue, value;
- //if they passed in a handler in addition to the handling that we need done
- if (existing) {
- existing.apply(this, arguments);
+ if (!childProp || !e[childProp] || e[childProp] === element) {
+ propOrValue = eventConfig.value;
+ value = (typeof propOrValue === "string" && this[propOrValue]) ? this[propOrValue](childProp && element) : propOrValue;
+ options[eventConfig.writeTo](value);
}
- };
+ });
};
};
View
12 src/knockout-kendoPanelBar.js
@@ -6,10 +6,20 @@ createBinding({
createBinding({
name: "kendoPanelItem",
parent: "kendoPanelBar",
- updateableOptions: [ENABLE],
watch: {
enabled: ENABLE,
expanded: [EXPAND, COLLAPSE]
},
+ childProp: "item",
+ events: {
+ expand: {
+ writeTo: EXPANDED,
+ value: true
+ },
+ collapse: {
+ writeTo: EXPANDED,
+ value: false
+ }
+ },
async: true
});
View
12 src/knockout-kendoSplitter.js
@@ -12,5 +12,17 @@ createBinding({
size: SIZE,
expanded: [EXPAND, COLLAPSE]
},
+ childProp: "pane",
+ events: {
+ collapse: {
+ writeTo: EXPANDED,
+ value: false
+ },
+ expand: {
+ writeTo: EXPANDED,
+ value: true
+ },
+ resize: SIZE
+ },
async: true
});
View
7 src/knockout-kendoTabStrip.js
@@ -12,5 +12,12 @@ createBinding({
},
enabled: ENABLE
},
+ childProp: "item",
+ events: {
+ selected: {
+ writeTo: SELECTED,
+ value: true
+ }
+ },
async: true
});
View
17 src/knockout-kendoTreeView.js
@@ -9,9 +9,24 @@ createBinding({
watch: {
enabled: ENABLE,
expanded: [EXPAND, COLLAPSE],
- select: function(element, value) {
+ selected: function(element, value) {
this.select(value ? element : null);
}
},
+ childProp: "node",
+ events: {
+ collapse: {
+ writeTo: EXPANDED,
+ value: false
+ },
+ expand: {
+ writeTo: EXPANDED,
+ value: true
+ },
+ select: {
+ writeTo: SELECTED,
+ value: true
+ }
+ },
async: true
});

0 comments on commit fa785ee

Please sign in to comment.