import dayjs from "dayjs"; const app = getApp(); interface IMessageItem { msgId: string; contentType: "1" | "2" | "3" | "4" | "5"; // 1:文本 2: 语音 3. 图片 4. 视频 5. 提示信息 content: any; fromDoctorId: string; doctorImg: string; createTime: string; createTimeName?: string; isSelf: 1 | 2; isRead: 1 | 2; doctorName: string; hospitalName: string; showTime?: boolean; isPlay?: boolean; uniqueCode?: string; } Page({ data: { id: "", show1: false, focus: false, fold: true, scrollTop: 0, scrollIntoView: "", doctorDetail: {} as any, roomDoctors: [], newRoomDoctors: [], case: {} as any, chatGroupInfo: {} as any, chatDoctor: {} as any, isLoad: false, isFinish: false, messageList: [] as IMessageItem[], lastMsgId: "", unReadCount: 0, userInfo: {} as any, sendMessage: "", videoUrl: "", protocol: `

罕心守护平台向用户提供了“聊天室”功能,基于此服务,我们在此特别声明:

罕心守护平台非常重视您的个人信息保护及平台信息的隐私性,您同意在聊天室功能使用时遵守以下规则:

1.严禁在聊天室内讨论或分享任何患者的个人身份信息,包括但不限于姓名、性别等。群内发送的任何素材内容,必须去除所有可能识别患者身份的敏感信息;

2.不以截图、录音或以任何形式将内容传播;

3.讨论内容仅限于专业交流,不得用于任何商业目的。

4.保持讨论的专业性和尊重性,避免使用侮辱性或攻击性语言。


`, }, innerAudioContext: null as WechatMiniprogram.InnerAudioContext | null, videoContext: null as WechatMiniprogram.VideoContext | null, onLoad(options) { this.setData({ id: options.id, }); this.videoContext = wx.createVideoContext("video"); this.innerAudioContext = wx.createInnerAudioContext({ useWebAudioImplement: true, }); app.waitLogin().then(() => { this.getAgree(); app.getUserInfo(this); }); }, onUnload() { wx.WebIM.conn.close(); if (this.innerAudioContext) { this.innerAudioContext.stop(); } if (this.videoContext) { this.videoContext.stop(); } }, init() { this.getMessageList(); this.getDetail(); }, getAgree() { wx.ajax({ method: "GET", url: "?r=takeda/account/chat-room-notice", data: { roomId: this.data.id, }, }).then((res) => { this.setData({ show1: res.show === 1, }); if (res.show !== 1) { this.init(); } }); }, onAgreeClose() { wx.navigateBack(); }, handleSubmitAgree() { wx.ajax({ method: "POST", url: "?r=takeda/account/close-chat-room-notice", data: {}, }).then(() => { this.setData({ show1: false, }); this.init(); }); }, getDetail() { wx.ajax({ method: "GET", url: "?r=takeda/chat/get-room-detail", data: { roomId: this.data.id }, }).then((res) => { this.setData({ roomDoctors: res.roomDoctors, newRoomDoctors: res.roomDoctors.slice(0, 4), case: res.case, chatGroupInfo: res.chatGroupInfo, chatDoctor: res.chatDoctor, }); wx.setNavigationBarTitle({ title: `聊天室(${res.roomDoctors.length})`, }); this.WebIMLogin(); }); }, handleRoomDetail() { wx.navigateTo({ url: `/module1/pages/chatRoomInfo/index?id=${this.data.id}&cid=${this.data.case.caseId}`, }); }, handleCaseDetail() { wx.navigateTo({ url: `/module1/pages/casesDetail/index?id=${this.data.case.caseId}`, }); }, handleView(index = -1) { const time = setTimeout(() => { this.setData({ scrollIntoView: index > -1 ? `view${index}` : `place`, }); clearTimeout(time); }, 300); }, getMessageList() { if (this.data.isLoad || this.data.isFinish) return; this.setData({ isLoad: true, }); const lastMsgId = this.data.lastMsgId; wx.ajax({ method: "GET", url: "?r=takeda/chat/get-message-list", data: { lastMsgId, roomId: this.data.id, }, }).then((res) => { if (res.length === 0) { this.setData({ isFinite: true, }); return; } res.map((item) => { return this.formatMessage(item); }); this.setData({ messageList: [...res.reverse(), ...this.data.messageList], lastMsgId: res[0].msgId, isLoad: false, }); this.filterCreateTime(); this.handleView(); }); }, scrolltoupper(e) { if (e.detail.direction === "top") { this.getMessageList(); } }, handleSendMessage() { const { sendMessage, userInfo } = this.data; if (!sendMessage) { wx.showToast({ icon: "none", title: "请输入内容", }); return; } const message: IMessageItem = { msgId: "", contentType: "1", content: sendMessage, fromDoctorId: userInfo.DoctorId, createTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), isSelf: 1, isRead: 2, doctorImg: userInfo.Img, doctorName: userInfo.Name, hospitalName: userInfo.HospitalName, }; this.setData({ sendMessage: "", }); this.WebIMSendMessage(message); }, handleSendAudio(e) { const { userInfo } = this.data; const contentStr = JSON.stringify({ url: e.detail.fileUrl, duration: e.detail.duration, }); const message: IMessageItem = { msgId: "", contentType: "2", content: contentStr, fromDoctorId: userInfo.DoctorId, createTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), isSelf: 1, isRead: 2, doctorImg: userInfo.Img, doctorName: userInfo.Name, hospitalName: userInfo.HospitalName, }; this.WebIMSendMessage(message); }, handleSendPhoto(e) { const { userInfo } = this.data; const contentStr = JSON.stringify({ url: e.detail.fileUrl, }); const message: IMessageItem = { msgId: "", contentType: "3", content: contentStr, fromDoctorId: userInfo.DoctorId, createTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), isSelf: 1, isRead: 2, doctorImg: userInfo.Img, doctorName: userInfo.Name, hospitalName: userInfo.HospitalName, }; this.WebIMSendMessage(message); }, handleSendVideo(e) { const { userInfo } = this.data; const contentStr = JSON.stringify({ url: e.detail.fileUrl, imgUrl: e.detail.imgUrl, }); const message: IMessageItem = { msgId: "", contentType: "4", content: contentStr, fromDoctorId: userInfo.DoctorId, createTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), isSelf: 1, isRead: 2, doctorImg: userInfo.Img, doctorName: userInfo.Name, hospitalName: userInfo.HospitalName, }; this.WebIMSendMessage(message); }, sendMessage({ uniqueCode, ...message }) { wx.ajax({ method: "POST", url: "?r=takeda/chat/send-message", data: { roomId: this.data.id, message: { contentType: message.contentType, content: message.content, uniqueCode, }, }, }); }, WebIMLogin() { const { chatDoctor } = this.data; wx.WebIM.conn .open({ user: chatDoctor.chatUserId, pwd: chatDoctor.chatUserPwd, }) .then(() => { this.listenMessage(); }); }, WebIMSendMessage(message: IMessageItem) { const { chatGroupInfo } = this.data; const option = { type: "txt", msg: message.content, to: chatGroupInfo.ChatGroupId, chatType: "groupChat", deliverOnlineOnly: "true", ext: { ...message, }, }; const msg = wx.WebIM.message.create(option); wx.WebIM.conn .send(msg) .then((res) => { this.sendMessage({ ...message, uniqueCode: res.serverMsgId }); this.setData({ messageList: [...this.data.messageList, this.formatMessage(message)], }); this.handleView(); }) .catch(() => { wx.showToast({ icon: "none", title: "发送失败", }); }); }, listenMessage() { const { chatGroupInfo } = this.data; wx.WebIM.conn.addEventHandler("room", { onTextMessage: (message) => { if (message.error) { return; } if (message.to === chatGroupInfo.ChatGroupId) { this.setData({ messageList: [ ...this.data.messageList, this.formatMessage({ ...message.ext, isSelf: 2, }), ], }); this.handleReadAll(); this.handleView(); } }, }); }, formatMessage(message: IMessageItem) { //消息内容类型,1-文本,2-语音,3-图片,4-视频,5-提示信息 if (["2", "3", "4"].includes(message.contentType)) { message.content = JSON.parse(message.content); } return message; }, formatTime(date: string) { let createTimeName = ""; if (dayjs().format("YYYY-MM-DD") === dayjs(date).format("YYYY-MM-DD")) { createTimeName = dayjs(date).format("HH:mm"); } else if (dayjs().format("YYYY-MM-DD") === dayjs(date).add(1, "day").format("YYYY-MM-DD")) { createTimeName = `昨天 ${dayjs(date).format("HH:mm")}`; } else if (dayjs().diff(date, "day") < 7) { createTimeName = dayjs(date).format(`dddd HH:mm`); } else { createTimeName = dayjs(date).format("YYYY-MM-DD HH:mm"); } return createTimeName; }, filterCreateTime() { const gapTime = 5 * 60 * 1000; const { messageList } = this.data; let preTime = 0; messageList.forEach((item, index) => { if (index === 0) { item.showTime = true; preTime = dayjs(item.createTime).valueOf(); item.createTimeName = this.formatTime(item.createTime); } else { const curTime = dayjs(item.createTime).valueOf(); if (curTime - preTime > gapTime) { item.showTime = true; item.createTimeName = this.formatTime(item.createTime); preTime = dayjs(item.createTime).valueOf(); } } }); this.setData({ messageList, }); }, handleFooter() { this.setData({ fold: !this.data.fold, }); if (!this.data.fold) { this.handleView(); } }, handleAudio(e) { const { index } = e.currentTarget.dataset; const { messageList } = this.data; const messageItem = messageList[index]; const { url } = messageItem.content; if (this.innerAudioContext) { if (messageItem.isPlay) { this.innerAudioContext.stop(); messageItem.isPlay = false; this.setData({ messageList, }); return; } this.innerAudioContext.stop(); this.innerAudioContext.src = url; this.innerAudioContext.play(); messageItem.isPlay = true; if (messageItem.isRead === 2 && messageItem.isSelf === 2) { messageItem.isRead = 1; this.handleReadAudio({ msgId: messageItem.msgId, uniqueCode: messageItem.uniqueCode, }); } this.innerAudioContext.onEnded(() => { messageItem.isPlay = false; this.setData({ messageList, }); }); this.setData({ messageList, }); } }, handleReadAudio({ msgId, uniqueCode }) { wx.ajax({ method: "POST", url: "?r=takeda/chat/read-message", data: { roomId: this.data.id, msgId, uniqueCode, }, }); }, handlePreview(e) { const { url } = e.currentTarget.dataset; wx.previewImage({ urls: [url], }); }, handleVideo(e) { const { url } = e.currentTarget.dataset; if (this.videoContext) { this.setData({ videoUrl: url, }); this.videoContext.play(); this.videoContext.requestFullScreen({}); } }, handleReadAll() { wx.ajax({ method: "POST", url: "?r=takeda/chat/read-all-message", data: { roomId: this.data.id }, }); }, handleFocus() { this.setData({ focus: true, }); }, handleBlur() { this.setData({ focus: false, }); }, });