TLDR; Я хочу вставить скомпилированный компонент Vue JS в редактируемое тело CKEditor, как часть процесса запуска плагина.
У меня есть собственный плагин с изображением CKEditor для сайта в стиле CMS. Пользователь вставляет изображение, выбирая свое изображение из средства выбора изображений (вне CKEditor), и затем выполняется команда CKEditor для вставки изображения:
const model = this.editor.model;
model.change(writer => {
const imageElement = writer.createElement('custom-image');
const insertAtSelection = findOptimalInsertionPosition(model.document.selection, model);
model.insertContent(imageElement, insertAtSelection);
});
Существует плагин, который регистрирует элемент 'custom-image' в схеме, внутри метода плагина init
:
const schema = this.editor.model.schema;
schema.register('custom-image', {
isObject: true,
isBlock: true,
allowIn: '$root'
});
Затем зарегистрирован обработчик downcast (также внутри метода init
плагина):
const conversion = this.editor.conversion;
// A similar handler is used for editingDowncast
conversion.for('dataDowncast').elementToElement({
model: 'custom-image',
view: (modelElement, viewWriter) => {
return writer.createContainerElement('div', {
class: 'custom-image',
});
}
});
Теперь у меня есть компонент Vue со ссылкой на узел DOM, который я хотел бы вставить во вновь созданный div.custom-image
(ContainerElement
).
Я попытался создать обработчик на downcastDispatcher, например:
this.editor.editing.downcastDispatcher.on("insert:custom-image", (evt, data, conversionApi) => {
const el = ... // Vue component is created here
const viewElement = conversionApi.mapper.toViewElement(data.item);
const domNode = view.domConverter.mapViewToDom(viewElement);
domNode.appendChild(el);
});
Проблема в том, что 1) viewElement
, похоже, еще не добавлен в DOM (поэтому mapViewToDom
возвращает неопределенное значение), и 2) если я жду добавления viewElement
в DOM (используя setTimeout (неприятный хак), содержимое компонента Vue в основном удалено, потому что схема не допускает их.
Компонент Vue, который добавляется, довольно сложный и взаимодействует с приложением вне CKEditor. Воссоздание компонента с использованием модели CKEditor было бы довольно грязным. Он также используется в представлении приложения, поэтому было бы неплохо иметь возможность повторно использовать один и тот же компонент в качестве части редактирования и просмотра приложения.
Итак, как лучше всего решить эту проблему?