|
@@ -192,14 +192,6 @@
|
|
|
@click='toggleMarkup({ start: `<kbd>`, end: `</kbd>` })'
|
|
|
)
|
|
|
q-tooltip(anchor='top middle' self='bottom middle') {{ t('editor.markup.keyboardKey') }}
|
|
|
- q-btn(
|
|
|
- v-if='!state.previewShown'
|
|
|
- icon='mdi-eye-arrow-right-outline'
|
|
|
- padding='xs sm'
|
|
|
- flat
|
|
|
- @click='state.previewShown = true'
|
|
|
- )
|
|
|
- q-tooltip(anchor='top middle' self='bottom middle') {{ t('editor.togglePreviewPane') }}
|
|
|
//--------------------------------------------------------
|
|
|
//- MONACO EDITOR
|
|
|
//--------------------------------------------------------
|
|
@@ -225,7 +217,7 @@
|
|
|
@click='state.previewShown = false'
|
|
|
)
|
|
|
q-tooltip(anchor='top middle' self='bottom middle') {{ t('editor.togglePreviewPane') }}
|
|
|
- .editor-markdown-preview-content.contents(ref='editorPreviewContainer')
|
|
|
+ .editor-markdown-preview-content.page-contents(ref='editorPreviewContainer')
|
|
|
div(
|
|
|
ref='editorPreview'
|
|
|
v-html='pageStore.render'
|
|
@@ -240,7 +232,6 @@ import { get, flatten, last, times, startsWith, debounce } from 'lodash-es'
|
|
|
import { DateTime } from 'luxon'
|
|
|
import * as monaco from 'monaco-editor'
|
|
|
import { Position, Range } from 'monaco-editor'
|
|
|
-import { WorkspaceEdit } from '../helpers/monacoTypes'
|
|
|
|
|
|
import { useEditorStore } from 'src/stores/editor'
|
|
|
import { usePageStore } from 'src/stores/page'
|
|
@@ -298,9 +289,9 @@ function insertAssetClb (opts) {
|
|
|
break
|
|
|
}
|
|
|
}
|
|
|
- insertAtCursor({ content })
|
|
|
+ insertAtCursor({ content, focus: false })
|
|
|
setTimeout(() => {
|
|
|
- cm.value.focus()
|
|
|
+ editor.focus()
|
|
|
}, 500)
|
|
|
}
|
|
|
|
|
@@ -313,15 +304,22 @@ function insertTable () {
|
|
|
/**
|
|
|
* Set current line as header
|
|
|
*/
|
|
|
-function setHeaderLine (lvl) {
|
|
|
- const curLine = cm.value.doc.getCursor('head').line
|
|
|
- let lineContent = cm.value.doc.getLine(curLine)
|
|
|
+function setHeaderLine (lvl, focus = true) {
|
|
|
+ const curLine = editor.getPosition().lineNumber
|
|
|
+ let lineContent = editor.getModel().getLineContent(curLine)
|
|
|
const lineLength = lineContent.length
|
|
|
if (startsWith(lineContent, '#')) {
|
|
|
lineContent = lineContent.replace(/^(#+ )/, '')
|
|
|
}
|
|
|
lineContent = times(lvl, n => '#').join('') + ' ' + lineContent
|
|
|
- cm.value.doc.replaceRange(lineContent, { line: curLine, ch: 0 }, { line: curLine, ch: lineLength })
|
|
|
+ editor.executeEdits('', [{
|
|
|
+ range: new Range(curLine, 1, curLine, lineLength + 1),
|
|
|
+ text: lineContent,
|
|
|
+ forceMoveMarkers: true
|
|
|
+ }])
|
|
|
+ if (focus) {
|
|
|
+ editor.focus()
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
/**
|
|
@@ -341,45 +339,68 @@ function getHeaderLevel (cm) {
|
|
|
/**
|
|
|
* Insert content at cursor
|
|
|
*/
|
|
|
-function insertAtCursor ({ content }) {
|
|
|
- const cursor = cm.value.doc.getCursor('head')
|
|
|
- cm.value.doc.replaceRange(content, cursor)
|
|
|
+function insertAtCursor ({ content, focus = true }) {
|
|
|
+ const cursor = editor.getPosition()
|
|
|
+ editor.executeEdits('', [{
|
|
|
+ range: new Range(cursor.lineNumber, cursor.column, cursor.lineNumber, cursor.column),
|
|
|
+ text: content,
|
|
|
+ forceMoveMarkers: true
|
|
|
+ }])
|
|
|
+ if (focus) {
|
|
|
+ editor.focus()
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* Insert content after current line
|
|
|
*/
|
|
|
-function insertAfter ({ content, newLine }) {
|
|
|
- const curLine = cm.value.doc.getCursor('to').line
|
|
|
- const lineLength = cm.value.doc.getLine(curLine).length
|
|
|
- cm.value.doc.replaceRange(newLine ? `\n${content}\n` : content, { line: curLine, ch: lineLength + 1 })
|
|
|
+function insertAfter ({ content, newLine, focus = true }) {
|
|
|
+ const curLine = editor.getPosition().lineNumber
|
|
|
+ editor.executeEdits('', [{
|
|
|
+ range: new Range(curLine + 1, 1, curLine + 1, 1),
|
|
|
+ text: newLine ? `\n${content}\n` : content,
|
|
|
+ forceMoveMarkers: true
|
|
|
+ }])
|
|
|
+ if (focus) {
|
|
|
+ editor.focus()
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* Insert content before current line
|
|
|
*/
|
|
|
-function insertBeforeEachLine ({ content, after }) {
|
|
|
- let lines = []
|
|
|
- if (!cm.value.doc.somethingSelected()) {
|
|
|
- lines.push(cm.value.doc.getCursor('head').line)
|
|
|
- } else {
|
|
|
- lines = flatten(cm.value.doc.listSelections().map(sl => {
|
|
|
- const range = Math.abs(sl.anchor.line - sl.head.line) + 1
|
|
|
- const lowestLine = (sl.anchor.line > sl.head.line) ? sl.head.line : sl.anchor.line
|
|
|
- return times(range, l => l + lowestLine)
|
|
|
- }))
|
|
|
- }
|
|
|
- lines.forEach(ln => {
|
|
|
- let lineContent = cm.value.doc.getLine(ln)
|
|
|
- const lineLength = lineContent.length
|
|
|
- if (startsWith(lineContent, content)) {
|
|
|
- lineContent = lineContent.substring(content.length)
|
|
|
+function insertBeforeEachLine ({ content, after, focus = true }) {
|
|
|
+ const edits = []
|
|
|
+ for (const selection of editor.getSelections()) {
|
|
|
+ const lineCount = selection.endLineNumber - selection.startLineNumber + 1
|
|
|
+ const lines = times(lineCount, l => l + selection.startLineNumber)
|
|
|
+ for (const line of lines) {
|
|
|
+ let lineContent = editor.getModel().getLineContent(line)
|
|
|
+ const lineLength = lineContent.length
|
|
|
+ if (startsWith(lineContent, content)) {
|
|
|
+ lineContent = lineContent.substring(content.length)
|
|
|
+ }
|
|
|
+ edits.push({
|
|
|
+ range: new Range(line, 1, line, lineLength + 1),
|
|
|
+ text: `${content}${lineContent}`,
|
|
|
+ forceMoveMarkers: true
|
|
|
+ })
|
|
|
}
|
|
|
- cm.value.doc.replaceRange(content + lineContent, { line: ln, ch: 0 }, { line: ln, ch: lineLength })
|
|
|
- })
|
|
|
- if (after) {
|
|
|
- const lastLine = last(lines)
|
|
|
- cm.value.doc.replaceRange(`\n${after}\n`, { line: lastLine, ch: cm.value.doc.getLine(lastLine).length + 1 })
|
|
|
+ if (after) {
|
|
|
+ const lastLine = last(lines)
|
|
|
+ const lineLength = editor.getModel().getLineContent(lastLine).length
|
|
|
+ edits.push({
|
|
|
+ range: new Range(lastLine, lineLength + 1, lastLine, lineLength + 1),
|
|
|
+ text: `\n${after}`,
|
|
|
+ forceMoveMarkers: true
|
|
|
+ })
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ editor.executeEdits('', edits)
|
|
|
+
|
|
|
+ if (focus) {
|
|
|
+ editor.focus()
|
|
|
}
|
|
|
}
|
|
|
|
|
@@ -387,7 +408,7 @@ function insertBeforeEachLine ({ content, after }) {
|
|
|
* Insert an Horizontal Bar
|
|
|
*/
|
|
|
function insertHorizontalBar () {
|
|
|
- insertAfter({ content: '---', newLine: true })
|
|
|
+ insertAfter({ content: '\n---\n', newLine: true })
|
|
|
}
|
|
|
|
|
|
/**
|
|
@@ -442,7 +463,7 @@ onMounted(async () => {
|
|
|
'editor.background': '#070a0d',
|
|
|
'editor.lineHighlightBackground': '#0d1117',
|
|
|
'editorLineNumber.foreground': '#546e7a',
|
|
|
- 'editorGutter.background': '#1e232a'
|
|
|
+ 'editorGutter.background': '#0d1117'
|
|
|
}
|
|
|
})
|
|
|
|
|
@@ -455,7 +476,13 @@ onMounted(async () => {
|
|
|
scrollBeyondLastLine: false,
|
|
|
fontSize: 16,
|
|
|
formatOnType: true,
|
|
|
- lineNumbersMinChars: 3
|
|
|
+ lineNumbersMinChars: 3,
|
|
|
+ tabSize: 2,
|
|
|
+ padding: {
|
|
|
+ top: 10,
|
|
|
+ bottom: 10
|
|
|
+ },
|
|
|
+ wordWrap: 'on'
|
|
|
})
|
|
|
|
|
|
window.edd = editor
|
|
@@ -467,7 +494,7 @@ onMounted(async () => {
|
|
|
id: 'markdown.extension.editing.toggleBold',
|
|
|
keybindings: [monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyB],
|
|
|
label: 'Toggle bold',
|
|
|
- precondition: '',
|
|
|
+ precondition: 'editorHasSelection',
|
|
|
run (ed) {
|
|
|
toggleMarkup({ start: '**' })
|
|
|
}
|
|
@@ -479,12 +506,21 @@ onMounted(async () => {
|
|
|
id: 'markdown.extension.editing.toggleItalic',
|
|
|
keybindings: [monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyI],
|
|
|
label: 'Toggle italic',
|
|
|
- precondition: '',
|
|
|
+ precondition: 'editorHasSelection',
|
|
|
run (ed) {
|
|
|
toggleMarkup({ start: '*' })
|
|
|
}
|
|
|
})
|
|
|
|
|
|
+ editor.addAction({
|
|
|
+ id: 'save',
|
|
|
+ keybindings: [monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyS],
|
|
|
+ label: 'Save',
|
|
|
+ precondition: '',
|
|
|
+ run (ed) {
|
|
|
+ }
|
|
|
+ })
|
|
|
+
|
|
|
editor.onDidChangeModelContent(debounce(ev => {
|
|
|
editorStore.$patch({
|
|
|
lastChangeTimestamp: DateTime.utc()
|
|
@@ -495,61 +531,10 @@ onMounted(async () => {
|
|
|
processContent(pageStore.content)
|
|
|
}, 500))
|
|
|
|
|
|
- // -> Initialize CodeMirror
|
|
|
- // cm.value = CodeMirror.fromTextArea(cmRef.value, {
|
|
|
- // tabSize: 2,
|
|
|
- // mode: 'text/markdown',
|
|
|
- // theme: 'wikijs-dark',
|
|
|
- // lineNumbers: true,
|
|
|
- // lineWrapping: true,
|
|
|
- // line: true,
|
|
|
- // styleActiveLine: true,
|
|
|
- // highlightSelectionMatches: {
|
|
|
- // annotateScrollbar: true
|
|
|
- // },
|
|
|
- // viewportMargin: 50,
|
|
|
- // inputStyle: 'contenteditable',
|
|
|
- // allowDropFileTypes: ['image/jpg', 'image/png', 'image/svg', 'image/jpeg', 'image/gif'],
|
|
|
- // // direction: siteConfig.rtl ? 'rtl' : 'ltr',
|
|
|
- // foldGutter: true,
|
|
|
- // gutters: ['CodeMirror-linenumbers', 'CodeMirror-foldgutter']
|
|
|
- // })
|
|
|
-
|
|
|
- // cm.value.setValue(pageStore.content)
|
|
|
- // cm.value.on('change', c => {
|
|
|
- // editorStore.$patch({
|
|
|
- // lastChangeTimestamp: DateTime.utc()
|
|
|
- // })
|
|
|
- // pageStore.$patch({
|
|
|
- // content: c.getValue()
|
|
|
- // })
|
|
|
- // onCmInput(pageStore.content)
|
|
|
- // })
|
|
|
-
|
|
|
- // cm.value.setSize(null, '100%')
|
|
|
+ editor.focus()
|
|
|
|
|
|
// -> Set Keybindings
|
|
|
// const keyBindings = {
|
|
|
- // 'F11' (c) {
|
|
|
- // c.setOption('fullScreen', !c.getOption('fullScreen'))
|
|
|
- // },
|
|
|
- // 'Esc' (c) {
|
|
|
- // if (c.getOption('fullScreen')) {
|
|
|
- // c.setOption('fullScreen', false)
|
|
|
- // }
|
|
|
- // },
|
|
|
- // [`${CtrlKey}-S`] (c) {
|
|
|
- // // save()
|
|
|
- // return false
|
|
|
- // },
|
|
|
- // [`${CtrlKey}-B`] (c) {
|
|
|
- // toggleMarkup({ start: '**' })
|
|
|
- // return false
|
|
|
- // },
|
|
|
- // [`${CtrlKey}-I`] (c) {
|
|
|
- // toggleMarkup({ start: '*' })
|
|
|
- // return false
|
|
|
- // },
|
|
|
// [`${CtrlKey}-Alt-Right`] (c) {
|
|
|
// let lvl = getHeaderLevel(c)
|
|
|
// if (lvl >= 6) { lvl = 5 }
|
|
@@ -563,7 +548,6 @@ onMounted(async () => {
|
|
|
// return false
|
|
|
// }
|
|
|
// }
|
|
|
- // cm.value.setOption('extraKeys', keyBindings)
|
|
|
// this.cm.on('inputRead', this.autocomplete)
|
|
|
|
|
|
// // Handle cursor movement
|
|
@@ -575,13 +559,6 @@ onMounted(async () => {
|
|
|
// // Handle special paste
|
|
|
// this.cm.on('paste', this.onCmPaste)
|
|
|
|
|
|
- // // Render initial preview
|
|
|
- // processContent(pageStore.content)
|
|
|
- // nextTick(() => {
|
|
|
- // cm.value.refresh()
|
|
|
- // cm.value.focus()
|
|
|
- // })
|
|
|
-
|
|
|
EVENT_BUS.on('insertAsset', insertAssetClb)
|
|
|
|
|
|
// this.$root.$on('editorInsert', opts => {
|
|
@@ -619,9 +596,9 @@ onMounted(async () => {
|
|
|
|
|
|
onBeforeUnmount(() => {
|
|
|
EVENT_BUS.off('insertAsset', insertAssetClb)
|
|
|
- // if (editor.value) {
|
|
|
- // editor.value.destroy()
|
|
|
- // }
|
|
|
+ if (editor) {
|
|
|
+ editor.dispose()
|
|
|
+ }
|
|
|
})
|
|
|
</script>
|
|
|
|
|
@@ -662,7 +639,7 @@ $editor-height-mobile: calc(100vh - 112px - 16px);
|
|
|
font-weight: 500;
|
|
|
}
|
|
|
&-preview {
|
|
|
- flex: 1 1 50%;
|
|
|
+ flex: 0 1 50%;
|
|
|
position: relative;
|
|
|
height: $editor-height;
|
|
|
overflow: hidden;
|
|
@@ -706,7 +683,7 @@ $editor-height-mobile: calc(100vh - 112px - 16px);
|
|
|
height: $editor-height;
|
|
|
overflow-y: scroll;
|
|
|
padding: 1rem;
|
|
|
- width: calc(100% + 17px);
|
|
|
+ max-width: calc(50vw - 57px);
|
|
|
// -ms-overflow-style: none;
|
|
|
// &::-webkit-scrollbar {
|
|
|
// width: 0px;
|