Browse Source

feat(component): paste image upload in editor content

main
Mohan 1 month ago
parent
commit
a2e4d0d245
  1. 48
      src/views/admin/ArticleEditorView.vue

48
src/views/admin/ArticleEditorView.vue

@ -19,6 +19,45 @@ const loading = ref(false)
const saving = ref(false) const saving = ref(false)
const error = ref<string | null>(null) const error = ref<string | null>(null)
const uploading = ref(false) const uploading = ref(false)
const pasting = ref(false)
async function uploadFile(file: File): Promise<string | null> {
try {
const resp = await mediaApi.apiMediaUploadPost(file, 'images')
const stored = resp.data.data
return stored?.url ?? null
} catch (e) {
console.error(e)
error.value = '图片上传失败'
return null
}
}
async function onPaste(event: ClipboardEvent) {
const items = event.clipboardData?.items
if (!items) return
const files: File[] = []
for (const item of items) {
if (item.type.startsWith('image/')) {
const file = item.getAsFile()
if (file) files.push(file)
}
}
if (files.length === 0) return
event.preventDefault()
pasting.value = true
error.value = null
try {
for (const file of files) {
const url = await uploadFile(file)
if (url) {
content.value += `\n![${file.name}](${url})\n`
}
}
} finally {
pasting.value = false
}
}
async function loadTags() { async function loadTags() {
try { try {
@ -144,7 +183,14 @@ onMounted(() => {
<textarea id="summary" v-model="summary" class="form-textarea" rows="3" maxlength="500"></textarea> <textarea id="summary" v-model="summary" class="form-textarea" rows="3" maxlength="500"></textarea>
<label class="field-label" for="content">内容</label> <label class="field-label" for="content">内容</label>
<textarea id="content" v-model="content" class="form-textarea" rows="16"></textarea>
<textarea
id="content"
v-model="content"
class="form-textarea"
rows="16"
:placeholder="pasting ? '图片上传中...' : '支持粘贴图片自动上传为 Markdown 图片语法'"
@paste="onPaste"
></textarea>
<label class="field-label" for="cover">封面图 URL</label> <label class="field-label" for="cover">封面图 URL</label>
<div class="cover-row"> <div class="cover-row">

Loading…
Cancel
Save