springboot整合富文本编辑器:博客项目
整合富文本编辑器editor.md
首先下载editormd资源包,解压到自己项目资源目录
地址链接:editor.md
** 前端发送请求进入编辑页**
controller层
/**
* 文章编辑页方法
*
* @return
*/
@GetMapping(“/toEditor”)
public String toEditor(Model model) {
model.addAttribute(“admin”, redisUtils.hmget(“user”).get(“username”));
//editormd 为编辑页面html
return “editor/editormd”;
}
editormd.html
<div id="layout">
<header>
<h1>现在开始写文章吧~</h1>
</header>
<form name="mdEditorForm">
<div align="center">
文章标题:<input type="text" name="title">
</div>
<div id="test-editormd">
<textarea style="display:none;" id="textContent" name="content"></textarea>
<!-- 第二个隐藏文本域,用来构造生成的HTML代码,方便表单POST提交,这里的name可以任意取,后台接受时以这个name键为准 -->
<!-- <textarea id="text" class="editormd-html-textarea" name="text"></textarea>-->
</div>
</form>
</div>
<script th:src="@{../js/jquery.min.js}"></script>
<script th:src="@{../js/editormd.min.js}"></script>
<script type="text/javascript">
var testEditor;
$(function () {
testEditor = editormd("test-editormd", {
width: "90%",
height: 640,
syncScrolling: "single",
emoji: true,
path: "../editormd/lib/",
//图片上传
imageUpload: true,
imageFormats: ["jpg", "jpeg", "gif", "png", "bmp", "webp"],
imageUploadURL: "/article/file/upload",
onload: function () {
console.log('onload', this);
},
toolbarIcons: function () {
return ["undo", "redo", "|",
"bold", "del", "italic", "quote", "ucwords", "uppercase", "lowercase", "|",
"h1", "h2", "h3", "h4", "h5", "h6", "|",
"list-ul", "list-ol", "hr", "|",
"link", "reference-link", "image", "code", "preformatted-text",
"code-block", "table", "datetime", "emoji", "html-entities", "pagebreak", "|",
"goto-line", "watch", "preview", "fullscreen", "clear", "search", "|",
"help", "info", "releaseIcon"]
},
toolbarIconTexts: {
releaseIcon: "<span bgcolor=\"gray\" >发布</span>",
},
toolbarHandlers: {
releaseIcon: function (cm, icon, cursor, selection) {
//表单提交
mdEditorForm.method = "post";
mdEditorForm.action = "/addArticle";//提交至服务器的路径
mdEditorForm.submit();
}
}
});
});
</script>
</body>
<div th:replace="~{commons/template :: js}"></div>
</html>
###自定义功能按钮(发布按钮)
toolbarIconTexts: {
releaseIcon: "<span bgcolor=\"gray\" >发布</span>",
// index : "<span bgcolor=\"red\">返回首页</span>",
},
toolbarHandlers: {
releaseIcon: function (cm, icon, cursor, selection) {
//表单提交
mdEditorForm.method = "post";
mdEditorForm.action = "/addArticle";//提交至服务器的路径
mdEditorForm.submit();
}
**新增文章方法
编辑的内容会封装进article
/**
* 文章新增方法
*
* @param article
* @param map
* @return
*/
@PostMapping("addArticle")
public String addArticle(Article article, Map map) {
//获取编辑器内容
map.put("content", article.getContent());
//java日期对象转成数据库日期对象
map.put("createdate", DateUtil.jtod(new Date()));
map.put("adminid",redisUtils.hmget("user").get("userid"));
int res = articleService.insert(map);
//新增成功返回1,否则返回0 逻辑内容可自定义,这里不做书写
}
查看编辑器内容
<div>
<!--文章头部信息:标题,作者,最后更新日期,导航-->
<h2 style="margin: auto 0" th:text="${article.title}"></h2>
<h3 th:text=" '作者:'+ ${article.author}"></h3>
<h3 th:text=" '日期:'+ ${article.createdate}"></h3>
<!--文章主体内容-->
<div id="doc-content" style="width: 80%">
<textarea style="display:none;" placeholder="markdown" th:text="${article.content}"></textarea>
</div>
</div>
<link rel="stylesheet" th:href="@{/css/editormd.preview.css}" />
<script th:src="@{/js/jquery.min.js}"></script>
<script th:src="@{/editormd/lib/marked.min.js}"></script>
<script th:src="@{/editormd/lib/prettify.min.js}"></script>
<script th:src="@{/editormd/lib/raphael.min.js}"></script>
<script th:src="@{/editormd/lib/underscore.min.js}"></script>
<script th:src="@{/editormd/lib/sequence-diagram.min.js}"></script>
<script th:src="@{/editormd/lib/flowchart.min.js}"></script>
<script th:src="@{/editormd/lib/jquery.flowchart.min.js}"></script>
<script th:src="@{/js/editormd.min.js}"></script>
<script type="text/javascript">
var testEditor;
$(function () {
testEditor = editormd.markdownToHTML("doc-content", {//注意:这里是上面DIV的id
htmlDecode: "style,script,iframe",
emoji: true,
taskList: true,
tocm: true,
tex: true, // 默认不解析
flowChart: true, // 默认不解析
sequenceDiagram: true, // 默认不解析
codeFold: true
});
});
</script>
查看文章方法
@RequestMapping("/article/{id}")
public String show(@PathVariable("id") int id, Model model) {
ArticleAdminVo article = articleService.getArticleById(id);
log.info(article);
model.addAttribute("article", article);
return "admin/editor/article";
}
到此为止就可以正常显示啦
解决图片上传问题
//开启图片上传功能
imageUpload: true,
imageFormats: ["jpg", "jpeg", "gif", "png", "bmp", "webp"],
imageUploadURL: "/article/file/upload",
onload: function () {
console.log('onload', this);
},
图片上传方法
/**
* 处理图片上传
*
* @param file
* @param request
* @return
* @throws IOException
*/
//博客图片上传问题
@RequestMapping(value = "/file/upload")
@ResponseBody
public JSONObject fileUpload(@RequestParam(value = "editormd-image-file", required = true) MultipartFile file, HttpServletRequest request) throws IOException{
//上传路径保存设置
//获得SpringBoot当前项目的路径:System.getProperty("user.dir")
String path = System.getProperty("user.dir") + "/upload/";
//按照月份进行分类:
Calendar instance = Calendar.getInstance();
String month = (instance.get(Calendar.MONTH) + 1) + "月";
path = path + month;
File realPath = new File(path);
if (!realPath.exists()) {
realPath.mkdirs();
}
//上传文件地址
System.out.println("上传文件保存地址:" + realPath);
//解决文件名字问题:我们使用uuid;
String filename = "pg-" + UUID.randomUUID().toString().replaceAll("-", "") + ".jpg";
File newfile = new File(realPath, filename);
//通过CommonsMultipartFile的方法直接写文件(注意这个时候)
file.transferTo(newfile);
//给editormd进行回调
JSONObject res = new JSONObject();
res.put("url", "/upload/" + month + "/" + filename);
res.put("success", 1);
res.put("message", "upload success!");
return res;
}
此时还不能正常上传图片,下面开始编写配置文件
@Configuration
public class MyMvcConfig implements WebMvcConfigurer {
//这里涉及到需要配置虚拟路径映射访问,因为对服务器的保护措施导致的,服务器不能对外部暴露真实的资源路径。
// 文件保存在真实物理路径/upload/下(即项目的物理地址下:F:/IDEA_Project_Location/自己/bookstore/upload/3月)
// 访问的时候使用虚路径/upload,比如文件名为1.png,就直接/upload/1.png就ok了。
@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
//将物理地址upload下的文件映射到/upload下
//访问的时候就直接访问http://localhost:9000/upload/文件名
registry.addResourceHandler("/upload/**")
.addResourceLocations("file:"+System.getProperty("user.dir")+"/upload/");
}
}
到此图片可正常显示了