Quill编辑器+VueJS2图像上传:Base64图像转换为URL

6

使用这里的编辑器:https://github.com/surmon-china/vue-quill-editor

我想将Quill编辑器中的图片保存到MySQL数据库,但是在base64中较大的图片太长而无法插入。

我尝试编写自定义图像处理程序,使其自动将图像上传到服务器并返回图像URL,但现在我被卡住了。

这是我的当前HTML:

<quill-editor v-model="content"
    :options="editorOption"
    @onEditorBlur($event)"
    @onEditorFocus($event)"
    @onEditorReady($event)"
    @onEditorChange($event)">
</quill-editor>

像这样将图像处理程序添加到编辑器中:

onEditorReady(editor) {
    editor.getModule('toolbar').addHandler('image', this.imageHandler);
    console.log('editor ready!', editor);
},

还有我自己的处理程序:

imageHandler(image, callback){
    console.log(image); // Always true
    console.log(callback); // Always undefined

    // Should get image in here somehow..
    var sendData = {
        image: 'SomethingShouldBeInHere',
    };

    // Send image to server, 
    //  Server will return link to image
    axios.put('/testImageUpload', sendData)
    .then(function(cbData) {
        // In here should add image tag to editor somehow..

    })
    .catch(function (error) {
        console.log(error);
    });
},

我尝试了这个:添加支持自定义图像处理程序,但它不起作用,因为图像始终为true且回调未定义。

也尝试了这个:Quill imageHandler演示,但遇到了与第一个链接相同的问题。

目前服务器是硬编码返回 "http://localhost/images/php.jpg"。

如果可能,我将不使用任何库(jQuery、dropzone等)。

我想,也许可以在onEditorChange()中检查是否插入了图像,然后发送请求到服务器,获取URL,在编辑器中搜索此base64并将其替换为URL,但这似乎不正确。

3个回答

9

在您的选项中设置处理程序,如下所示

editorOption: {
  modules: {
   toolbar: {
    container: [['image'], ...],
    handlers: {
     'image': function(){
      document.getElementById('getFile').click()
     }
    }
   } 
  }
}


methods: {
  uploadFunction(e){
  
    //you can get images data in e.target.files
    //an single example for using formData to post to server
    
    
    var form = new FormData()
    form.append('file[]', e.target.files[0])
    
    //do your post
    
    
  }
}
<template>
  <quill-editor v-model="content"
            :options="editorOption"
            @change="oneEditorChange($event)">
  </quill-editor>
  <input type="file" id="getFile" @change="uploadFunction($event)" />
</template>


1
你能提供更多的上下文吗?这些处理程序应该在哪里设置呢? - Ben
1
搞定了,谢谢!从没想过加另一个输入并使用它 =) - Margus Kevin
请问您能否指导我如何从这个编辑器中移除图像和视频上传功能?我正在我的项目中实现它,我只需要基本的文本编辑功能。谢谢。 - Benjiro
@Benjiro 你可以设置一个自定义工具栏,只包含你想要的功能,并覆盖默认设置。https://quilljs.com/docs/modules/toolbar/ - Alruna L

3
这是我的源代码...
//Template
<input type="file" @change="uploadFunction" id="file" hidden>

<quill-editor 
      v-model="model" 
      :options="editorOption" 
      ref="quillEdit">
</quill-editor>

和脚本

 //script
    import "quill/dist/quill.core.css";
    import "quill/dist/quill.snow.css";
    import "quill/dist/quill.bubble.css";
    import Quill from "quill";
    import { quillEditor } from "vue-quill-editor";
    import ImageResize from "quill-image-resize-module";
    import axios from '~/plugins/axios'

    export default {
      data() {
        model: '',
        selectedFile : '',
        editorOption: {
            // some quill options
            modules: {
              toolbar: {
                container: [["bold", "image"]],
                handlers: {
                  image: function() {
                    document.getElementById('file').click()
                  }
                }
              },
              imageResize: {
                modules: ["Resize", "DisplaySize", "Toolbar"]
              }
            }
          },
       },
       methods: {
        uploadFunction(e){
             this.selectedFile = e.target.files[0];

          var form = new FormData();
          form.append("file", this.selectedFile);
          form.append("name", this.selectedFile.name);

            //upload image to server
            axios.post('media-save', form,{
             'headers': {
                 'Content-Type': "multipart/form-data"
              }
             })
            .then(r => {
              console.log('success')

              //this code to set your position cursor
const range = this.$refs.quillEdit.quill.getSelection()
//this code to set image on your server to quill editor
              this.$refs.quillEdit.quill.insertEmbed(range.index , 'image', `http://your.api/${r}`)
            })
            .catch(e => {
              console.log('error')
         }
       }
    }

insertEmbed(range, ... range is an object. So should be range.index - Shirker
@Shirker 谢谢你的纠正,但现在我意识到如果数据是一个对象,那么图像将被放置在最后一段,所以我以前从来没有受到干扰... :D - M ilham
我也听说在调用 getSelection() 之前先调用 ..quill.focus() 更安全。在我的情况下,this.$refs.quillEdit.quill 将会是 this.$refs.quillEdit[0].quill,因为 $refs 返回一个数组。 - Shirker

0
import React, { useState, useEffect } from 'react';

// ** Reactstrap Imports
import {
    Row,
    Form,
    Modal,
    ModalHeader,
    ModalBody,
    Col
} from 'reactstrap'

import { useTranslation } from 'react-i18next'

import { useQuill } from 'react-quilljs';

import 'quill/dist/quill.snow.css'

export default function ReadingModal({ open, handleModal, datas })
{

    const { t } = useTranslation()

    const [ News, setNews ] = useState(datas || '')

    return (
        <Modal isOpen={open} toggle={handleModal} className="modal-dialog-centered modal-lg" onClosed={handleModal}>
            <ModalHeader className='bg-transparent pb-0' toggle={handleModal} ></ModalHeader>
            <ModalBody className="px-sm-3 pt-30 pb-3">
                <div className='text-center'>
                    <h4>{News && News['title']}</h4>
                </div>
                <Row tag={Form} className="gy-1">
                        <Col>
                            {News && News['body']}
                        </Col>
                </Row>
            </ModalBody>
        </Modal>
    );
};

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接