SpringBoot3+vue3实现系统公告功能
设计数据库表
1.创建系统公共表
1 2 3 4 5 6 7 CREATE TABLE `notice` ( `id` int NOT NULL COMMENT '主键ID' , `title` varchar (255 ) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '公共标题' , `content` varchar (255 ) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '公告内容' , `time ` varchar (255 ) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '发布时间' , PRIMARY KEY (`id`) ) ENGINE= InnoDB DEFAULT CHARSET= utf8mb4 COLLATE = utf8mb4_unicode_ci COMMENT= '系统公告表' ;
公告首页渲染
Timeline 时间线 | Element Plus
Notice.vue
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 <template> <div> <div class="card" style="margin-bottom: 5px"> <!-- 加上clearable这个属性可以快速清除也就是那个叉叉顺便刷新一下 v-model="data.name" 将输入的文字显示到输入框内--> <el-input clearable @clear="load" style="width: 240px;margin-right: 5px;" v-model="data.title" placeholder="请输入标题查询" :prefix-icon="Search"></el-input> <el-button type="primary" @click="load">查 询</el-button> <el-button @click="reset">重 置</el-button> </div> <div class="card" style="margin-bottom: 5px"> <el-button type="primary" @click="handleAdd">新 增</el-button> </div> <div class="card" style="margin-bottom: 5px"> <el-table :data="data.tableData" style="width: 100%" :header-cell-style="{fontWeight: 'bold',color: '#333',backgroundColor: '#c902f6'}"> <el-table-column prop="title" label="公告标题"/> <el-table-column prop="content" label="公告内容" /> <el-table-column prop="time" label="公告时间" /> <el-table-column label="操作" width="100"> <template #default="scope"> <el-button type="primary" icon="Edit" circle @click="handleEdit(scope.row)"></el-button> <el-button type="danger" icon="Delete" circle @click="del(scope.row.id)"></el-button> </template> </el-table-column> </el-table> </div> <el-dialog v-model="data.formVisible" title="公告信息" width="30%" destroy-on-close> <el-form ref="formRef" :model="data.form" :rules="data.rules" label-width="80px" style="padding: 20px 30px 10px 0"> <el-form-item prop="title" label="公告标题"> <el-input v-model="data.form.title" autocomplete="off" placeholder="请输入公共标题"/> </el-form-item> <el-form-item prop="content" label="公共内容"> <el-input type="textarea" :rows="3" v-model="data.form.content" autocomplete="off" placeholder="请输入公告内容"/> </el-form-item> </el-form> <template #footer> <div class="dialog-footer"> <el-button @click="data.formVisible = false">Cancel</el-button> <el-button type="primary" @click="save()"> Confirm </el-button> </div> </template> </el-dialog> </div> </template> <script setup> import {Search} from "@element-plus/icons-vue"; import {reactive,ref} from "vue"; import request from "@/utils/request.js"; import {ElMessage, ElMessageBox} from "element-plus"; const formRef = ref() const data = reactive({ user: JSON.parse(localStorage.getItem('code2025_user') || "{}"), title: null, pageNum: 1, pageSize: 5, total: 0, tableData: [], form: {}, formVisible: false, rules: { title: [ {required: true,message: '请填写公告标题',trigger: 'blur'} ], content: [ {required: true,message: '请填写公告内容',trigger: 'blur'} ], } }) const load = () => { request.get('/notice/selectPage',{ params: { pageNum: data.pageNum, pageSize: data.pageSize, title: data.title } }).then(res=>{ if(res.code === '200'){ data.tableData = res.data?.list data.total = res.data?.total }else{ ElMessage.error(res.msg) } }) } load() const handleEdit = (row) => { data.form = JSON.parse(JSON.stringify(row)) data.formVisible = true } const handleAdd = () => { data.form = {} data.formVisible = true } const add = () => { request.post('/notice/add',data.form).then(res => { if(res.code==='200'){ ElMessage.success("新增成功") data.formVisible = false load() }else{ ElMessage.error(res.msg) } }) } const save = () => { formRef.value.validate(valid => { if(valid) { data.form.id?update():add() }else{ ElMessage.error(res.msg) } }) } const update = () => { request.put('/notice/update',data.form).then(res => { if(res.code === '200'){ ElMessage.success('更新成功') data.formVisible = false load() }else{ ElMessage.error(res.msg) } }) } const del = (id)=>{ ElMessageBox.confirm('删除后无法恢复,您确认删除吗?','删除确认',{ type:"warning" }).then(res => { request.delete('/notice/delete/'+id).then(res=>{ if(res.code === '200'){ ElMessage.success('删除成功') load() }else{ ElMessage.error(res.msg); } }) }).catch(err=>{ }) } const reset = () =>{ data.title = null; load() } </script>
Home.vue
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 <template> <div> <div class="card">泥嚎!欢迎使用本系统!</div> <div class="card" style="margin-top: 10px;width: 50%;"> <div style="font-size: 18px; margin-bottom: 20px;">系统公告</div> <el-timeline style="max-width: 600px"> <el-timeline-item :timestamp="item.time" color="#0bbd87" placement="top" v-for="item in data.noticeData"> <!-- <el-card>--> <!-- 也可以根据官网<div style="font-size: 20px">{{ item.title }}</div>--> <h4>{{ item.title }}</h4> <p>{{ item.content }}</p> <!-- </el-card>--> </el-timeline-item> </el-timeline> </div> </div> </template> <script setup> import {reactive} from "vue"; import request from "@/utils/request.js"; import {ElMessage} from "element-plus"; const data = reactive({ user: JSON.parse(localStorage.getItem('code2025_user') || "{}"), noticeData: [] }) const loadNotice = () => { request.get('/notice/selectAll').then(res=>{ if(res.code === '200'){ data.noticeData = res.data if(data.noticeData.length > 3){ data.noticeData = data.noticeData.slice(0,3) } }else{ ElMessage.error(res.msg) } }) } loadNotice() </script>
后端直接根据User的来改即可.
前端渲染也可以参考手风琴效果
Collapse折叠面板 自行尝试即可