Squashed commit of the following:
commit d0722f229c376afa241441bc91d085f6c6f68d4e Author: dong <58670809@qq.com> Date: Thu Apr 20 10:51:28 2023 +0800 新会话群
This commit is contained in:
parent
d082dc2fbc
commit
df2cae5c2b
125
src/api/newChat.js
Normal file
125
src/api/newChat.js
Normal file
@ -0,0 +1,125 @@
|
||||
|
||||
import request from '@/utils/request';
|
||||
|
||||
/**
|
||||
* 获取群列表
|
||||
* @param {String} groupId
|
||||
* @returns
|
||||
*/
|
||||
export function getGroupList(groupId) {
|
||||
return request({
|
||||
url: `/api/simulation/${groupId}/conversation/group/list`,
|
||||
method: 'get'
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 创建群
|
||||
* @param {String} groupId
|
||||
* @param {String} data
|
||||
* @param {String} data.name
|
||||
* @param {String} data.imageUrl
|
||||
* @param {Array} data.memberIds
|
||||
* @returns
|
||||
*/
|
||||
export function createGroup(groupId, data) {
|
||||
return request({
|
||||
url: `/simulation/${groupId}/operate/Conversation_Group_Create`,
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 修改群组名称
|
||||
* @param {String} groupId
|
||||
* @param {Object} data
|
||||
* @param {String} data.id
|
||||
* @param {String} data.name
|
||||
* @returns
|
||||
*/
|
||||
export function updateGroupName(groupId, data) {
|
||||
return request({
|
||||
url: `/simulation/${groupId}/operate/Conversation_Group_Update_Name`,
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 修改群组群主
|
||||
* @param {String} groupId
|
||||
* @param {Object} data
|
||||
* @param {Number} data.id
|
||||
* @param {String} data.memberId
|
||||
* @returns
|
||||
*/
|
||||
export function updateGroupLeader(groupId, data) {
|
||||
return request({
|
||||
url: `/simulation/${groupId}/operate/Conversation_Group_Update_Leader`,
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 邀请人员入群
|
||||
* @param {String} groupId
|
||||
* @param {Object} data
|
||||
* @param {Number} data.id
|
||||
* @param {Array} data.memberIds
|
||||
* @returns
|
||||
*/
|
||||
export function inviteMemberToGroup(groupId, data) {
|
||||
return request({
|
||||
url: `/simulation/${groupId}/operate/Conversation_Group_Invite_Member`,
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 移除群内人员
|
||||
* @param {String} groupId
|
||||
* @param {Object} data
|
||||
* @param {Number} data.id
|
||||
* @param {Array} data.memberIds
|
||||
* @returns
|
||||
*/
|
||||
export function removeMemberFromGroup(groupId, data) {
|
||||
return request({
|
||||
url: `/simulation/${groupId}/operate/Conversation_Group_Remove_Member`,
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 退出群组
|
||||
* @param {String} groupId
|
||||
* @param {Object} data
|
||||
* @param {Number} data.id
|
||||
* @returns
|
||||
*/
|
||||
export function exitGroup(groupId, data) {
|
||||
return request({
|
||||
url: `/simulation/${groupId}/operate/Conversation_Group_Exit`,
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 解散群组
|
||||
* @param {String} groupId
|
||||
* @param {Object} data
|
||||
* @param {Number} data.id
|
||||
* @returns
|
||||
*/
|
||||
export function dissolveGroup(groupId, data) {
|
||||
return request({
|
||||
url: `/simulation/${groupId}/operate/Conversation_Group_Dissolve`,
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
@ -806,6 +806,19 @@ const map = {
|
||||
map.memberMap.EMERGENCY = [];
|
||||
}
|
||||
}
|
||||
if (!map.conversationGroupMap) {
|
||||
map.conversationGroupMap = { METRO: [], RAILWAY: [], EMERGENCY: [] };
|
||||
} else {
|
||||
if (!map.conversationGroupMap.METRO) {
|
||||
map.conversationGroupMap.METRO = [];
|
||||
}
|
||||
if (!map.conversationGroupMap.RAILWAY) {
|
||||
map.conversationGroupMap.RAILWAY = [];
|
||||
}
|
||||
if (!map.conversationGroupMap.EMERGENCY) {
|
||||
map.conversationGroupMap.EMERGENCY = [];
|
||||
}
|
||||
}
|
||||
state.map = map;
|
||||
let showConfig = {};
|
||||
if (Vue.prototype.$jlmap && typeof Vue.prototype.$jlmap.getShowConfig === 'function') {
|
||||
|
@ -119,7 +119,8 @@ const socket = {
|
||||
simulationWorkParam: {},
|
||||
conversationMessage: {},
|
||||
controlTransfer: {},
|
||||
operationModeApplyList: [] // 模式转换消息列表
|
||||
operationModeApplyList: [], // 模式转换消息列表
|
||||
conversationGroup: {} // 群组消息
|
||||
},
|
||||
getters: {
|
||||
},
|
||||
@ -406,6 +407,9 @@ const socket = {
|
||||
state.operationModeApplyList.splice(index, 1);
|
||||
}
|
||||
});
|
||||
},
|
||||
setConversationGroup: (state, message) => {
|
||||
state.conversationGroup = message;
|
||||
}
|
||||
},
|
||||
|
||||
@ -644,6 +648,9 @@ const socket = {
|
||||
},
|
||||
operationModeApply: ({ commit }, message) => {
|
||||
commit('operationModeApply', message);
|
||||
},
|
||||
setConversationGroup: ({ commit }, message) => {
|
||||
commit('setConversationGroup', message);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
@ -31,7 +31,7 @@ export function handlerUrl() {
|
||||
// BASE_API = 'http://192.168.3.94:9000'; // 旭强
|
||||
// BASE_API = 'http://192.168.3.15:9000'; // 张赛
|
||||
// BASE_API = 'http://192.168.3.5:9000'; // 夏增彬
|
||||
// BASE_API = 'http://192.168.3.37:9000'; // 卫志宏
|
||||
BASE_API = 'http://192.168.3.37:9000'; // 卫志宏
|
||||
// BASE_API = 'http://b29z135112.zicp.vip';
|
||||
// BASE_API = 'http://2925963m2a.zicp.vip'; // 杜康
|
||||
// BASE_API = 'http://2i38984j47.qicp.vip'; // 张赛
|
||||
|
@ -99,6 +99,9 @@ function handle(data) {
|
||||
case 'Simulation_Member':
|
||||
store.dispatch('socket/memberChangeCountIncrease');
|
||||
break;
|
||||
case 'Simulation_Conversation_Group':
|
||||
store.dispatch('socket/setConversationGroup', msg);
|
||||
break;
|
||||
case 'Simulation_Time_Sync':
|
||||
store.dispatch('socket/setSimulationTimeSync', msg);
|
||||
break;
|
||||
|
@ -29,7 +29,7 @@ import TrainingTip from './trainingList/trainingTip';
|
||||
import TrainingPositionTip from './trainingList/trainingPositionTip.vue';
|
||||
import TrainingMenu from './trainingList/trainingMenu';
|
||||
import TrainingDesign from './trainingDesign/designPane.vue';
|
||||
import ChatBox from './chatBox';
|
||||
import ChatBox from './newChat/index.vue';
|
||||
import TrainingLeftSlider from './trainingList/trainingLeftSlider';
|
||||
import LineBoard from './lineBoard';
|
||||
import BottomTable from './bottomTable';
|
||||
|
328
src/views/newMap/display/newChat/chatDialog.vue
Normal file
328
src/views/newMap/display/newChat/chatDialog.vue
Normal file
@ -0,0 +1,328 @@
|
||||
<template>
|
||||
<el-dialog
|
||||
v-dialogDrag
|
||||
class="chatDialog"
|
||||
:visible.sync="dialogVisible"
|
||||
width="50%"
|
||||
:modal="false"
|
||||
:show-close="false"
|
||||
append-to-body
|
||||
:close-on-click-modal="false"
|
||||
:before-close="handleClose"
|
||||
>
|
||||
<div slot="title" class="dialogHeader">
|
||||
<div class="icon">
|
||||
<i class="el-icon-minus pointer" @click="handleClose" />
|
||||
</div>
|
||||
</div>
|
||||
<div class="dialogBody">
|
||||
<div v-show="false" class="leftBox">
|
||||
<div class="leftLogo">
|
||||
<img :src="logoImgUrl" :alt="logoImgUrl">
|
||||
</div>
|
||||
<div v-for="(item, index) in tabs" :key="index" class="tab pointer" :class="{active: index === tabActive}" @click="tabsClick(index)">
|
||||
<i :class="item.icon" />
|
||||
<div class="tabLabel">{{ item.label }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div v-if="tabActive==0" class="content">
|
||||
<div class="middle">
|
||||
<div class="middleTop">
|
||||
<div v-for="(item, index) in filterTab" :key="index" class="filterType pointer" :class="{active: index === filterActive}" @click="filterClick(index)">
|
||||
<div class="filterLabel">{{ item.label }}</div>
|
||||
<div class="activeLine" />
|
||||
</div>
|
||||
<div class="nullDiv" />
|
||||
<div class="editFilter pointer">
|
||||
<i class="el-icon-plus" />
|
||||
<!-- <i class="el-icon-more" /> -->
|
||||
</div>
|
||||
</div>
|
||||
<div class="middleMain">
|
||||
<div v-for="(item, index) in groupList" :key="index" class="row pointer" :class="{active: item.id === groupIdActive}" @click="groupClick(item)">
|
||||
<div class="groupIcon"><img :src="getImgUrl(item.imageUrl)" alt=""></div>
|
||||
<div class="groupInfo">
|
||||
<div class="text"><b>{{ item.name }}</b></div>
|
||||
<div class="text">{{ item.message }}</div>
|
||||
</div>
|
||||
<div class="groupMarke">
|
||||
<div class="time">{{ item.time }}</div>
|
||||
<i v-if="item.isMute" class="el-icon-close-notification" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="right">消息</div>
|
||||
</div>
|
||||
<div v-else-if="tabActive==1">文档</div>
|
||||
<div v-else-if="tabActive==2">工作台</div>
|
||||
<div v-else-if="tabActive==3">通讯录</div>
|
||||
</div>
|
||||
</el-dialog>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import {mapGetters} from 'vuex';
|
||||
import { getGroupList } from '@/api/newChat';
|
||||
export default {
|
||||
name: '',
|
||||
components: {
|
||||
|
||||
},
|
||||
props: {
|
||||
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
logoImgUrl: '',
|
||||
dialogVisible: false,
|
||||
tabs: [
|
||||
{label:'消息', icon:'el-icon-chat-dot-square'},
|
||||
{label:'文档', icon:'el-icon-document'},
|
||||
{label:'工作台', icon:'el-icon-menu'},
|
||||
{label:'通讯录', icon:'el-icon-notebook-1'}
|
||||
],
|
||||
tabActive: 0,
|
||||
filterTab: [
|
||||
{label: '全部', value: ''}
|
||||
// {label: '未读', value: ''},
|
||||
// {label: '@我', value: ''},
|
||||
// {label: '单聊', value: ''},
|
||||
// {label: '群聊', value: ''}
|
||||
],
|
||||
filterActive: 0,
|
||||
groupList: [
|
||||
{name: '分公司领导', imageUrl: '', time: '15:36', message: '控制中心消息:【I 类】'},
|
||||
{name: '集团公司', imageUrl: '', time: '04-17', message: '【演练结束】2号线二期:14:58 Y04列车演练结束', isMute: true}
|
||||
],
|
||||
groupIdActive: 0
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
...mapGetters('projectConfig', ['loginProLogo']),
|
||||
groupId() {
|
||||
return this.$route.query.group;
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
'$store.state.socket.conversationGroup': function(val) {
|
||||
if (val) {
|
||||
console.log('🚀 ~ file: chatDialog.vue:110 ~ val:', val);
|
||||
|
||||
}
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
},
|
||||
created() {
|
||||
this.getBaseInfo();
|
||||
this.getGroupList();
|
||||
},
|
||||
beforeDestroy() {
|
||||
this.handleClose();
|
||||
},
|
||||
methods: {
|
||||
getGroupList() {
|
||||
getGroupList(this.groupId).then(res => {
|
||||
console.log(res, '---res--');
|
||||
this.groupList = res.data;
|
||||
if (this.groupList && this.groupList[0].id) {
|
||||
this.groupIdActive = this.groupList[0].id;
|
||||
}
|
||||
}).catch(err => {
|
||||
console.log(err, '---获取群组列表失败--');
|
||||
});
|
||||
},
|
||||
getImgUrl(url) {
|
||||
return url ? this.$store.state.user.ossUrl + '/conversationGroup/' + url : '';
|
||||
},
|
||||
getBaseInfo() {
|
||||
this.logoImgUrl = this.$store.state.user.ossUrl + '/logo/' + this.loginProLogo;
|
||||
},
|
||||
tabsClick(index) {
|
||||
this.tabActive = index;
|
||||
},
|
||||
filterClick(index) {
|
||||
this.filterActive = index;
|
||||
},
|
||||
groupClick(item) {
|
||||
console.log('🚀 ~ file: chatDialog.vue:149 ~ groupClick ~ item:', item);
|
||||
this.groupIdActive = item.id;
|
||||
},
|
||||
handleClose() {
|
||||
this.$store.dispatch('training/setChatBoxMin', true);
|
||||
this.dialogVisible = false;
|
||||
}
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang='scss'>
|
||||
.chatDialog{
|
||||
pointer-events: none !important;
|
||||
.el-dialog__header,
|
||||
.el-dialog__body {
|
||||
padding: 0px;
|
||||
pointer-events: all !important;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
<style lang='scss' scoped>
|
||||
.chatDialog {
|
||||
.pointer {
|
||||
cursor: pointer;
|
||||
}
|
||||
.dialogHeader {
|
||||
padding: 5px 10px;
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
align-items: center;
|
||||
background: #0076F6;
|
||||
.icon {
|
||||
color: #fff;
|
||||
}
|
||||
}
|
||||
.dialogBody {
|
||||
display: flex;
|
||||
height: 600px;
|
||||
.leftBox {
|
||||
background: #ddd;
|
||||
width: 70px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
.leftLogo {
|
||||
width: 53px;
|
||||
height: 53px;
|
||||
padding: 5px;
|
||||
margin: 5px 0;
|
||||
img {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
.tab {
|
||||
width: 53px;
|
||||
height: 53px;
|
||||
margin: 5px 0;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
border-radius: 5px;
|
||||
&:hover {
|
||||
background: #ccc;
|
||||
}
|
||||
i {
|
||||
font-size: 26px;
|
||||
}
|
||||
.tabLabel {
|
||||
font-size: 12px;
|
||||
margin-top: 5px;
|
||||
}
|
||||
}
|
||||
.active {
|
||||
background: #aaa;
|
||||
color: blue;
|
||||
}
|
||||
}
|
||||
.content {
|
||||
display: flex;
|
||||
flex: 1;
|
||||
.middle {
|
||||
width: 280px;
|
||||
padding: 5px;
|
||||
.middleTop {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
padding: 3px;
|
||||
border-bottom: 1px solid #ccc;
|
||||
.filterType {
|
||||
padding: 3px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-direction: column;
|
||||
.filterLabel {
|
||||
padding: 3px;
|
||||
}
|
||||
.activeLine {
|
||||
width: 60%;
|
||||
height: 1px;
|
||||
border: 1px solid #fff;
|
||||
}
|
||||
}
|
||||
.active {
|
||||
.filterLabel {
|
||||
font-weight: bold;
|
||||
}
|
||||
.activeLine {
|
||||
border: 1px solid #aaa;
|
||||
}
|
||||
}
|
||||
.nullDiv {
|
||||
flex: 1;
|
||||
}
|
||||
}
|
||||
.middleMain {
|
||||
overflow-y: auto;
|
||||
height: calc(100% - 40px);
|
||||
.row {
|
||||
padding: 5px;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
border-radius: 5px;
|
||||
&:hover {
|
||||
background: #ddd;
|
||||
}
|
||||
.groupIcon {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
img {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
.groupInfo {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
flex: 1;
|
||||
overflow: hidden;
|
||||
.text {
|
||||
height: 22px;
|
||||
padding: 3px 5px;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
}
|
||||
.groupMarke {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
.time, i {
|
||||
padding: 3px 0px;
|
||||
justify-content: center;
|
||||
}
|
||||
.time {
|
||||
justify-content: flex-end;
|
||||
}
|
||||
}
|
||||
}
|
||||
.active {
|
||||
background: #ccc;
|
||||
}
|
||||
}
|
||||
}
|
||||
.right {
|
||||
flex: 1;
|
||||
background: #ddd;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
64
src/views/newMap/display/newChat/index.vue
Normal file
64
src/views/newMap/display/newChat/index.vue
Normal file
@ -0,0 +1,64 @@
|
||||
<template>
|
||||
<div v-quickMenuDrag class="voice-chat-box">
|
||||
<div v-if="chatBoxMin" :id="sideButtonDom.domId" @click="clickBtn">
|
||||
<el-button circle style="color: #0C161A;" icon="el-icon-mic" />
|
||||
</div>
|
||||
<chatDialog ref="chatDialog" />
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { OperationEvent } from '@/scripts/cmdPlugin/OperationHandler';
|
||||
import {UserOperationType} from '@/scripts/ConstDic';
|
||||
import chatDialog from './chatDialog';
|
||||
export default {
|
||||
name: 'ChatBox',
|
||||
components: {
|
||||
chatDialog
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
};
|
||||
},
|
||||
computed:{
|
||||
chatBoxMin() {
|
||||
return this.$store.state.training.chatBoxMin;
|
||||
},
|
||||
sideButtonDom() {
|
||||
return OperationEvent.Conversation.Chat.sideButton;
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
},
|
||||
mounted() {
|
||||
},
|
||||
methods: {
|
||||
clickBtn() {
|
||||
const operate = {
|
||||
operation: this.sideButtonDom.operation,
|
||||
param: { chatBoxMin: this.chatBoxMin },
|
||||
userOperationType: UserOperationType.LEFTCLICK
|
||||
};
|
||||
this.$store.dispatch('training/setChatBoxMin', false);
|
||||
this.$refs.chatDialog.dialogVisible = true;
|
||||
if (this.$store.state.trainingNew.trainingSwitch) {
|
||||
this.$nextTick(() => {
|
||||
this.$store.dispatch('trainingNew/next', operate);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.voice-chat-box {
|
||||
position: absolute;
|
||||
left: 20px;
|
||||
bottom: 50%;
|
||||
height: 1px;
|
||||
width: 1px;
|
||||
z-index: 2000;
|
||||
}
|
||||
</style>
|
||||
|
@ -303,6 +303,123 @@
|
||||
<el-button size="small" type="primary" @click="keyClear">一键清空</el-button>
|
||||
</div>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane class="view-control" label="会话群" name="six" :lazy="lazy">
|
||||
<el-tabs v-model="conversationActive" class="card" style="height: 100%">
|
||||
<el-tab-pane class="view-control" label="地铁CBTC" name="METRO">
|
||||
<div style="height: 100%;overflow-y: auto;padding: 5px;">
|
||||
<el-row :gutter="5" style="margin-bottom: 5px;">
|
||||
<el-col :span="4"><div style="text-align: center;font-size: 14px;">群名称</div></el-col>
|
||||
<el-col :span="4"><div style="text-align: center;font-size: 14px;">群头像</div></el-col>
|
||||
<el-col :span="5"><div style="text-align: center;font-size: 14px;">群主</div></el-col>
|
||||
<el-col :span="8"><div style="text-align: center;font-size: 14px;">成员</div></el-col>
|
||||
<el-col :span="3"><div style="text-align: center;font-size: 14px;">操作</div></el-col>
|
||||
</el-row>
|
||||
<el-row v-for="(item, index) in conversationMetroList" :key="index" :gutter="5" class="conversationRow">
|
||||
<el-col :span="4">
|
||||
<el-input v-model="item.name" size="mini" />
|
||||
</el-col>
|
||||
<el-col :span="4">
|
||||
<div class="uploadImgDiv">
|
||||
<img v-if="item.imageUrl" :src="getImgUrl(item.imageUrl)" :alt="getImgUrl(item.imageUrl)">
|
||||
<i class="el-icon-plus" />
|
||||
<input :id="'upload_file_METRO' + index" ref="files" type="file" class="input_file_box" accept="image/jpeg,image/png" @change="uploadLogo('METRO', index)">
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="5">
|
||||
<el-select v-model="item.leaderId" placeholder="请选择" size="mini">
|
||||
<el-option v-for="elem in memberMetroList" :key="elem.id" :label="getLabel(elem)" :value="elem.id" />
|
||||
</el-select>
|
||||
</el-col>
|
||||
<el-col :span="8">
|
||||
<el-select v-model="item.memberIds" multiple collapse-tags placeholder="请选择" size="mini">
|
||||
<el-option v-for="elem in memberMetroList" :key="elem.id" :label="getLabel(elem)" :value="elem.id" />
|
||||
</el-select>
|
||||
</el-col>
|
||||
<el-col :span="3" style="text-align: center;">
|
||||
<el-button type="primary" size="mini" @click="deleteConversation(index, 'METRO')">删除</el-button>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</div>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane class="view-control" label="大铁CTC" name="RAILWAY">
|
||||
<div style="height: 100%;overflow-y: auto;padding: 5px;">
|
||||
<el-row :gutter="5" style="margin-bottom: 5px;">
|
||||
<el-col :span="4"><div style="text-align: center;font-size: 14px;">群名称</div></el-col>
|
||||
<el-col :span="4"><div style="text-align: center;font-size: 14px;">群头像</div></el-col>
|
||||
<el-col :span="5"><div style="text-align: center;font-size: 14px;">群主</div></el-col>
|
||||
<el-col :span="8"><div style="text-align: center;font-size: 14px;">成员</div></el-col>
|
||||
<el-col :span="3"><div style="text-align: center;font-size: 14px;">操作</div></el-col>
|
||||
</el-row>
|
||||
<el-row v-for="(item, index) in conversationRailwayList" :key="index" :gutter="5" class="conversationRow">
|
||||
<el-col :span="4">
|
||||
<el-input v-model="item.name" size="mini" />
|
||||
</el-col>
|
||||
<el-col :span="4">
|
||||
<div class="uploadImgDiv">
|
||||
<img v-if="item.imageUrl" :src="getImgUrl(item.imageUrl)" :alt="getImgUrl(item.imageUrl)">
|
||||
<i class="el-icon-plus" />
|
||||
<input :id="'upload_file_RAILWAY' + index" ref="files" type="file" class="input_file_box" accept="image/jpeg,image/png" @change="uploadLogo('RAILWAY', index)">
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="5">
|
||||
<el-select v-model="item.leaderId" placeholder="请选择" size="mini">
|
||||
<el-option v-for="elem in memberRailwayList" :key="elem.id" :label="getLabel(elem)" :value="elem.id" />
|
||||
</el-select>
|
||||
</el-col>
|
||||
<el-col :span="8">
|
||||
<el-select v-model="item.memberIds" multiple collapse-tags placeholder="请选择" size="mini">
|
||||
<el-option v-for="elem in memberRailwayList" :key="elem.id" :label="getLabel(elem)" :value="elem.id" />
|
||||
</el-select>
|
||||
</el-col>
|
||||
<el-col :span="3" style="text-align: center;">
|
||||
<el-button type="primary" size="mini" @click="deleteConversation(index, 'RAILWAY')">删除</el-button>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</div>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane class="view-control" label="应急调度" name="EMERGENCY">
|
||||
<div style="height: 100%;overflow-y: auto;padding: 5px;">
|
||||
<el-row :gutter="5" style="margin-bottom: 5px;">
|
||||
<el-col :span="4"><div style="text-align: center;font-size: 14px;">群名称</div></el-col>
|
||||
<el-col :span="4"><div style="text-align: center;font-size: 14px;">群头像</div></el-col>
|
||||
<el-col :span="5"><div style="text-align: center;font-size: 14px;">群主</div></el-col>
|
||||
<el-col :span="8"><div style="text-align: center;font-size: 14px;">成员</div></el-col>
|
||||
<el-col :span="3"><div style="text-align: center;font-size: 14px;">操作</div></el-col>
|
||||
</el-row>
|
||||
<el-row v-for="(item, index) in conversationEmergencyList" :key="index" :gutter="5" class="conversationRow">
|
||||
<el-col :span="4">
|
||||
<el-input v-model="item.name" size="mini" />
|
||||
</el-col>
|
||||
<el-col :span="4">
|
||||
<div class="uploadImgDiv">
|
||||
<img v-if="item.imageUrl" :src="getImgUrl(item.imageUrl)" :alt="getImgUrl(item.imageUrl)">
|
||||
<i class="el-icon-plus" />
|
||||
<input :id="'upload_file_EMERGENCY' + index" ref="files" type="file" class="input_file_box" accept="image/jpeg,image/png" @change="uploadLogo('EMERGENCY', index)">
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="5">
|
||||
<el-select v-model="item.leaderId" placeholder="请选择" size="mini">
|
||||
<el-option v-for="elem in memberEmergencyList" :key="elem.id" :label="getLabel(elem)" :value="elem.id" />
|
||||
</el-select>
|
||||
</el-col>
|
||||
<el-col :span="8">
|
||||
<el-select v-model="item.memberIds" multiple collapse-tags placeholder="请选择" size="mini">
|
||||
<el-option v-for="elem in memberEmergencyList" :key="elem.id" :label="getLabel(elem)" :value="elem.id" />
|
||||
</el-select>
|
||||
</el-col>
|
||||
<el-col :span="3" style="text-align: center;">
|
||||
<el-button type="primary" size="mini" @click="deleteConversation(index, 'EMERGENCY')">删除</el-button>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</div>
|
||||
</el-tab-pane>
|
||||
</el-tabs>
|
||||
<div class="button_box">
|
||||
<el-button-group class="map-draft-group">
|
||||
<el-button type="primary" size="small" @click="createConversation">新建会话群</el-button>
|
||||
</el-button-group>
|
||||
</div>
|
||||
</el-tab-pane>
|
||||
</el-tabs>
|
||||
</template>
|
||||
|
||||
@ -310,6 +427,7 @@
|
||||
import {mapGetters} from 'vuex';
|
||||
import { getDisStationList } from '@/api/disStation';
|
||||
import ConstConfig from '@/scripts/ConstConfig';
|
||||
import { getUploadUrl } from '@/api/projectConfig';
|
||||
export default {
|
||||
name: 'SimulationMember',
|
||||
data() {
|
||||
@ -317,6 +435,7 @@ export default {
|
||||
lazy: true,
|
||||
activeName: 'first',
|
||||
memberActive: 'METRO',
|
||||
conversationActive: 'METRO',
|
||||
roleList: ConstConfig.ConstSelect.roleTypeList,
|
||||
systemList: [
|
||||
{ label: '地铁CBTC', value: 'METRO' },
|
||||
@ -377,6 +496,15 @@ export default {
|
||||
},
|
||||
memberEmergencyList() {
|
||||
return this.$store.state.map.map.memberMap.EMERGENCY;
|
||||
},
|
||||
conversationMetroList() {
|
||||
return this.$store.state.map.map.conversationGroupMap.METRO;
|
||||
},
|
||||
conversationRailwayList() {
|
||||
return this.$store.state.map.map.conversationGroupMap.RAILWAY;
|
||||
},
|
||||
conversationEmergencyList() {
|
||||
return this.$store.state.map.map.conversationGroupMap.EMERGENCY;
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
@ -386,6 +514,79 @@ export default {
|
||||
this.initDisStationList();
|
||||
},
|
||||
methods: {
|
||||
getImgUrl(url) {
|
||||
return url ? this.$store.state.user.ossUrl + '/conversationGroup/' + url : '';
|
||||
},
|
||||
getLabel(obj) {
|
||||
let name = '';
|
||||
const findType = this.roleList.find(item => {
|
||||
return item.value == obj.type;
|
||||
});
|
||||
if (findType) {
|
||||
name += findType.label;
|
||||
}
|
||||
name += '-';
|
||||
if (obj.type == 'DISPATCHER') {
|
||||
const findDeviceCode = this.disStationList.find(item => {
|
||||
return item.code == obj.deviceCode;
|
||||
});
|
||||
if (findDeviceCode) {
|
||||
name += findDeviceCode.name;
|
||||
}
|
||||
} else if (obj.type == 'DRIVER') {
|
||||
const findDeviceCode = this.trainList.find(item => {
|
||||
return item.groupNumber == obj.deviceCode;
|
||||
});
|
||||
if (findDeviceCode) {
|
||||
name += findDeviceCode.groupNumber;
|
||||
}
|
||||
} else {
|
||||
const findDeviceCode = this.stationList.find(item => {
|
||||
return item.code == obj.deviceCode;
|
||||
});
|
||||
if (findDeviceCode) {
|
||||
name += findDeviceCode.name;
|
||||
}
|
||||
}
|
||||
return name;
|
||||
},
|
||||
deleteConversation(index, type) {
|
||||
const conversationMap = { METRO: this.conversationMetroList, RAILWAY: this.conversationRailwayList, EMERGENCY: this.conversationEmergencyList };
|
||||
if (conversationMap[this.conversationActive]) {
|
||||
conversationMap[this.conversationActive].splice(index, 1);
|
||||
}
|
||||
},
|
||||
createConversation() {
|
||||
const list = [];
|
||||
this.conversationMetroList.forEach(item => {
|
||||
if (item.id) {
|
||||
list.push(item.id);
|
||||
}
|
||||
});
|
||||
this.conversationRailwayList.forEach(item => {
|
||||
if (item.id) {
|
||||
list.push(item.id);
|
||||
}
|
||||
});
|
||||
this.conversationEmergencyList.forEach(item => {
|
||||
if (item.id) {
|
||||
list.push(item.id);
|
||||
}
|
||||
});
|
||||
const maxNum = list.length ? Math.max(...list) : 0;
|
||||
const obj = {
|
||||
id: maxNum + 1,
|
||||
name: '',
|
||||
imageUrl: '',
|
||||
leaderId: '',
|
||||
memberIds: []
|
||||
};
|
||||
console.log('🚀 ~ file: index.vue:584 ~ createConversation ~ obj:', obj);
|
||||
const conversationMap = { METRO: this.conversationMetroList, RAILWAY: this.conversationRailwayList, EMERGENCY: this.conversationEmergencyList };
|
||||
if (conversationMap[this.conversationActive]) {
|
||||
conversationMap[this.conversationActive].push(obj);
|
||||
}
|
||||
},
|
||||
initDisStationList() {
|
||||
getDisStationList(this.$route.params.mapId).then(resp => {
|
||||
this.disStationList = resp.data || [];
|
||||
@ -836,11 +1037,94 @@ export default {
|
||||
keyClear() {
|
||||
const memberMap = { METRO: this.memberMetroList, RAILWAY: this.memberRailwayList, EMERGENCY: this.memberEmergencyList };
|
||||
memberMap[this.clearForm.systemType].splice(0, memberMap[this.clearForm.systemType].length);
|
||||
},
|
||||
uploadLogo(type, index) {
|
||||
const pic = document.getElementById('upload_file_' + type + index);
|
||||
if (!pic.files || !pic.files[0]) {
|
||||
return;
|
||||
}
|
||||
const file = pic.files[0];
|
||||
const mineType = file.type;
|
||||
const fileSize = file.size;
|
||||
if (mineType != 'image/png' && mineType != 'image/jpeg') {
|
||||
this.$message.error('仅支持png和jpeg格式的图片');
|
||||
return;
|
||||
}
|
||||
if (fileSize / (1024 * 1024) > 1) {
|
||||
this.$message.error('图片应该小于1M');
|
||||
return;
|
||||
}
|
||||
const fileArray = file.name.split('.');
|
||||
const fileType = fileArray[fileArray.length - 1] || '';
|
||||
if (!fileType) {
|
||||
return;
|
||||
}
|
||||
const params = {
|
||||
directory:'conversationGroup',
|
||||
fileName:'group_' + Math.floor(Math.random() * 1000000) + '.' + fileType,
|
||||
method:'PUT'
|
||||
};
|
||||
const conversationMap = { METRO: this.conversationMetroList, RAILWAY: this.conversationRailwayList, EMERGENCY: this.conversationEmergencyList };
|
||||
const that = this;
|
||||
getUploadUrl(params).then((response) => {
|
||||
const url = response.data;
|
||||
if (url) {
|
||||
const xhr = new XMLHttpRequest();
|
||||
xhr.open('PUT', url);
|
||||
xhr.setRequestHeader('Content-Type', 'multipart/form-data');
|
||||
xhr.send(file);
|
||||
xhr.onreadystatechange = function() {
|
||||
if (xhr.readyState === 4 && xhr.status == 200) {
|
||||
if (conversationMap[type] && conversationMap[type][index]) {
|
||||
conversationMap[type][index].imageUrl = params.fileName;
|
||||
}
|
||||
} else if (xhr.status != 200) {
|
||||
that.$message.error('上传失败,请稍后再试');
|
||||
}
|
||||
};
|
||||
}
|
||||
});
|
||||
|
||||
// 参数:directory:MINIO文件夹
|
||||
// fileName:存储文件名
|
||||
// method:生成链接的请求方式
|
||||
}
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
$imgWidth: 70px;
|
||||
$imgHeight: 70px;
|
||||
.conversationRow {
|
||||
margin-bottom: 5px;
|
||||
line-height: $imgHeight;
|
||||
}
|
||||
.uploadImgDiv {
|
||||
margin: 0 auto;
|
||||
width: $imgWidth;
|
||||
height: $imgHeight;
|
||||
border: 1px #ccc dashed;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
cursor: pointer;
|
||||
img {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
i{
|
||||
width: 100%;
|
||||
text-align: center;
|
||||
line-height: $imgHeight;
|
||||
}
|
||||
.input_file_box {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
opacity: 0;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
Loading…
Reference in New Issue
Block a user