SpringBoot集成Vue3实现的系统(三)

学习目标:SpringBoot集成Vue3实现的系统(三)小内容完结篇

提示:SpringBoot2与Vue3的小练习图文摘录(三)

例如:

  • 三篇文章带你更熟悉掌握前后端分离的基本实现

新闻模块化操作

在后台的很多实际应用中都存在这很多的内容编辑的处理,所以我们需要使用到的是【富文本编辑器】

SpringBoot集成Vue3实现的系统(三)_第1张图片

在此我们选择的是vue集成wangEditor

SpringBoot集成Vue3实现的系统(三)_第2张图片

集成wangeditor编辑器的实现

参考官网即可:https://www.wangeditor.com/v5/for-frame.html#vue3
SpringBoot集成Vue3实现的系统(三)_第3张图片

①、首先需要通过官网的提示操作进行安装
yarn add @wangeditor/editor
# 或者 npm install @wangeditor/editor --save

yarn add @wangeditor/editor-for-react
# 或者 npm install @wangeditor/editor-for-react --save
②、学习文档熟悉组件Toolbar和Editor以及对应的函数

SpringBoot集成Vue3实现的系统(三)_第4张图片

③、参考在线的demo示例来根据自己的需求进行修改处理

SpringBoot集成Vue3实现的系统(三)_第5张图片

https://stackblitz.com/edit/vue3-wangeditor-demo?file=src%2Fcomponents%2FBasicEditor.vue

SpringBoot集成Vue3实现的系统(三)_第6张图片

新增新闻公告模块来使用wangEditor富文本编辑器的使用

①、数据库表
CREATE TABLE `t_news` (
    `id` INT ( 11 ) NOT NULL AUTO_INCREMENT COMMENT '公告主键编号',
    `title` VARCHAR ( 255 ) DEFAULT NULL COMMENT '标题',
    `content` TEXT COMMENT '内容',
    `author` VARCHAR ( 255 ) DEFAULT NULL COMMENT '作者',
    `create_time` DATETIME DEFAULT NULL COMMENT '创建时间',
    `update_time` DATETIME DEFAULT NULL COMMENT '修改时间',
    `create_user` INT ( 11 ) DEFAULT NULL COMMENT '创建用户编号',
    `update_user` INT ( 11 ) DEFAULT NULL COMMENT '修改公告用户编号',
    `deleted` INT ( 11 ) DEFAULT '0' COMMENT '逻辑删除【默认值为0】',
PRIMARY KEY ( `id` ) 
) ENGINE = INNODB AUTO_INCREMENT = 8 DEFAULT CHARSET = utf8;
②、后端通过MybatisX插件生成对应的三层代码

SpringBoot集成Vue3实现的系统(三)_第7张图片

注意实体对象的中如果有时间可以通过JSONFormat注解实现【前端的时间解析就可以去除】
SpringBoot集成Vue3实现的系统(三)_第8张图片

③、前端中复制一个书籍/用户的vue文件并进行修改

SpringBoot集成Vue3实现的系统(三)_第9张图片

④、修改查询的请求路径即可

SpringBoot集成Vue3实现的系统(三)_第10张图片

新增公告的实现

News.vue中的新增公告的对话框

SpringBoot集成Vue3实现的系统(三)_第11张图片


    <el-dialog v-model="dialogVisible" title="公告信息" width="80%">
      <el-form :model="form" label-width="120px"  >
        <el-form-item label="公告标题:">
          <el-input v-model="form.title" style="width: 80%;" />
        el-form-item>
        
        
        <el-form-item label="内   容:">
          <div style="border: 1px solid #ccc">
            <Toolbar
              style="border-bottom: 1px solid #ccc"
              :editor="editorRef"
              :defaultConfig="toolbarConfig"
              :mode="mode"
            />
            <Editor
              style="height: 400px; overflow-y: hidden;"
              v-model="form.content"
              :defaultConfig="editorConfig"
              :mode="mode"
              @onCreated="handleCreated"
              @onChange="handleChange"
              @onDestroyed="handleDestroyed"
              @onFocus="handleFocus"
              @onBlur="handleBlur"
              @customAlert="customAlert"
              @customPaste="customPaste"
            />
          div>
        el-form-item>
      el-form>
      <template #footer>
        <span class="dialog-footer">
          <el-button @click="dialogVisible = false">取消el-button>
          <el-button type="primary" @click="save">确认el-button>
        span>
      template>
    el-dialog>
script中的实现

参照文档使用vue3的特性来写
SpringBoot集成Vue3实现的系统(三)_第12张图片

代码如下:
<script>
import { getData, postData } from "../utils/remote";
import '@wangeditor/editor/dist/css/style.css' // 引入 css

import {h}  from "vue"

import { onBeforeUnmount, ref, shallowRef, onMounted,reactive,toRefs } from 'vue'
import { Editor, Toolbar } from '@wangeditor/editor-for-vue'

import { ElNotification } from "element-plus";

export default {
  name:"News",
  components: { Editor, Toolbar },
  setup() {

    const state=reactive({
        form: {},
        total: 0,
        dialogVisible: false,
        search: "",
        currentPage: 1,
        pageSize: 5,
        tableData: []
    });

    // 编辑器实例,必须用 shallowRef,重要!
    const editorRef = shallowRef();

    // 内容 HTML
    const valueHtml = ref('

hello

'
); // 模拟 ajax 异步获取内容 onMounted(() => { setTimeout(() => { valueHtml.value = '

模拟 Ajax 异步设置内容

'
; }, 1500); }); const toolbarConfig = {}; const editorConfig = { placeholder: '请输入内容...' }; // 组件销毁时,也及时销毁编辑器,重要! onBeforeUnmount(() => { const editor = editorRef.value; if (editor == null) return; editor.destroy(); }); // 编辑器回调函数 const handleCreated = (editor) => { console.log('created', editor); editorRef.value = editor; // 记录 editor 实例,重要! }; const handleChange = (editor) => { console.log('change:', editor.getHtml()); }; const handleDestroyed = (editor) => { console.log('destroyed', editor); }; const handleFocus = (editor) => { console.log('focus', editor); }; const handleBlur = (editor) => { console.log('blur', editor); }; const customAlert = (info, type) => { alert(`【自定义提示】${type} - ${info}`); }; const customPaste = (editor, event, callback) => { console.log('ClipboardEvent 粘贴事件对象', event); // 自定义插入内容 // editor.insertText('xxx'); // 返回值(注意,vue 事件的返回值,不能用 return) // callback(false); // 返回 false ,阻止默认粘贴行为 callback(true) // 返回 true ,继续默认的粘贴行为 }; const insertText = () => { const editor = editorRef.value; if (editor == null) return; editor.insertText('hello world'); }; const printHtml = () => { const editor = editorRef.value; if (editor == null) return; console.log(editor.getHtml()); }; const disable = () => { const editor = editorRef.value; if (editor == null) return; editor.disable() }; load(); //查询所有的公告信息 function load(){ getData("news/loadAllByPage", { pageNum: state.currentPage, pageSize: state.pageSize, search: state.search, }).then((res) => { console.log(res); state.tableData = res.data.records; state.total = res.data.total; }); } //打开新增公告的对话框 function add(){ state.dialogVisible = true; state.form = {}; handleCreated(); } //点击保存触发的事件 function save(){ const editor=editorRef.value; if(editor==null)return; state.form.content=editor.getHtml(); console.log("获取的内容:"+editor.getHtml()); //新增和修改是共用的 if(state.form.id){ //更新 //获取当前登录的用户名 let users=JSON.parse(sessionStorage.getItem("user")||"{}"); state.form.author=users.nickname; //发起请求 postData("news/edit",state.form).then(res=>{ console.log(res.data); if (res.data) { ElNotification({ title: "温馨提示", message: h("i",{style:'color:teal'},"成功修改公告信息!"), type: 'success' }); } else { ElNotification({ title: "温馨提示", message: h("i",{style:'color:teal'},"修改公告信息失败!"), type: 'error' }); } state.dialogVisible = false; load();//重新加载信息 }); }else{ //新增 //获取当前登录的用户名 let users=JSON.parse(sessionStorage.getItem("user")||"{}"); state.form.author=users.nickname; //发起请求 postData("news/save",state.form).then(res=>{ console.log(res.data); if (res.data) { ElNotification({ title: "温馨提示", message: h("i",{style:'color:teal'},"成功发布公告信息!"), type: 'success' }); } else { ElNotification({ title: "温馨提示", message: h("i",{style:'color:teal'},"发布公告信息失败!"), type: 'error' }); } state.dialogVisible = false; load();//重新加载信息 }); } } function handleEdit(row){ if(!editorRef){ const editors=editorRef.value; editors.insertText(row.content); } state.form=JSON.parse(JSON.stringify(row)); state.dialogVisible=true; } function handleDelete(id){ postData("news/"+id).then(res=>{ if (res.data) { ElNotification({ title: "温馨提示", message: h("i",{style:'color:teal'},"成功删除公告信息!"), type: 'success' }); load();//重新加载 } else { ElNotification({ title: "温馨提示", message: h("i",{style:'color:teal'},"删除公告信息失败!"), type: 'error' }); } }); } function handleSizeChange(pageSize) { //改变当前页的页大小触发 state.pageSize = pageSize; load(); } function handleCurrentChange(pageNum) { //改变当前页的时候触发 state.currentPage = pageNum; load(); } return { ...toRefs(state), editorRef, valueHtml, mode:"default", // 或 'simple' toolbarConfig, editorConfig, handleCreated, handleChange, handleDestroyed, handleFocus, handleBlur, customAlert, customPaste, load, add, insertText, printHtml, disable, save, handleSizeChange, handleCurrentChange, handleEdit, handleDelete }; } }
新增和修改共用
 //点击保存触发的事件
   function save(){
        const editor=editorRef.value;
        if(editor==null)return;
        state.form.content=editor.getHtml();
        console.log("获取的内容:"+editor.getHtml());
        //新增和修改是共用的
        if(state.form.id){
            //更新
            //获取当前登录的用户名
            let users=JSON.parse(sessionStorage.getItem("user")||"{}");
            state.form.author=users.nickname;
            //发起请求
            postData("news/edit",state.form).then(res=>{
              console.log(res.data);
                if (res.data) {
                  ElNotification({
                    title: "温馨提示",
                    message: h("i",{style:'color:teal'},"成功修改公告信息!"),
                    type: 'success'
                  });
                } else {
                  ElNotification({
                    title: "温馨提示",
                    message: h("i",{style:'color:teal'},"修改公告信息失败!"),
                    type: 'error'
                  });
                }
                state.dialogVisible = false;
                load();//重新加载信息  
            });
        }else{
            //新增
            //获取当前登录的用户名
            let users=JSON.parse(sessionStorage.getItem("user")||"{}");
            state.form.author=users.nickname;
            //发起请求
            postData("news/save",state.form).then(res=>{
              console.log(res.data);
                if (res.data) {
                  ElNotification({
                    title: "温馨提示",
                    message: h("i",{style:'color:teal'},"成功发布公告信息!"),
                    type: 'success'
                  });
                } else {
                  ElNotification({
                    title: "温馨提示",
                    message: h("i",{style:'color:teal'},"发布公告信息失败!"),
                    type: 'error'
                  });
                }
                state.dialogVisible = false;
                load();//重新加载信息  
            });
        }
   }
   
   
    function handleEdit(row){
        if(!editorRef){
              const editors=editorRef.value;
              editors.insertText(row.content);
        }
        state.form=JSON.parse(JSON.stringify(row));
        state.dialogVisible=true;
   }
后端控制器的编写:
package com.xuguoguo.controller;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.xuguoguo.commons.Result;
import com.xuguoguo.entity.Book;
import com.xuguoguo.entity.News;
import com.xuguoguo.service.NewsService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.List;

/**
 @Package: com.xuguoguo.controller
 @ClassName: BookController
 @Author: XuGuoGuo
 @CreateTime: 2023/12/12-16:40
 @Description:
 */
@RestController
@RequestMapping("/news")
public class NewsController {

    //注入service
    @Autowired
    private NewsService newsService;

    @RequestMapping("/loadAll")
    public Result loadAll(){
        List<News> list = newsService.list();
        return Result.of(list);
    }

    @RequestMapping("/loadAllByPage")
    public Result loadAllByPage(@RequestParam("pageNum")Integer pageNum,
                                @RequestParam("pageSize")Integer pageSize,
                                String search){
        //通过分页的插件【拦截器】
        Page<News> pages = new Page<>(pageNum, pageSize);
        //构造条件构造器
        QueryWrapper<News> bookQueryWrapper = new QueryWrapper<>();
        if (search!=null&& !"".equals(search)) {
            bookQueryWrapper.like("title",search);
        }
        Page<News> page = newsService.page(pages, bookQueryWrapper);
        return Result.of(page);
    }


    @RequestMapping("/save")
    public Result save(@RequestBody News news){
        //调用service实现新增用户
        boolean save = newsService.save(news);
        return Result.of(save);
    }

    @RequestMapping("/edit")
    public Result edit(@RequestBody News news){
        boolean b = newsService.updateById(news);
        return Result.of(b);
    }

    @RequestMapping("/{id}")
    public Result deleted(@PathVariable("id")Integer id){
        boolean b = newsService.removeById(id);
        return Result.of(b);
    }


    @RequestMapping("/delBatch")
    public Result delBatch(@RequestBody List<Integer> ids){
        //调用service中的批量删除实现
        boolean b = newsService.removeBatchByIds(ids);
        return Result.of(b);
    }

}
访问如下:

SpringBoot集成Vue3实现的系统(三)_第13张图片SpringBoot集成Vue3实现的系统(三)_第14张图片
SpringBoot集成Vue3实现的系统(三)_第15张图片

vue前端与后端分离的小练习就到此结束了,大家可以自行练习,加强学习哦!~~~ 有问题可留言或者评论私我~

小章节完毕,敬请期待后续更新(可留言需要学习哪方面的内容哈)!如果需要源码的朋友们可关注微信公众号"锅锅编程生活"或者扫描二维码关注回复关键字/后台留言获取即可!
SpringBoot集成Vue3实现的系统(三)_第16张图片

你可能感兴趣的:(SpringBoot,Vue,Java,spring,boot,后端,java,vscode,mysql,大数据)