springboot uses the quill rich text editor plugin to upload custom pictures

1. Problem description:

  1. Quill's own picture upload is base64. If it is directly stored in the database, there may be a risk of overflow when there are many pictures. So use ajax to send formData custom image upload

2. Principle flow

Upload a picture by customizing an input, send an ajax request during nochagne, return to the front end after writing in the background, insert the display

3. Specific code

Pay attention to the version of quill, some people just have the wrong version and the effect does not work. You can go to the official website of quill to find the latest cdn link https://quilljs.com/

Front-end code:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
    <title>Quill</title>
    <link href="https://cdn.bootcss.com/quill/2.0.0-dev.3/quill.snow.css" rel="stylesheet">
    <link href="https://cdn.bootcss.com/quill/2.0.0-dev.3/quill.bubble.css" rel="stylesheet">
    <style>
        body {
            padding: 10px 30px;
        }
        #editor {
            min-height: 180px;
        }
    </style>
</head>
<body>
<div>jjsjsj</div>
<!--存放富文本div-->
<div id="editor" class="showContent">
    <!--回显的内容-->
    <!--可以直接在指定元素内加入文本或者html标签-->
</div>
<!-- 单图片上传:this.files[0] 图片列表的第0项,也就是当前选择的图片 -->
<input type="file" onchange="updateImg(this.files[0])" id="imgData" style="display: none;">
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.js"></script>
<script src="//cdn.quilljs.com/1.3.6/quill.js"></script>
<script src="https://cdn.bootcss.com/quill/2.0.0-dev.3/quill.js"></script>
<script>
    var quill;
    $(function() {
        /* 编辑器操作条选项 */
        var toolbarOptions = [
            ['bold', 'italic', 'underline', 'strike'], //加粗、倾斜、下划线、删除线
            [{'align': []}], //内容对齐方式:左对齐、右对齐、居中、平行
            [{'color': []}, {'background': []}], //字体颜色、文本的背景色
            ['image'],  //图片上传
            ['clean'], //清除格式
            [{'header': 1}, {'header': 2}], //标题H1 H2
            [{'list': 'ordered'}, {'list': 'bullet'}],  //数据列表
            [{'script': 'sub'}, {'script': 'super'}],   // 上标、下标
            [{'indent': '-1'}, {'indent': '+1'}],   // 缩进、减少缩进
            [{'size': ['small', false, 'large', 'huge']}], // 自定义下拉:字体的样式....跟加粗差不多
            [{'header': [1, 2, 3, 4, 5, 6, false]}],  //标题 H1 H2 H3......
            [{'direction': 'rtl'}], // 文本方向
            [{'font': []}],
            ['blockquote', 'code-block']
            // ['video'], //视频上传
            // ['formula'] //需要加载cdnjs.cloudflare.com/ajax/libs/KaTeX/0.7.1/katex.min.js
        ];
        /**
         * 初始化富文本,绑定一个div: div id为editor
         */
        quill = new Quill('#editor', {
            modules: {
                toolbar: toolbarOptions  //指定编辑器操作条
            },
            theme: 'snow', //主题,有两种,snow和bubble,一般都是使用snow
            placeholder: '请输入内容....',
            readOnly: false
        });
        
        //修改样式
        var Align = Quill.import('attributors/style/align');
        Align.whitelist = ['right', 'center', 'justify'];
        Quill.register(Align, true);
        /* 传入布尔值,控制编辑器是否可用 */
        quill.enable();
        //quill.blur(); //失去焦点
        //quill.focus(); //获得焦点

        /**
         * 自定义上传图片第二步
         *
         * 通过addHander监听点击控件事件:image事件
         */
        var toolbar = quill.getModule('toolbar');
        toolbar.addHandler('image',function () {
            $('#imgData').click();
        });
    });

    /**
     * 自定义上传图片第三步
     *
     * 图片上传接口
     */
    function updateImg(file) {
        var formData = new FormData();
        formData.append('file', file);
        $.ajax({
            url: '/uploadPhoto',                        //url
            type: 'post',                        //以post发送
            data: formData,             //要发送的数据。后端接收$_POST['user']
            dataType: 'json',                  //返回的数据类型
            cache: false,
            traditional: true,
            contentType: false,
            processData: false,
            success: function (res) {
                /*console.log(res);*/
                //图片上传成功之后的回调
                const range = quill.getSelection();
                if (range) {
                    //将上传好的图片,插入到富文本的range.index(当前光标处)
                    quill.insertEmbed(range.index, 'image', "" + res.src);
                }
            },
            error: function (e) {
                console.log(e);
            }
        });
    }

    /**
     * 获取富文本内容方法(提交)
     */
    function submitData() {
        res = quill.container.firstChild.innerHTML; //获取当前富文本编辑器实例的内容(带html标签)
        console.log(res); //获取当前富文本编辑器实例的内容(带html标签)
    };
</script>
</body>
</html>

Backend code, using java, a controller is shown below

@RequestMapping("/uploadPhoto")
    @ResponseBody
    public Map<String,String> testQuestion(@RequestParam MultipartFile file){
        Map<String,String> data = new HashMap<>();
       OutputStream os = null;
            InputStream inputStream = null;
            String fileName = System.currentTimeMillis() + ".jpg";
            String userUrl = savePath+fileName;
            try {
                inputStream = photo.getInputStream();
            } catch (IOException e) {
                e.printStackTrace();
            }
            try {
                byte[] bs = new byte[1024];
                int len;
                // 输出的文件流保存到本地文件
                File tempFile = new File(writePath);
                if (!tempFile.exists()) {
                    tempFile.mkdirs();
                }
                os = new FileOutputStream(tempFile.getPath() + File.separator + fileName);
                // 开始读取
                while ((len = inputStream.read(bs)) != -1) {
                    os.write(bs, 0, len);
                }
                os.flush();
        data.put("src", userUrl);
        return data;
    }

Insert picture description here

Published 25 original articles · praised 4 · visits 1516

Guess you like

Origin blog.csdn.net/weixin_39025362/article/details/105540925
Recommended