2020-05-24 23:13:21 +05:30
|
|
|
<script>
|
|
|
|
import 'codemirror/lib/codemirror.css';
|
|
|
|
import '@toast-ui/editor/dist/toastui-editor.css';
|
|
|
|
|
2020-07-28 23:09:34 +05:30
|
|
|
import AddImageModal from './modals/add_image/add_image_modal.vue';
|
2020-06-23 00:09:42 +05:30
|
|
|
import {
|
|
|
|
EDITOR_OPTIONS,
|
|
|
|
EDITOR_TYPES,
|
|
|
|
EDITOR_HEIGHT,
|
|
|
|
EDITOR_PREVIEW_STYLE,
|
|
|
|
CUSTOM_EVENTS,
|
|
|
|
} from './constants';
|
|
|
|
|
|
|
|
import {
|
2020-07-28 23:09:34 +05:30
|
|
|
registerHTMLToMarkdownRenderer,
|
2020-06-23 00:09:42 +05:30
|
|
|
addCustomEventListener,
|
|
|
|
removeCustomEventListener,
|
|
|
|
addImage,
|
|
|
|
getMarkdown,
|
2020-07-28 23:09:34 +05:30
|
|
|
} from './services/editor_service';
|
2020-05-24 23:13:21 +05:30
|
|
|
|
|
|
|
export default {
|
|
|
|
components: {
|
|
|
|
ToastEditor: () =>
|
|
|
|
import(/* webpackChunkName: 'toast_editor' */ '@toast-ui/vue-editor').then(
|
|
|
|
toast => toast.Editor,
|
|
|
|
),
|
2020-06-23 00:09:42 +05:30
|
|
|
AddImageModal,
|
2020-05-24 23:13:21 +05:30
|
|
|
},
|
|
|
|
props: {
|
2020-07-28 23:09:34 +05:30
|
|
|
content: {
|
2020-05-24 23:13:21 +05:30
|
|
|
type: String,
|
|
|
|
required: true,
|
|
|
|
},
|
|
|
|
options: {
|
|
|
|
type: Object,
|
|
|
|
required: false,
|
|
|
|
default: () => EDITOR_OPTIONS,
|
|
|
|
},
|
|
|
|
initialEditType: {
|
|
|
|
type: String,
|
|
|
|
required: false,
|
|
|
|
default: EDITOR_TYPES.wysiwyg,
|
|
|
|
},
|
|
|
|
height: {
|
|
|
|
type: String,
|
|
|
|
required: false,
|
|
|
|
default: EDITOR_HEIGHT,
|
|
|
|
},
|
|
|
|
previewStyle: {
|
|
|
|
type: String,
|
|
|
|
required: false,
|
|
|
|
default: EDITOR_PREVIEW_STYLE,
|
|
|
|
},
|
2020-07-28 23:09:34 +05:30
|
|
|
imageRoot: {
|
|
|
|
type: String,
|
|
|
|
required: true,
|
|
|
|
validator: prop => prop.endsWith('/'),
|
|
|
|
},
|
2020-05-24 23:13:21 +05:30
|
|
|
},
|
2020-06-23 00:09:42 +05:30
|
|
|
data() {
|
|
|
|
return {
|
|
|
|
editorApi: null,
|
|
|
|
previousMode: null,
|
|
|
|
};
|
|
|
|
},
|
2020-05-24 23:13:21 +05:30
|
|
|
computed: {
|
|
|
|
editorOptions() {
|
|
|
|
return { ...EDITOR_OPTIONS, ...this.options };
|
|
|
|
},
|
2020-06-23 00:09:42 +05:30
|
|
|
editorInstance() {
|
|
|
|
return this.$refs.editor;
|
|
|
|
},
|
|
|
|
},
|
|
|
|
beforeDestroy() {
|
2020-07-28 23:09:34 +05:30
|
|
|
this.removeListeners();
|
2020-05-24 23:13:21 +05:30
|
|
|
},
|
|
|
|
methods: {
|
2020-07-28 23:09:34 +05:30
|
|
|
addListeners(editorApi) {
|
|
|
|
addCustomEventListener(editorApi, CUSTOM_EVENTS.openAddImageModal, this.onOpenAddImageModal);
|
|
|
|
|
|
|
|
editorApi.eventManager.listen('changeMode', this.onChangeMode);
|
|
|
|
},
|
|
|
|
removeListeners() {
|
|
|
|
removeCustomEventListener(
|
|
|
|
this.editorApi,
|
|
|
|
CUSTOM_EVENTS.openAddImageModal,
|
|
|
|
this.onOpenAddImageModal,
|
|
|
|
);
|
|
|
|
|
|
|
|
this.editorApi.eventManager.removeEventHandler('changeMode', this.onChangeMode);
|
|
|
|
},
|
|
|
|
resetInitialValue(newVal) {
|
|
|
|
this.editorInstance.invoke('setMarkdown', newVal);
|
|
|
|
},
|
2020-05-24 23:13:21 +05:30
|
|
|
onContentChanged() {
|
2020-06-23 00:09:42 +05:30
|
|
|
this.$emit('input', getMarkdown(this.editorInstance));
|
|
|
|
},
|
|
|
|
onLoad(editorApi) {
|
|
|
|
this.editorApi = editorApi;
|
|
|
|
|
2020-07-28 23:09:34 +05:30
|
|
|
registerHTMLToMarkdownRenderer(editorApi);
|
2020-06-23 00:09:42 +05:30
|
|
|
|
2020-07-28 23:09:34 +05:30
|
|
|
this.addListeners(editorApi);
|
2020-06-23 00:09:42 +05:30
|
|
|
},
|
|
|
|
onOpenAddImageModal() {
|
|
|
|
this.$refs.addImageModal.show();
|
|
|
|
},
|
2020-07-28 23:09:34 +05:30
|
|
|
onAddImage({ imageUrl, altText, file }) {
|
|
|
|
const image = { imageUrl, altText };
|
|
|
|
|
|
|
|
if (file) {
|
|
|
|
this.$emit('uploadImage', { file, imageUrl });
|
|
|
|
// TODO - ensure that the actual repo URL for the image is used in Markdown mode
|
|
|
|
}
|
|
|
|
|
2020-06-23 00:09:42 +05:30
|
|
|
addImage(this.editorInstance, image);
|
2020-05-24 23:13:21 +05:30
|
|
|
},
|
2020-06-23 00:09:42 +05:30
|
|
|
onChangeMode(newMode) {
|
|
|
|
this.$emit('modeChange', newMode);
|
2020-05-24 23:13:21 +05:30
|
|
|
},
|
|
|
|
},
|
|
|
|
};
|
|
|
|
</script>
|
|
|
|
<template>
|
2020-06-23 00:09:42 +05:30
|
|
|
<div>
|
|
|
|
<toast-editor
|
|
|
|
ref="editor"
|
2020-07-28 23:09:34 +05:30
|
|
|
:initial-value="content"
|
2020-06-23 00:09:42 +05:30
|
|
|
:options="editorOptions"
|
|
|
|
:preview-style="previewStyle"
|
|
|
|
:initial-edit-type="initialEditType"
|
|
|
|
:height="height"
|
|
|
|
@change="onContentChanged"
|
|
|
|
@load="onLoad"
|
|
|
|
/>
|
2020-07-28 23:09:34 +05:30
|
|
|
<add-image-modal ref="addImageModal" :image-root="imageRoot" @addImage="onAddImage" />
|
2020-06-23 00:09:42 +05:30
|
|
|
</div>
|
2020-05-24 23:13:21 +05:30
|
|
|
</template>
|