Reputation: 1150
I 'm currently trying to implement a custom KnockoutJS binding to make a div contenteditable. As an example, I'll take the ViewModel from the first tutorial at knockoutJS and add a "edit mode"-flag:
JSBin: http://jsbin.com/ejugip/3/edit
ViewModel Code:
function HelloWorldViewModel() {
var self = this;
self.isInEditMode = ko.observable(true);
self.firstName = ko.observable('Bert');
self.lastName = ko.observable('Berntington');
self.fullName = ko.computed(function () {
return self.firstName() + ' ' + self.lastName();
});
}
View Code:
<fieldset id="HelloWorldView">
<legend>Hello World</legend>
<p><input type="checkbox" data-bind="checked: isInEditMode" /> edit mode</p>
<label>First name:</label>
<div data-bind="contenteditable: isInEditMode, text: firstName"></div>
<label>Last name:</label>
<div data-bind="contenteditable: isInEditMode, text: lastName"></div>
<label>Full name:</label>
<div data-bind="text: fullName"></div>
</fieldset>
This is my binding handler code, so far:
function makeEditable(element, editable) {
$(element).attr('contenteditable', (editable) ? true : false);
$(element).removeClass('Editable');
if (editable) {
$(element).addClass('Editable');
}
}
ko.bindingHandlers.contenteditable = {
init: function (element, valueAccessor) {},
update: function (element, valueAccessor) {
var editable = ko.utils.unwrapObservable(valueAccessor());
makeEditable(element, editable);
}
};
For now, I'm just adding the contenteditable attribute to the element and a css class.
So entering and leaving the edit mode works fine. One thing that's still missing is, that the viewModel gets updated after the contenteditable elements are edited.
What's the best way to get the viewmodel in sync with my editable elements? Do I need an own custom "text:" binding, or is there an easier way?
Upvotes: 2
Views: 2860
Reputation: 15984
Some time ago I created a KO based contenteditable binding plus editor that you can maybe get some inspiration from.
https://github.com/madcapnmckay/Knockout-UI/blob/master/js/ui-editor.js
Hope this helps.
Upvotes: 5