基于SpringBoot + Vue的个人博客系统15——写文章功能
简介写文章页面,使用 Markdown 编辑器, 关于Markdown编辑器,vue-admin-template 默认使用的是 tui.editor ,这里使用 mavonEditor,因为 mavonEditor 的用法更加简单,文档也通俗易通,而且个人感觉样式更加美观,可以根据个人喜好自行选择。tui.editor : https://github.com/nhnent/tui.editor
简介
写文章页面,使用 Markdown 编辑器, 关于Markdown编辑器,vue-admin-template 默认使用的是 tui.editor ,这里使用 mavonEditor,因为 mavonEditor 的用法更加简单,文档也通俗易通,而且个人感觉样式更加美观,可以根据个人喜好自行选择。
tui.editor : https://github.com/nhnent/tui.editor
mavonEditor : https://github.com/hinesboy/mavonEditor
代码实现
1、安装mavonEditor
npm install mavon-editor --save
2、在main.js
中全局注册该组件
import mavonEditor from 'mavon-editor'
import 'mavon-editor/dist/css/index.css'
// use mavonEditor
Vue.use(mavonEditor)
3、在@/views/editor/index.vue
中使用组件,即可使用
<template>
<div class="app-container">
<mavon-editor v-model="article.content" class="editor" />
</div>
</template>
<script>
export default {
data() {
return {
article: {
content: "",
},
};
},
methods: {},
};
</script>
<style lang="scss" scoped>
.editor {
height: 650px;
}
</style>
4、效果如图
5、我们要做的是文章提交功能,所以这里还要在页面展示文章信息的表单
这里有两种思路:
- 一种是将文章信息的表单展示在编辑器上方,文章信息的表单和文章内容在同一个页面中
- 另一种是当用户点击提交的时候弹出提示框,让用户填写文章信息。
这里选择第二种思路,先显示一个文章标题的输入框
<div class="title-box">
<input type="text" class="title" v-model="article.title" placeholder="请输入标题..." />
<el-button type="text" @click="openDialog">提交</el-button>
</div>
<mavon-editor v-model="article.content" class="editor" />
.title-box {
display: grid;
grid-template-columns: 22fr 2fr;
}
.title {
background: none;
color: #303133;
text-indent: 0px;
outline: none;
font-size: 16px;
font-weight: bold;
display: block;
border: none;
border-bottom: 1px solid #e0e0e0;
border-radius: 0;
line-height: 1;
overflow: visible;
margin-bottom: 15px;
padding: 4px;
}
.title:focus {
border-color: #409eff;
}
效果如图:
此时 data 中的数据:
data() {
return {
showDialog: false,
categories: [],
inputTag: "",
inputTagVisible: false,
showAddCategoryInput: false,
article: {
title: "",
content: "",
category: "",
tags: [],
tabloid: "",
type: true,
author: "",
newCategory: "",
},
};
},
当点击“提交”按钮的时候,调用 openDialog 方法,显示文章信息表单弹出框
// 断言 target 为非空
assertNotEmpty(target, msg) {
if (!target) {
this.$message({
message: msg,
type: "warning",
});
return false;
}
return true;
},
// 打开文章信息填写框
openDialog() {
if (
this.assertNotEmpty(this.article.title, "请填写文章标题") &&
this.assertNotEmpty(this.article.content, "请填写文章内容")
) {
this.showDialog = true;
}
},
6、使用 el-dialog 组件做弹出框
<el-dialog :title="`发布文章:${article.title}`" :visible.sync="showDialog" width="30%">
<el-form label-position="left" label-width="80px">
<el-form-item label="标签:" style="width:fit-content">
<el-tag
:key="tag"
v-for="tag in article.tags"
closable
:disable-transitions="false"
@close="handleTagClose(tag)"
>{{tag}}</el-tag>
<el-input
v-if="inputTagVisible"
v-model="inputTag"
ref="saveTagInput"
size="small"
@keyup.enter.native="handleTagInputConfirm"
@blur="handleTagInputConfirm"
class="input-new-tag"
></el-input>
<el-button v-else class="button-new-tag" size="small" @click="showTagInput">+ 新标签</el-button>
</el-form-item>
<el-form-item label="分类:">
<el-select v-model="article.category" placeholder="请选择">
<el-option
v-for="(category,index) in categories"
:key="index"
:label="category"
:value="category"
></el-option>
</el-select>
<el-button type="text" @click="showAddCategoryInput = true" class="add-category-btn">自定义分类</el-button>
</el-form-item>
<el-collapse-transition>
<el-form-item label="新分类:" v-show="showAddCategoryInput">
<el-input v-model="article.newCategory" @keypress.enter.native="addCategory"></el-input>
</el-form-item>
</el-collapse-transition>
<el-form-item label="摘要:">
<el-input type="textarea" v-model="article.tabloid" rows="4"></el-input>
</el-form-item>
<el-form-item label="作者:">
<el-input type="text" v-model="article.author"></el-input>
</el-form-item>
<el-form-item>
<el-checkbox v-model="article.type">原创</el-checkbox>
</el-form-item>
</el-form>
<span slot="footer">
<el-button @click="handleCancel">取 消</el-button>
<el-button type="primary" @click="handleSubmit">发布</el-button>
</span>
</el-dialog>
说明:
- 其中动态添加标签的功能参考:https://element.eleme.cn/#/zh-CN/component/tag
- 实现了自定分类的功能
7、网络请求
新建@/api/category.js
封装获取全部分类的方法
import request from '@/utils/request'
export function getAllCategories() {
return request({
url: '/categories',
method: 'get',
})
}
在@/utils/request.js
中配置post的默认请求头
service.defaults.headers.post['Content-Type'] = 'application/json;charset=UTF-8';
在@/api/article.js
添加添加文章的方法
export function postArticle(params) {
return request({
url: '/auth/articles',
method: "post",
data: {
title: params.title,
content: params.content,
category: params.category,
tags: params.tags.join(),
tabloid: params.tabloid,
type: params.type ? 1 : 0,
author: params.author,
}
})
}
说明:
- 注意对标签数组的处理
在 created 函数中获取所有分类
created() {
getAllCategories().then((res) => {
this.categories = res.data.map((item) => item.name);
});
},
8、然后编写“发布”和“取消”两个按钮的回调函数
handleCancel() {
this.showDialog = false;
},
handleSubmit() {
if (
this.assertNotEmpty(this.article.category, "分类不能为空") &&
this.assertNotEmpty(this.article.tags.join(), "文章标签不能为空") &&
this.assertNotEmpty(this.article.tabloid, "文章摘要不能为空") &&
this.assertNotEmpty(this.article.author, "文章作者不能为空")
) {
this.showDialog = false;
postArticle(this.article).then((res) => {
this.$notify({
title: "提示",
message: `文章《${this.article.title}》发布成功`,
type: "success",
});
this.$router.push("/example/table");
});
}
},
说明:
- this.$notify 为Element-UI提供的消息框,可参考官方文档:https://element.eleme.cn/#/zh-CN/component/notification
- 文章提交成功之后,跳转到文章管理页面
效果图:
发布文章界面:
文章发布成功:
参考代码:https://gitee.com/qianyucc/QBlog2/tree/v-10.0
更多推荐
所有评论(0)