rt-sim-training-client/src/views/messageBoard/index.vue

449 lines
18 KiB
Vue
Raw Normal View History

2020-11-16 19:26:23 +08:00
<template>
<div id="elDialog" class="message-board-box">
<div class="message-board-title">留言板</div>
2021-04-16 17:46:07 +08:00
<div class="message-board-content">
2020-11-16 19:26:23 +08:00
<div v-if="postCommentList.length">
<template v-for="(item,i) in postCommentList">
2021-04-16 17:46:07 +08:00
<div :key="i" class="eachPostComment">
2020-11-16 19:26:23 +08:00
<div style="margin-bottom: 10px;display: flex;align-items: center;">
<img :src="avatarUrl(item)" class="head_portrait">
2021-04-16 17:46:07 +08:00
<div class="MBCcreatorNickName">{{ item.creatorNickName }}</div>
2020-11-16 19:26:23 +08:00
<div style="display: inline-block;">{{ item.createTime }}</div>
</div>
<div style="margin-left: 60px;" v-html="$escapeHTML(`${item.content}`)" />
2020-11-17 16:55:05 +08:00
<div style="width: 100%;display:flex;align-items: center;justify-content: flex-end;">
2021-04-16 17:46:07 +08:00
<img :src="replyIcon" class="replyIcon" @click="replyLeaveMessage(item.id, i)">
<img v-if="userId == item.creatorId || superAdmin" :src="deleteIcon" class="deleteIcon" @click="deleteMessage(item.id)">
2020-11-17 16:55:05 +08:00
</div>
2021-04-16 17:46:07 +08:00
<div v-if="item.comments && item.comments.total > 0" class="eachComment">
2020-11-17 16:55:05 +08:00
<div v-if="moreMessageId == item.id">
<template v-for="(elem,j) in allCommentList">
2020-11-17 18:29:03 +08:00
<div :key="j" style="font-size: 14px;margin-top: 10px;">
2020-11-17 16:55:05 +08:00
<span style="margin-right: 5px;">{{ computedCommentName(elem) }}</span>
2020-11-19 14:17:01 +08:00
<span style="margin-right: 15px;" v-html="$escapeHTML(`${elem.content}`)" />
2020-11-17 16:55:05 +08:00
<span style="margin-right: 10px;">{{ elem.commentTime }}</span>
2021-04-16 17:46:07 +08:00
<span class="replyLeaveMessage" @click="replyLeaveMessage(item.id, i,elem.id, elem.userNickname)">回复</span>
2020-11-17 18:29:03 +08:00
<span v-if="userId == elem.userId || superAdmin" style="color:#409EFF;cursor: pointer;" type="text" @click="deleteComment(item.id, i, elem.id)">删除</span>
2020-11-17 16:55:05 +08:00
</div>
</template>
</div>
<div v-else>
<template v-for="(elem,j) in item.comments.list">
2020-11-17 18:29:03 +08:00
<div :key="j" style="font-size: 14px;margin-top: 18px;">
2020-11-17 16:55:05 +08:00
<span style="margin-right: 5px;">{{ computedCommentName(elem) }}</span>
2020-11-19 14:17:01 +08:00
<span style="margin-right: 15px;" v-html="$escapeHTML(`${elem.content}`)" />
2020-11-17 16:55:05 +08:00
<span style="margin-right: 10px;">{{ elem.commentTime }}</span>
2021-04-16 17:46:07 +08:00
<span class="replyLeaveMessage" @click="replyLeaveMessage(item.id, i,elem.id, elem.userNickname)">回复</span>
2020-11-17 18:29:03 +08:00
<span v-if="userId == elem.userId || superAdmin" style="color:#409EFF;cursor: pointer;" type="text" @click="deleteComment(item.id, i, elem.id)">删除</span>
2020-11-17 16:55:05 +08:00
</div>
</template>
</div>
<div v-if="item.comments.total > 3 && moreMessageId != item.id" style="margin-top: 10px;">
2020-11-17 16:55:05 +08:00
<span class="view_more" @click="viewMoreComment(item)">{{ `${item.comments.total}条回复,点击查看更多>>` }}</span>
</div>
</div>
<div v-if="replyMessageId == item.id" style="width: 80%;margin-left: 10%;text-align: center;">
2020-11-19 14:17:01 +08:00
<quill-editor
:ref="'answerInput' + item.id"
v-model="commentContent"
style="width: 80%;margin-left: 10%;margin-top: 10px;"
class-name="answer_input"
:margin-bottom="20"
editor-type="onlyEmoji"
:no-handle-p="true"
:height="100"
:placeholder="replyUserName"
/>
<div>
2020-11-17 16:55:05 +08:00
<el-button type="danger" size="small" @click="commentMessage">回复</el-button>
<el-button size="small" @click="cancelComment">取消</el-button>
</div>
</div>
2020-11-16 19:26:23 +08:00
</div>
</template>
</div>
2020-11-30 18:22:22 +08:00
<div v-else class="empty-text">
2020-11-17 16:55:05 +08:00
<span>暂无留言</span>
2020-11-16 19:26:23 +08:00
</div>
<div style="width: 100%;text-align: center;">
<el-pagination
:current-page.sync="pageNum"
:page-size="pageSize"
layout="total, prev, pager, next,jumper"
:total="total"
@current-change="handleCurrentChange"
/>
</div>
2020-11-20 11:22:21 +08:00
</div>
2020-11-19 14:17:01 +08:00
<quill-editor ref="quillEditor" v-model="content" style="width: 80%;margin-left: 10%;" :margin-bottom="20" editor-type="imgEmoji" :no-handle-p="true" />
2020-11-16 19:26:23 +08:00
<span id="boardBottom" class="dialog-footer">
<el-button @click="handleClear">清空</el-button>
2020-11-17 18:29:03 +08:00
<el-button type="danger" @click="commitComment">留言</el-button>
2020-11-16 19:26:23 +08:00
</span>
2021-04-16 17:46:07 +08:00
<el-button size="mini" type="danger" class="goSlide" @click="goSlide">我要留言</el-button>
<div v-show="imgShow" class="popUpImgView" @click="handelCloseImg">
<img id="targetImg" src="" class="popUpImg">
2020-11-16 19:26:23 +08:00
</div>
</div>
2020-11-16 19:26:23 +08:00
</template>
<script>
2020-11-19 14:17:01 +08:00
import { answerPost, queryMessagePagingByProjectCode, deleteMessageByAdmin, deleteMessageBySelf, commentLevelMessage, commentComents,
queryMessageCommentList, deleteCommentByAdmin, deleteCommentBySelf, getPostByProjectCode } from '@/api/learn';
2020-11-17 16:55:05 +08:00
import lick_icon from '@/assets/like.png';
import unlike_icon from '@/assets/unlike.png';
import reply_icon from '@/assets/reply.png';
import delete_icon from '@/assets/delete.png';
import { superAdmin } from '@/router/index';
2020-11-18 10:54:25 +08:00
import { ProjectCode } from '@/scripts/ProjectConfig';
2021-03-03 15:12:21 +08:00
import QuillEditor from '@/components/QuillEditor/index';
2020-11-16 19:26:23 +08:00
export default {
name: 'MessageBoard',
2021-03-03 15:12:21 +08:00
components: {
QuillEditor
},
2020-11-16 19:26:23 +08:00
data() {
return {
content: '',
postCommentList: [],
pageSize: 10,
pageNum: 0,
total: 0,
2020-11-17 16:55:05 +08:00
imgShow: false,
lickIcon: lick_icon,
unlikeIcon: unlike_icon,
replyIcon: reply_icon,
deleteIcon: delete_icon,
replyMessageId: '',
commentContent: '',
replyCommentId: '',
replyMessageIndex: '',
allCommentList: [],
2020-11-17 18:29:03 +08:00
moreMessageId: '',
replyUserName: '',
2020-11-18 10:54:25 +08:00
postId: ''
2020-11-16 19:26:23 +08:00
};
},
2020-11-17 16:55:05 +08:00
computed: {
userId() {
return this.$store.state.user.id;
},
superAdmin() {
return this.$store.state.user.roles.includes(superAdmin);
},
2020-11-18 10:54:25 +08:00
projectCode() {
const project = this.$route.query.project;
2020-11-18 10:54:25 +08:00
return ProjectCode[project];
2020-11-17 16:55:05 +08:00
}
},
2020-11-16 19:26:23 +08:00
created() {
const that = this;
window.handleZoomImg = function () {
that.imgShow = true;
document.getElementById('targetImg').src = event.target.currentSrc;
};
},
2020-11-18 10:54:25 +08:00
mounted() {
getPostByProjectCode(this.projectCode).then(resp => {
this.postId = resp.data.id;
});
this.handleCurrentChange();
2020-11-18 10:54:25 +08:00
},
2020-11-16 19:26:23 +08:00
methods: {
commitComment() {
const images = this.content.match(/<img/g);
2020-11-19 14:17:01 +08:00
const answerContent = this.handleEmojiContent(this.content);
2020-11-16 19:26:23 +08:00
if (images && images.length > 3) {
this.$message.error('留言内容使用图片应小于三张!');
return;
}
2020-11-19 14:17:01 +08:00
if (answerContent.length > 1000) {
2020-11-17 16:55:05 +08:00
this.$message.error('留言内容超出最大长度!');
return;
}
2020-11-19 14:17:01 +08:00
if (!answerContent) {
2020-11-17 19:06:59 +08:00
this.$message.error('留言内容不能为空!');
return;
}
2020-11-19 14:17:01 +08:00
answerPost({postId: this.postId, content: answerContent}).then(resp => {
2020-11-18 10:54:25 +08:00
this.pageNum = 1;
2020-11-16 19:26:23 +08:00
this.handleCurrentChange();
this.content = '';
}).catch(error => {
this.$message.error('留言失败 ');
2020-11-17 16:55:05 +08:00
console.log(error);
2020-11-16 19:26:23 +08:00
});
},
handleCurrentChange() {
2020-11-18 10:54:25 +08:00
queryMessagePagingByProjectCode(this.projectCode, {pageSize: this.pageSize, pageNum: this.pageNum}).then(resp => {
2020-11-16 19:26:23 +08:00
this.postCommentList = [];
(resp.data.list || []).forEach(item => {
2020-11-19 14:17:01 +08:00
item.content = this.replaceEmoji(item.content);
item.comments && item.comments.list && item.comments.list.forEach(elem => {
elem.content = this.replaceEmoji(elem.content);
});
2020-11-16 19:26:23 +08:00
this.postCommentList.push(item);
});
this.total = resp.data.total;
});
},
2020-11-19 14:17:01 +08:00
replaceEmoji(content) {
let value = content.replace(/<img/g, '<img style="width: 100px;height: auto;cursor: zoom-in;" onclick="handleZoomImg()"');
const list = value.match(/<<<([^>]*)>>>/g);
(list || []).forEach(elem => {
const targetValue = elem.substring(3, elem.length - 3);
value = value.replace(elem, `<span class="ql-emojiblot" data-name="${targetValue}"><span contenteditable="false"><span class="ap ap-${targetValue}">ss</span></span></span>`);
});
return value;
},
2020-11-16 19:26:23 +08:00
goSlide() {
const bottom = document.getElementById('boardBottom');
const element = document.getElementById('elDialog').childNodes[0];
element.scrollTop = bottom.offsetTop;
this.$refs.quillEditor.getFocus();
},
avatarUrl(val) {
if (val && val.creatorAvatarPath) {
2021-12-30 19:36:26 +08:00
return this.$store.state.user.resourcesUrl + val.creatorAvatarPath;
2020-11-16 19:26:23 +08:00
} else {
return 'https://joylink.club/oss/wxmicro_assistant/userhead/defaultuser.png';
}
},
handleClear() {
this.content = '';
},
handelCloseImg() {
this.imgShow = false;
document.getElementById('targetImg').src = '';
2020-11-17 16:55:05 +08:00
},
2020-11-17 18:29:03 +08:00
replyLeaveMessage(messageId, messageIndex, commentId, userNickname) {
this.cancelComment();
2020-11-17 16:55:05 +08:00
this.replyMessageId = messageId;
this.replyCommentId = commentId;
this.replyMessageIndex = messageIndex;
2020-11-17 18:29:03 +08:00
if (commentId) {
this.replyUserName = '@' + userNickname + ' ';
2020-11-19 14:17:01 +08:00
this.commentContent = '';
2020-11-17 18:29:03 +08:00
}
2020-11-17 16:55:05 +08:00
this.$nextTick(()=>{
2020-11-19 14:17:01 +08:00
this.$refs['answerInput' + messageId][0].getFocus();
2020-11-17 16:55:05 +08:00
});
},
cancelComment() {
this.replyMessageId = '';
this.commentContent = '';
this.replyCommentId = '';
this.replyMessageIndex = '';
2020-11-17 18:29:03 +08:00
this.replyUserName = '';
2020-11-17 16:55:05 +08:00
},
commentMessage() {
2020-11-19 14:17:01 +08:00
const contentValue = this.handleEmojiContent(this.commentContent);
if (contentValue.length > 300) {
this.$message.error('回复内容超出最大长度!');
return;
}
2020-11-17 16:55:05 +08:00
if (this.replyCommentId) {
2020-11-19 14:17:01 +08:00
commentComents(this.replyMessageId, this.replyCommentId, {content:contentValue}).then(resp => {
2020-11-17 16:55:05 +08:00
this.getCommentList(this.replyMessageId, this.replyMessageIndex);
2020-11-17 18:29:03 +08:00
this.cancelComment();
2020-11-17 16:55:05 +08:00
}).catch(error => {
2020-11-19 14:17:01 +08:00
this.$message.error('评论回复失败!');
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
} else {
2020-11-19 14:17:01 +08:00
commentLevelMessage(this.replyMessageId, {content:contentValue}).then(resp => {
2020-11-17 16:55:05 +08:00
this.getCommentList(this.replyMessageId, this.replyMessageIndex);
2020-11-17 18:29:03 +08:00
this.cancelComment();
2020-11-17 16:55:05 +08:00
}).catch(error => {
2020-11-19 14:17:01 +08:00
this.$message.error('评论回复失败!');
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
}
},
getCommentList(messageId, messageIndex) {
queryMessageCommentList(messageId).then(resp => {
2020-11-19 14:17:01 +08:00
const replaceValue = [];
resp.data && resp.data.forEach(item => {
item.content = this.replaceEmoji(item.content);
replaceValue.push(item);
});
2020-11-17 16:55:05 +08:00
if (this.moreMessageId == messageId) {
2020-11-19 14:17:01 +08:00
this.allCommentList = replaceValue;
2020-11-17 16:55:05 +08:00
}
2020-11-19 14:17:01 +08:00
if (replaceValue.length > 3) {
this.postCommentList[messageIndex].comments.list = replaceValue.slice(0, 3);
this.postCommentList[messageIndex].comments.total = replaceValue.length;
2020-11-17 16:55:05 +08:00
} else {
2020-11-19 14:17:01 +08:00
this.postCommentList[messageIndex].comments.list = replaceValue;
this.postCommentList[messageIndex].comments.total = replaceValue.length;
2020-11-17 16:55:05 +08:00
}
}).catch(error => {
this.$message.error('更新回复失败!');
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
},
computedCommentName(elem) {
2020-11-17 18:29:03 +08:00
if (elem.replyUserNickName) {
2020-11-17 16:55:05 +08:00
return `${elem.userNickname} 回复@ ${elem.replyUserNickName}`;
} else {
return elem.userNickname + '';
}
},
deleteMessage(messageId) {
if (this.superAdmin) {
deleteMessageByAdmin(messageId).then(resp => {
// this.$message.success('删除留言成功!');
this.handleCurrentChange();
}).catch(error => {
this.$message.error('删除留言失败!');
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
} else {
deleteMessageBySelf(messageId).then(resp => {
// this.$message.success('删除留言成功!');
this.handleCurrentChange();
}).catch(error => {
this.$message.error('删除留言失败!');
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
}
},
deleteComment(messageId, messageIndex, commentId) {
if (this.superAdmin) {
deleteCommentByAdmin(commentId).then(resp => {
this.getCommentList(messageId, messageIndex);
}).catch(error => {
this.$message.error('删除回复失败!');
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
} else {
deleteCommentBySelf(commentId).then(resp => {
this.getCommentList(messageId, messageIndex);
}).catch(error => {
this.$message.error('删除回复失败!');
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
}
},
viewMoreComment(data) {
queryMessageCommentList(data.id).then(resp => {
2020-11-19 14:17:01 +08:00
this.allCommentList = [];
resp.data && resp.data.forEach(item => {
item.content = this.replaceEmoji(item.content);
this.allCommentList.push(item);
});
2020-11-17 16:55:05 +08:00
this.moreMessageId = data.id;
}).catch(error => {
2020-11-17 18:31:29 +08:00
console.error(error);
2020-11-17 16:55:05 +08:00
});
2020-11-17 18:29:03 +08:00
},
2020-11-19 14:17:01 +08:00
handleEmojiContent(content) {
const list = content.match(/<span class="ql-emojiblot" data-name="(\S*)"><span contenteditable="false"><span class="ap ap-(\S*)<\/span><\/span><\/span>/g);
(list || []).forEach(item => {
let targetValue = item.split(' ')[2];
targetValue = targetValue.substring(11, targetValue.length - 8);
content = content.replace(item, '<<<' + targetValue + '>>>');
});
return content;
2020-11-16 19:26:23 +08:00
}
}
};
</script>
2021-04-16 17:46:07 +08:00
<style lang="scss" scoped>
2020-11-16 19:26:23 +08:00
.dialog-footer{
margin: 0 auto;
padding: 10px 0 30px;
2020-11-16 19:26:23 +08:00
display: flex;
justify-content: center;
}
2020-11-30 18:22:22 +08:00
.empty-text{
text-align: center;
width: 100%;
height: 50px;
line-height: 50px;
font-size: 18px;
color: #ccc;
}
2020-11-16 19:26:23 +08:00
.head_portrait{
width: 50px;
height: 50px;
border-radius: 25px;
}
2020-11-17 16:55:05 +08:00
.view_more {
cursor: pointer;
}
.view_more:hover {
cursor: pointer;
color: #409EFF;
}
2020-11-16 19:26:23 +08:00
.img-box{
width: 100px;
height: auto;
}
.message-board-box{
width: 100%;
background-image:url('../../assets/bg_board.jpg');
background-size: 100% 100%;
min-height: 100%;
2020-11-16 19:26:23 +08:00
}
/deep/.ql-container{
height: 80%;
}
.message-board-title{
2020-11-17 18:29:03 +08:00
font-size: 30px;
color: #F00;
font-family: 'fangsong';
font-weight: bolder;
width: 100%;
text-align: center;
height: 80px;
line-height: 80px;
2020-11-17 18:29:03 +08:00
}
2021-04-16 17:46:07 +08:00
.message-board-content{
width: 80%;
margin-left: 10%;
padding: 20px;
margin-bottom: 20px;
background-color: rgba(255,255,255,0);
border: 1px solid #ebeef5;
border-radius: 4px;
box-shadow: 0 2px 12px 0 rgba(0,0,0,.1);
}
.eachPostComment{
border: 1px solid #C0C0C0;
border-radius: 5px;
margin-bottom: 20px;
box-shadow: 2px 2px 3px #808080;
padding: 10px 20px;
background-color: #fff
}
.eachComment{
background: #F5F5F5;
margin-top: 10px;
width: calc(100% - 120px);
margin-left: 60px;
border-radius: 5px;
padding: 1px 10px 10px;
}
.replyLeaveMessage{color:#409EFF;cursor: pointer;margin-right: 10px;}
.MBCcreatorNickName{display: inline-block;margin-right: 20px;margin-left:10px;font-size: 18px;color: #000;}
.replyIcon{width: 16px;height: auto;margin-right: 30px;cursor: pointer;}
.deleteIcon{width: 16px;height: auto;cursor:pointer;}
.goSlide{position: fixed; left: 91%;top: 80px;width: 90px;}
.popUpImgView{position: fixed;width: 100%;height: 100%;left: 0;top: 0;background: rgba(0,0,0,0.5);cursor: zoom-out;}
.popUpImg{position: fixed;top: 50%;left: 50%;transform: translate(-50%,-50%);min-width: 500px;max-height: 80%;height: auto;}
2020-11-16 19:26:23 +08:00
</style>
2020-12-30 15:30:24 +08:00
<style>
.ql-size-small {
font-size: 0.75em;
}
.ql-size-large{
font-size: 1.5em;
}
.ql-size-huge{
font-size: 2.5em;
}
</style>