Vue - Bind to innerHTML
by Ben Clayton
HTML
<div id="app" onchange="alert('change')">
<hr>
<div v-demo:foo.a.b="message"></div>
<hr>
<div v-myhtml="message"></div>
<hr>
<div v-twoway="message" contenteditable></div>
</div>
https://stackoverflow.com/questions/47200760/vuejs-directive-two-way-binding<br>
Try this in developer tools console ('result' window)<br>
vm.$data.message = "<h1>Hello Bert</h1>"
CSS
#app {
padding: 20px;
}
h1 {
color: red;
font-size: 24px;
}
Vue
Vue.directive('demo', {
bind: function (el, binding, vnode) {
var s = JSON.stringify
el.innerHTML =
'name: ' + s(binding.name) + '<br>' +
'value: ' + s(binding.value) + '<br>' +
'expression: ' + s(binding.expression) + '<br>' +
'argument: ' + s(binding.arg) + '<br>' +
'modifiers: ' + s(binding.modifiers) + '<br>' +
'vnode keys: ' + Object.keys(vnode).join(', ')
}
})
Vue.directive('myhtml', {
bind: function (el, binding, vnode) {
el.innerHTML =binding.value
},
update: function (el, binding, vnode) {
el.innerHTML =binding.value
}
})
Vue.directive('twoway', {
bind: function (el, binding, vnode) {
var select = $(el);
console.log( select.html() , binding.value );
select
.html(binding.value)
.trigger('change')
.on('keyup', function () {
var ex = binding.expression;
// if binding expression is a dotted path then resolve parts seperately
var bits = ex.split('.');
var path = vnode.context;
var i=0;
while (i < bits.length -1) {
path = path[bits[i++]];
}
if ( typeof path[bits[i]] != 'undefined' ) {
path[bits[i]] = select.html();
}
vnode.context.$emit('change');
console.log( 'change' );
})
},
update: function (el, binding, vnode) {
if ( el.innerHTML != binding.value ){
// this damages the cursor position, a bit of a pain !!!!
el.innerHTML =binding.value
}
}
});
window['vm'] = new Vue({
el: '#app',
data: {
message: '<h1>Hello World</h1>'
}
})
console.log("VM inited",vm);