mirror of
https://github.com/LC044/WeChatMsg
synced 2024-11-15 14:31:18 +08:00
443 lines
16 KiB
Python
443 lines
16 KiB
Python
# -*- coding: utf-8 -*-
|
||
"""
|
||
@File : Group.py
|
||
@Author : Shuaikang Zhou
|
||
@Time : 2022/12/20 20:26
|
||
@IDE : Pycharm
|
||
@Version : Python3.10
|
||
@comment : ···
|
||
"""
|
||
import datetime
|
||
import json
|
||
|
||
from .GroupUi import *
|
||
from PyQt5.QtGui import *
|
||
from PyQt5.QtWidgets import *
|
||
from PyQt5.QtCore import *
|
||
from ....DB import data
|
||
import time
|
||
# from .chat import MainWinController
|
||
from .create_groupUi import Ui_Frame
|
||
from .CreateGroup import CreateGroupView
|
||
from .addGroup import Ui_Frame as Add_GroupUi
|
||
|
||
|
||
class GroupControl(QWidget, Ui_Form):
|
||
backSignal = pyqtSignal(str)
|
||
addSignal = pyqtSignal(int)
|
||
|
||
# createSignal = pyqtSignal(Group)
|
||
|
||
def __init__(self, parent=None, Me=None):
|
||
super(GroupControl, self).__init__(parent)
|
||
self.groups = None
|
||
self.setupUi(self)
|
||
self.Me = Me
|
||
self.btn_create_group.clicked.connect(self.create_group_view)
|
||
self.btn_add_group.clicked.connect(self.addGroupUi)
|
||
self.btn_sendMsg.clicked.connect(self.sendMsg) # 发送信息按钮
|
||
self.btn_del_group.clicked.connect(self.delete_group)
|
||
self.toolButton.clicked.connect(self.about)
|
||
self.frame_ag = QtWidgets.QFrame(self.frame)
|
||
self.frame_ag.setGeometry(QtCore.QRect(0, 0, 800, 720))
|
||
self.frame_ag.setFrameShape(QtWidgets.QFrame.Box)
|
||
self.frame_ag.setFrameShadow(QtWidgets.QFrame.Raised)
|
||
self.frame_ag.setObjectName("frame_cg")
|
||
self.frame_ag.setVisible(False)
|
||
self.addSignal.connect(self.new_groupUi)
|
||
# print(self.username)
|
||
self.groups = {}
|
||
self.last_gid = None
|
||
self.now_gid = None
|
||
self.group_users = None
|
||
self.last_msg_time = datetime.datetime(2022, 12, 19, 15, 4) # 上次信息的时间
|
||
self.initUi()
|
||
|
||
def initUi(self):
|
||
|
||
groups = data.get_groups(self.Me.username)
|
||
self.groups_num = len(groups)
|
||
print('群组:', groups)
|
||
max_hight = max(self.groups_num * 80, 680)
|
||
self.scrollAreaWidgetContents.setGeometry(QtCore.QRect(0, 0, 300, max_hight))
|
||
for i in range(len(groups)):
|
||
group = groups[i]
|
||
# print(contact)
|
||
g_id = group[0]
|
||
print('群聊信息:', group)
|
||
pushButton_2 = OneGroup(self.scrollAreaWidgetContents, group)
|
||
pushButton_2.setGeometry(QtCore.QRect(0, 80 * i, 300, 80))
|
||
pushButton_2.setLayoutDirection(QtCore.Qt.LeftToRight)
|
||
pushButton_2.clicked.connect(pushButton_2.show_msg)
|
||
pushButton_2.gidSingal.connect(self.chat)
|
||
self.groups[g_id] = pushButton_2
|
||
|
||
def chat(self, g_id):
|
||
# self.frame_ag.setVisible(False)
|
||
print('当前聊天群号:', g_id)
|
||
self.frame_msg.setVisible(True)
|
||
self.frame_ag.setVisible(False)
|
||
self.now_gid = g_id
|
||
self.group_users = data.get_group_users(g_id)
|
||
# 将当前群的界面设置为灰色
|
||
# if self.last_gid and self.last_gid != g_id:
|
||
# self.groups[self.last_gid].setStyleSheet("background-color : rgb(253,253,253)")
|
||
# self.last_gid = g_id
|
||
# self.groups[g_id].setStyleSheet("background-color : rgb(198,198,198)")
|
||
g_name = self.groups[g_id].g_name
|
||
self.l_g_name.setText(f'{g_name}({g_id})')
|
||
self.message.clear()
|
||
self.message.append(str(g_id))
|
||
# 创建新的线程用于显示聊天记录
|
||
self.Thread = ChatMsg(self.Me.username, g_id, self.Me.socket)
|
||
self.Thread.isSend_signal.connect(self.showMsg)
|
||
self.Thread.recvSignal.connect(self.showMsg)
|
||
self.Thread.sendSignal.connect(self.showMsg)
|
||
self.Thread.start()
|
||
pass
|
||
|
||
def sendMsg(self, msg):
|
||
"""
|
||
发送信息
|
||
:param msg:信息内容
|
||
:return:
|
||
"""
|
||
msg = self.textEdit.toPlainText()
|
||
message = self.Thread.send_msg(msg)
|
||
if message:
|
||
print(msg, '发送成功')
|
||
# self.showMsg(message)
|
||
else:
|
||
print(msg, '发送失败')
|
||
self.textEdit.clear()
|
||
|
||
def create_group_view(self):
|
||
"""建群界面"""
|
||
self.frame_msg.setVisible(False)
|
||
self.frame_ag.setVisible(False)
|
||
# self.frame_ag.setVisible(True)
|
||
# print(self.Me.__dict__)
|
||
self.create_view = CreateGroupView(username=self.Me.username)
|
||
self.create_view.gidSignal.connect(self.new_groupUi)
|
||
self.create_view.show()
|
||
|
||
def addGroupBack(self):
|
||
"""加群界面"""
|
||
self.frame_msg.setVisible(True)
|
||
self.frame_ag.setVisible(False)
|
||
# self.CG_Ui = None
|
||
|
||
def delete_group(self):
|
||
"""退群"""
|
||
a = QMessageBox.question(self, '警告', '你确定要退群吗?', QMessageBox.Yes | QMessageBox.No,
|
||
QMessageBox.No) # "退出"代表的是弹出框的标题,"你确认退出.."表示弹出框的内容
|
||
if a == QMessageBox.Yes:
|
||
data.delete_group(self.Me.username, self.now_gid)
|
||
self.frame_msg.setVisible(False)
|
||
self.last_gid = None
|
||
self.groups_num -= 1
|
||
self.l_g_name.setText('已退群')
|
||
self.groups[self.now_gid].setVisible(False)
|
||
self.groups.pop(self.now_gid)
|
||
else:
|
||
return
|
||
|
||
def show(self):
|
||
self.message.append('2020303457')
|
||
|
||
def addGroupUi(self):
|
||
"""加群的界面"""
|
||
self.frame_msg.setVisible(False)
|
||
self.CG_Ui = Add_GroupUi()
|
||
self.CG_Ui.setupUi(self.frame_ag)
|
||
self.CG_Ui.back.clicked.connect(self.addGroupBack)
|
||
self.CG_Ui.btn_add.clicked.connect(self.addGroup)
|
||
self.CG_Ui.btn_search.clicked.connect(self.searchGroup)
|
||
self.frame_ag.setVisible(True)
|
||
self.CG_Ui.tips.setVisible(False)
|
||
self.CG_Ui.time.setVisible(False)
|
||
pass
|
||
|
||
def searchGroup(self):
|
||
"""搜索群聊"""
|
||
gid = self.CG_Ui.line_g_id.text()
|
||
if not gid:
|
||
self.CG_Ui.error.setText('请输入群号')
|
||
return False
|
||
nickname = self.CG_Ui.line_nickname.text()
|
||
group = data.search_group(gid)
|
||
if not group:
|
||
self.CG_Ui.error.setText('未找到群聊')
|
||
return False
|
||
avatar = data.get_avator(gid)
|
||
pixmap = QPixmap(avatar).scaled(60, 60) # 按指定路径找到图片
|
||
self.CG_Ui.avatar_img.setPixmap(pixmap) # 在label上显示图片
|
||
return group
|
||
|
||
def addGroup(self):
|
||
"""添加群聊"""
|
||
gid = self.CG_Ui.line_g_id.text()
|
||
gid = int(gid)
|
||
nickname = self.CG_Ui.line_nickname.text()
|
||
flag = data.add_group(self.Me.username, gid, nickname)
|
||
if not flag:
|
||
self.CG_Ui.error.setText('群聊不存在')
|
||
return False
|
||
avatar = data.get_avator(gid)
|
||
pixmap = QPixmap(avatar).scaled(60, 60) # 按指定路径找到图片
|
||
self.CG_Ui.avatar_img.setPixmap(pixmap) # 在label上显示图片
|
||
self.CG_Ui.error.setText('加群成功')
|
||
# self.addSignal.emit(gid)
|
||
self.new_groupUi(gid)
|
||
|
||
def new_groupUi(self, gid):
|
||
nickname = ''
|
||
group = data.search_group(gid)
|
||
if not group:
|
||
return False
|
||
g_name = group[1]
|
||
self.groups_num += 1
|
||
max_hight = max(self.groups_num * 80, 680)
|
||
self.scrollAreaWidgetContents.setGeometry(QtCore.QRect(0, 0, 300, max_hight))
|
||
group = [
|
||
gid, g_name, nickname, 3, 1
|
||
]
|
||
# g_id = group[0]
|
||
print('群聊信息:', group)
|
||
pushButton_2 = OneGroup(self.scrollAreaWidgetContents, group)
|
||
pushButton_2.setGeometry(QtCore.QRect(0, 80 * self.groups_num - 80, 300, 80))
|
||
pushButton_2.setLayoutDirection(QtCore.Qt.LeftToRight)
|
||
pushButton_2.clicked.connect(pushButton_2.show_msg)
|
||
pushButton_2.gidSingal.connect(self.chat)
|
||
# pushButton_2.setVisible(True)
|
||
print('加群成功', gid)
|
||
print(pushButton_2.g_id)
|
||
self.groups[gid] = pushButton_2
|
||
pushButton_2.setVisible(True)
|
||
print(self.groups)
|
||
print(self.now_gid, self.last_gid)
|
||
|
||
def showMsg(self, message):
|
||
"""
|
||
显示聊天消息
|
||
:param message:
|
||
:return:
|
||
"""
|
||
# print(message)
|
||
gid = message[1]
|
||
if self.now_gid is None or gid != self.now_gid:
|
||
return
|
||
# self.now_gid = gid
|
||
talker = message[5]
|
||
isSend = message[6]
|
||
content = message[3]
|
||
msg_time = message[4]
|
||
# print(message)
|
||
# print(msg_time, type(msg_time))
|
||
self.check_time(msg_time)
|
||
if isSend == 1 and talker == self.Me.username:
|
||
# 自己发的信息在右边显示
|
||
self.right(content, talker)
|
||
else:
|
||
# 收到的信息在左边显示
|
||
self.left(content, talker)
|
||
self.message.moveCursor(self.message.textCursor().End)
|
||
|
||
def about(self):
|
||
group = data.search_group(self.now_gid)
|
||
QMessageBox.about(
|
||
self,
|
||
"关于",
|
||
f"关于本群\n群名:{group[1]}\n群号:{self.now_gid}"
|
||
)
|
||
|
||
def check_time(self, msg_time):
|
||
"""
|
||
判断两次聊天时间是否大于五分钟
|
||
超过五分钟就显示时间
|
||
:param msg_time:
|
||
:return:
|
||
"""
|
||
dt = msg_time - self.last_msg_time
|
||
# print(msg_time)
|
||
if dt.seconds >= 300:
|
||
html = '''
|
||
<table align="center" style="vertical-align: middle;">
|
||
<tbody>
|
||
<tr>
|
||
<td>%s</td>
|
||
</tr>
|
||
</tbody>
|
||
</table>''' % (msg_time.strftime("%Y-%m-%d %H:%M"))
|
||
# print(html)
|
||
self.last_msg_time = msg_time
|
||
self.message.insertHtml(html)
|
||
|
||
def right(self, content, taklekId):
|
||
html = '''
|
||
<div>
|
||
<table align="right" style="vertical-align: middle;">
|
||
<tbody>
|
||
<tr>
|
||
<td>%s :</td>
|
||
<td style="border: 1px #000000 solid"><img align="right" src="%s" width="45" height="45"/></td>
|
||
<td width="15"></td>
|
||
</tr>
|
||
</tbody>
|
||
</table>
|
||
</div>
|
||
''' % (content, self.Me.my_avatar)
|
||
self.message.insertHtml(html)
|
||
|
||
def left(self, content, taklekId):
|
||
avatar = data.get_avator(taklekId)
|
||
html = '''
|
||
<div>
|
||
<table align="left" style="vertical-align: middle;">
|
||
<tbody>
|
||
<tr>
|
||
<td width="15"></td>
|
||
<td style="border: 1px #000000 solid"><img align="right" src="%s" width="45" height="45"/></td>
|
||
<td>: %s</td>
|
||
</tr>
|
||
</tbody>
|
||
</table>
|
||
</div>
|
||
''' % (avatar, content)
|
||
self.message.insertHtml(html)
|
||
|
||
|
||
class OneGroup(QtWidgets.QPushButton):
|
||
"""
|
||
联系人类,继承自pyqt的按钮,里面封装了联系人头像等标签
|
||
"""
|
||
gidSingal = pyqtSignal(int)
|
||
|
||
def __init__(self, Ui, contact=None):
|
||
super(OneGroup, self).__init__(Ui)
|
||
self.layoutWidget = QtWidgets.QWidget(Ui)
|
||
self.layoutWidget.setObjectName("layoutWidget")
|
||
self.gridLayout1 = QtWidgets.QGridLayout(self.layoutWidget)
|
||
self.gridLayout1.setSizeConstraint(QtWidgets.QLayout.SetMaximumSize)
|
||
self.gridLayout1.setContentsMargins(10, 10, 10, 10)
|
||
self.gridLayout1.setHorizontalSpacing(20)
|
||
self.gridLayout1.setVerticalSpacing(10)
|
||
self.gridLayout1.setObjectName("gridLayout1")
|
||
self.time0_1 = QtWidgets.QLabel(self.layoutWidget)
|
||
font = QtGui.QFont()
|
||
font.setPointSize(8)
|
||
self.time0_1.setFont(font)
|
||
self.time0_1.setLayoutDirection(QtCore.Qt.RightToLeft)
|
||
self.time0_1.setAlignment(QtCore.Qt.AlignRight | QtCore.Qt.AlignTrailing | QtCore.Qt.AlignVCenter)
|
||
self.time0_1.setObjectName("time0_1")
|
||
self.gridLayout1.addWidget(self.time0_1, 0, 2, 1, 1)
|
||
self.remark1 = QtWidgets.QLabel(self.layoutWidget)
|
||
font = QtGui.QFont()
|
||
font.setPointSize(15)
|
||
self.remark1.setFont(font)
|
||
self.remark1.setObjectName("remark1")
|
||
self.gridLayout1.addWidget(self.remark1, 0, 1, 1, 1)
|
||
self.msg1 = QtWidgets.QLabel(self.layoutWidget)
|
||
font = QtGui.QFont()
|
||
font.setPointSize(8)
|
||
self.msg1.setFont(font)
|
||
self.msg1.setObjectName("msg1")
|
||
self.gridLayout1.addWidget(self.msg1, 1, 1, 1, 2)
|
||
self.image1 = QtWidgets.QLabel(self.layoutWidget)
|
||
self.image1.setMinimumSize(QtCore.QSize(60, 60))
|
||
self.image1.setMaximumSize(QtCore.QSize(60, 60))
|
||
self.image1.setLayoutDirection(QtCore.Qt.RightToLeft)
|
||
self.image1.setAutoFillBackground(False)
|
||
self.image1.setStyleSheet("background-color: #ffffff;")
|
||
self.image1.setInputMethodHints(QtCore.Qt.ImhNone)
|
||
self.image1.setFrameShape(QtWidgets.QFrame.NoFrame)
|
||
self.image1.setFrameShadow(QtWidgets.QFrame.Plain)
|
||
self.image1.setAlignment(QtCore.Qt.AlignLeading | QtCore.Qt.AlignLeft | QtCore.Qt.AlignVCenter)
|
||
self.image1.setObjectName("image1")
|
||
self.gridLayout1.addWidget(self.image1, 0, 0, 2, 1)
|
||
self.gridLayout1.setColumnStretch(0, 1)
|
||
self.gridLayout1.setColumnStretch(1, 6)
|
||
self.gridLayout1.setRowStretch(0, 5)
|
||
self.gridLayout1.setRowStretch(1, 3)
|
||
self.setLayout(self.gridLayout1)
|
||
if contact:
|
||
self.g_id = contact[0]
|
||
self.g_name = contact[1]
|
||
self.nickname = contact[2]
|
||
self.type = contact[3]
|
||
self.addTime = contact[4]
|
||
self.show_info(id)
|
||
|
||
def show_info(self, id):
|
||
if 1:
|
||
# try:
|
||
avatar = data.get_avator(self.g_id)
|
||
remark = id
|
||
time = datetime.datetime.now().strftime("%m-%d %H:%M")
|
||
msg = '还没说话'
|
||
pixmap = QPixmap(avatar).scaled(60, 60) # 按指定路径找到图片
|
||
self.image1.setPixmap(pixmap) # 在label上显示图片
|
||
self.remark1.setText(self.g_name)
|
||
self.time0_1.setText(time)
|
||
|
||
def show_msg(self):
|
||
print('点击的群号', self.g_id)
|
||
self.gidSingal.emit(self.g_id)
|
||
pass
|
||
|
||
|
||
class ChatMsg(QThread):
|
||
"""
|
||
发送信息线程
|
||
"""
|
||
isSend_signal = pyqtSignal(tuple)
|
||
recvSignal = pyqtSignal(tuple)
|
||
sendSignal = pyqtSignal(tuple)
|
||
|
||
def __init__(self, my_u, g_id, socket, parent=None):
|
||
super().__init__(parent)
|
||
self.sec = 2 # 默认1000秒
|
||
self.my_u = my_u
|
||
self.g_id = g_id
|
||
self.group_users = data.get_group_users(g_id)
|
||
self.my_avatar = data.get_avator(my_u)
|
||
self.socket = socket
|
||
|
||
def send_msg(self, msg):
|
||
# 给群里所有在线的用户发送信息
|
||
for group_user in self.group_users:
|
||
username = group_user[0]
|
||
if username == self.my_u:
|
||
continue
|
||
ta_port = group_user[4]
|
||
nickname = group_user[3]
|
||
self.ta_addr = ('localhost', ta_port)
|
||
if ta_port == -1:
|
||
print(f'{nickname}不在线')
|
||
continue
|
||
send_data = {
|
||
'type': 'G',
|
||
'gid': self.g_id,
|
||
'username': self.my_u,
|
||
'content': msg
|
||
}
|
||
print(f'{nickname}在线,{msg} 发送成功')
|
||
self.socket.sendto(json.dumps(send_data).encode('utf-8'), self.ta_addr)
|
||
message = data.send_group_msg(
|
||
gid=self.g_id,
|
||
msg=msg,
|
||
talker=self.my_u,
|
||
IsSend=1,
|
||
_type=3
|
||
)
|
||
self.sendSignal.emit(message)
|
||
return message
|
||
|
||
def run(self):
|
||
# return
|
||
messages = data.get_group_message(self.g_id)
|
||
# print(messages)
|
||
for message in messages:
|
||
self.isSend_signal.emit(message)
|
||
# self.recv_msg()
|