#javascript #vue.js #vuejs2
#javascript #vue.js #vuejs2
Вопрос:
Мне нужно знать, какая наилучшая практика для переноса библиотеки JS DOM в Vue. В качестве примера я буду использовать EditorJS.
<template>
<div :id="holder"></div>
</template>
import Editor from '@editorjs/editorjs'
export default {
name: "editorjs-wrapper",
props: {
holder: {
type: String,
default: () => {return "vue-editor-js"},
required: true
}
},
data(){
return {
editor: null
};
},
methods: {
init_editor(){
this.editor = new Editor({
holder: this.holder,
tools: {
}
});
}
},
mounted(){
this.init_editor();
},
//... Destroy on destroy
}
Первый:
Предположим, у меня есть несколько экземпляров <editorjs-wrapper>
в одном представлении без :hook
, тогда все намерения будут иметь одинаковый идентификатор.
<div id="app">
<editorjs-wrapper></editorjs-wrapper>
<editorjs-wrapper></editorjs-wrapper>
</div>
Все становится немного странным, так как они оба пытаются обработать DOM #vue-editor-js
. Было бы лучше, если бы компонент генерировал случайный идентификатор по умолчанию?
Второй:
EditorJS предоставляет save()
метод для извлечения ее содержимого. Что лучше для родительского элемента, чтобы иметь возможность вызывать save()
метод из EditorJS внутри дочернего элемента?
У меня есть два способа:
$emit
и наблюдение (события)
// Parent
<div id="#app">
<editorjs-wrapper @save="save_method" :save="save">
</div>
// Child
...
watch: {
save: {
immediate: true,
handler(new_val, old_val){
if(new_val) this.editor.save().then(save=>this.$emit('save', save)) // By the way I have not tested it it might be that `this` scope is incorrect...
}
}
}
...
То есть родительский элемент запускает сохранение в дочернем элементе, и таким образом дочерний элемент генерирует событие сохранения после вызова метода из EditorJS.
this.$refs.childREF
Этот способ обеспечит тесную связь между родительским и дочерним компонентами.
Третий:
Если я хочу обновить содержимое дочернего элемента как родительского, я не знаю, как это сделать, в других проектах, которые я безуспешно пробовал с v-modal
для двухсторонней привязки:
export default{
name: example,
props:{
content: String
},
watch:{
content: {
handler(new_val, old_val){
this.update_content(new_val);
}
}
},
data(){
return {
some_js_framework: // Initialized at mount
}
},
methods: {
update_content: function(new_val){
this.some_js_framework.update(new_val)
},
update_parent: function(new_val){
this.$emit('input', this.some_js_framework.get_content());
}
},
mounted(){
this.some_js_framework = new Some_js_framework();
this.onchange(this.update_parent);
}
}
Проблема в том:
- Обновлено дочернее содержимое
- Дочернее событие emit
input
- Родительский элемент обновляет двустороннее предложение
v-model
- Поскольку родительский элемент обновил значение, дочерний просмотр обновляется, и, таким образом,
onchange
обработчик запускается, таким образом, 1. снова.