export class MarkdownEditor {
constructor(options) {
this.options = options;
this.vditor = null;
this.init();
}
init() {
const {
elementId,
markdown,
theme,
editOnly,
uploadAddress,
fileUpload,
markdownValueEl
} = this.options;
if (!elementId || typeof Vditor === 'undefined') return;
if (markdownValueEl) {
markdownValueEl.style.display = 'none';
}
this.vditor = new Vditor(elementId, {
value: markdown,
height: '800px',
width: '100%',
theme: theme === 'dark' ? 'dark' : 'classic',
mode: 'ir',
cache: { enable: false },
preview: {
mode: editOnly ? 'editor' : 'both',
theme: {
current: theme === 'dark' ? 'dark' : 'classic',
path: 'https://dpangzi.com/library/vditor/css/content-theme'
},
hljs: {
enable: true,
style: 'vs2015',
lineNumber: true
}
},
counter: { enable: true },
link: { isOpen: false },
tab: ' ',
toolbar: [
'emoji', 'headings', 'bold', 'italic', 'strike', 'link', '|',
'list', 'ordered-list', 'check', 'outdent', 'indent', '|',
'quote', 'line', 'code', 'inline-code', 'insert-before', 'insert-after', '|',
'upload', 'table', '|',
'undo', 'redo', '|',
'edit-mode', 'content-theme', 'code-theme', '|',
'both', 'preview', 'fullscreen'
],
upload: {
accept: 'image/*',
handler: async (files) => {
if (!files || files.length === 0) return;
const file = files[0];
if (!file.type.startsWith('image/')) {
console.error('Only image uploads are supported via this handler.');
return;
}
if (typeof fileUpload === 'function' && uploadAddress && uploadAddress.trim() !== '') {
await fileUpload(file, (url) => {
if (url) {
this.vditor?.insertValue(``);
}
}, uploadAddress);
}
}
},
after: () => {
const element = document.getElementById(elementId);
const toolbar = element?.querySelector('.vditor-toolbar');
if (toolbar) {
const buttons = toolbar.querySelectorAll('button:not([type])');
buttons.forEach((button) => button.setAttribute('type', 'button'));
}
}
});
}
getMarkdown() {
if (!this.vditor) return '';
return this.vditor.getValue();
}
getHtml() {
if (!this.vditor) return '';
return this.vditor.getHTML();
}
} 评论加载中...