优化了部分代码

This commit is contained in:
zayac 2024-04-07 19:50:36 +08:00
parent 555ca73bba
commit ed5b11fbc8
10 changed files with 210 additions and 184 deletions

View File

@ -5,7 +5,7 @@ from src.core.util import resource_path
# logger.remove() # logger.remove()
# logger.add(sys.stderr, level="INFO") # logger.add(sys.stderr, level="INFO")
logger.add("{time:YYYY-MM}/{time:YYYY-MM-DD}.log", rotation="00:00", level="DEBUG", retention='1 day', logger.add("/{time:YYYY-MM}/{time:YYYY-MM-DD}.log", rotation="00:00", level="DEBUG", retention='1 day',
encoding='utf-8') encoding='utf-8')
QtCore.QDir.addSearchPath('icons', resource_path('ui/icon/')) QtCore.QDir.addSearchPath('icons', resource_path('ui/icon/'))

View File

@ -1,4 +1,4 @@
import qdarkstyle import qdarkstyle, sys
from PyQt6.QtWidgets import QApplication from PyQt6.QtWidgets import QApplication
from src.ui.app import Application from src.ui.app import Application
@ -9,4 +9,4 @@ if __name__ == '__main__':
app.setStyleSheet(qdarkstyle.load_stylesheet(qt_api='pyqt6')) app.setStyleSheet(qdarkstyle.load_stylesheet(qt_api='pyqt6'))
main_win = Application() main_win = Application()
main_win.show() main_win.show()
app.exec() sys.exit(app.exec())

View File

@ -1,3 +1,4 @@
import os
import time import time
import schedule import schedule
from loguru import logger from loguru import logger
@ -9,45 +10,49 @@ from src.entity.pay_record import get_pay_failed_by_user
from src.entity.user import get_user_by_username_and_password from src.entity.user import get_user_by_username_and_password
from src.entity.visual_list import text_count_by_user from src.entity.visual_list import text_count_by_user
# 日志配置
logger.add("debug.log", format="{time} {level} {message}", level="DEBUG", rotation="1 week", compression="zip")
def job_count(username, password):
def execute_task(task_func, username, password):
try: try:
logger.info(f'Running job_count for username: {username}') logger.info(f'Running {task_func.__name__} for username: {username}')
user = get_user_by_username_and_password(username, password) user = get_user_by_username_and_password(username, password)
send_message(user.bot_token, user.count_group_id, text_count_by_user(user, get_curr_day())) message = task_func(user, get_curr_day()) # Assuming all tasks take a 'user' and 'date'
logger.info(f'Finished job_count for username: {username}') send_message(user.bot_token, user.count_group_id, message)
except Exception as e: logger.info(f'Finished {task_func.__name__} for username: {username}')
logger.error(f'Error running job_count for username: {username}, Error: {e}') except Exception as e: # Consider catching more specific exceptions if possible
logger.error(f'Error running {task_func.__name__} for username: {username}, Error: {e}')
logger.exception(e) # This will log the full stack trace
def query_failed_deposit(username, password): def job_count(user, date):
try: return text_count_by_user(user, date)
logger.info(f'Running query_failed_deposit for username: {username}')
user = get_user_by_username_and_password(username, password)
send_message(user.bot_token, user.count_group_id, get_pay_failed_by_user(user, get_curr_day()))
logger.info(f'Finished query_failed_deposit for username: {username}')
except Exception as e:
logger.error(f'Error running query_failed_deposit for username: {username}, Error: {e}')
def query_net_win(username, password): def query_failed_deposit(user, date):
try: return get_pay_failed_by_user(user, date)
logger.info(f'Running query_net_win for username: {username}')
user = get_user_by_username_and_password(username, password)
send_message(user.bot_token, user.count_group_id, get_net_win_by_user(user, date=get_curr_day())) def query_net_win(user, date):
logger.info(f'Finished query_net_win for username: {username}') return get_net_win_by_user(user, date)
except Exception as e:
logger.error(f'Error running query_net_win for username: {username}, Error: {e}')
if __name__ == '__main__': if __name__ == '__main__':
logger.info('Starting scheduled tasks') logger.info('Starting scheduled tasks')
# Get credentials from environment variables
username = os.getenv('MY_APP_USERNAME', 'default_username')
password = os.getenv('MY_APP_PASSWORD', 'default_password')
times = ['10:50', '14:40', '17:40', '20:40', '21:40', '23:59'] times = ['10:50', '14:40', '17:40', '20:40', '21:40', '23:59']
for time_str in times: for time_str in times:
schedule.every().day.at(time_str).do(job_count, 'zayac', '123456') schedule.every().day.at(time_str).do(execute_task, job_count, username, password)
schedule.every().day.at(time_str).do(query_net_win, 'zayac', '123456') schedule.every().day.at(time_str).do(execute_task, query_net_win, username, password)
schedule.every().day.at('23:59').do(query_failed_deposit, 'zayac', '123456')
schedule.every().day.at('23:59').do(execute_task, query_failed_deposit, username, password)
while True: while True:
schedule.run_pending() schedule.run_pending()
time.sleep(1) time.sleep(10)
# logger.info('Running scheduled tasks') # This line is commented out to reduce log verbosity

View File

@ -46,7 +46,6 @@ def query_banner_info(account: Account):
last_banner_info = get_banner_info(account) last_banner_info = get_banner_info(account)
while True: while True:
try: try:
date = get_curr_day()
banner_info = get_banner_info(account) banner_info = get_banner_info(account)
logger.debug(f'{account.name}请求成功:{banner_info}') logger.debug(f'{account.name}请求成功:{banner_info}')
logger.info( logger.info(

View File

@ -1,7 +1,5 @@
import asyncio import asyncio
from concurrent.futures import ThreadPoolExecutor
from dataclasses import dataclass from dataclasses import dataclass
from datetime import datetime
from typing import Dict, List, Optional from typing import Dict, List, Optional
from src import logger from src import logger

View File

@ -1,6 +1,5 @@
import configparser
import os
import time import time
from enum import Enum
from loguru import logger from loguru import logger
from PyQt6.QtCore import QDate, QDateTime, Qt, QThreadPool, QTime, QTimer from PyQt6.QtCore import QDate, QDateTime, Qt, QThreadPool, QTime, QTimer
@ -11,6 +10,7 @@ from PyQt6.QtWidgets import (QApplication, QCheckBox, QDateEdit, QHBoxLayout,
QTableWidget, QTableWidgetItem, QTabWidget, QTableWidget, QTableWidgetItem, QTabWidget,
QTextEdit, QVBoxLayout, QWidget) QTextEdit, QVBoxLayout, QWidget)
from src.ui.config import ConfigManager
from src.core.message_client import send_message from src.core.message_client import send_message
from src.core.util import convert_data, resource_path from src.core.util import convert_data, resource_path
from src.entity.member import get_today_new_member_list from src.entity.member import get_today_new_member_list
@ -24,6 +24,15 @@ from src.ui.title_bar import CustomTitleBar
class Application(QMainWindow): class Application(QMainWindow):
def __init__(self): def __init__(self):
super().__init__() super().__init__()
self.config_manager = ConfigManager()
self.thread_pool = QThreadPool()
self.report_timer = None
self.date_update_timer = None
self.username = None
self.password = None
self.minimum = False
self.customTitleBar = None
self.tray_icon = None
self.tables = {} self.tables = {}
self.is_dragging = False self.is_dragging = False
self.drag_position = None self.drag_position = None
@ -37,10 +46,7 @@ class Application(QMainWindow):
# 1. 加载配置文件 # 1. 加载配置文件
self.load_config() self.load_config()
# 2. 设置线程池 # 2. 设置 UI
self.thread_pool = QThreadPool()
# 3. 设置 UI
self.setup_ui() self.setup_ui()
# 4. 初始化系统托盘图标 # 4. 初始化系统托盘图标
@ -49,13 +55,9 @@ class Application(QMainWindow):
# 5. 初始化表格数据 # 5. 初始化表格数据
self.init_table_data() self.init_table_data()
# 6. 设置日期更新和报告定时器 self.setup_timers()
self.setup_date_update_timer()
self.setup_report_timer() self.connect_signals()
# 7. 全局信号处理,更新用户信息
global_signals.user_data_updated.connect(self.refresh_user_data)
# 8. 消息通知对象
self.chat_id = self.user.group_id if self.user.group_id else self.user.chat_id
def setup_ui(self): def setup_ui(self):
self.apply_stylesheet() self.apply_stylesheet()
@ -63,6 +65,14 @@ class Application(QMainWindow):
self.create_central_widget() self.create_central_widget()
self.setup_layouts() self.setup_layouts()
def setup_timers(self):
self.setup_date_update_timer()
self.setup_report_timer()
def connect_signals(self):
self.tray_icon.activated.connect(self.tray_icon_clicked)
global_signals.user_data_updated.connect(self.refresh_user_data)
def set_window_properties(self): def set_window_properties(self):
self.resize(600, 400) self.resize(600, 400)
self.setWindowTitle("zayac的小工具") self.setWindowTitle("zayac的小工具")
@ -82,40 +92,20 @@ class Application(QMainWindow):
self.setMenuWidget(self.customTitleBar) self.setMenuWidget(self.customTitleBar)
def init_tray_icon(self): def init_tray_icon(self):
self.tray_icon = QSystemTrayIcon(QIcon("icons:icon.png"), self) self.tray_icon = SystemTrayIcon(QIcon("icons:icon.png"), self) # 替换为正确的图标路径
tray_menu = QMenu()
exit_action = QAction("退出", self)
exit_action.triggered.connect(self.exit_application)
tray_menu.addAction(exit_action)
self.tray_icon.setContextMenu(tray_menu)
self.tray_icon.activated.connect(self.tray_icon_clicked)
self.tray_icon.show() self.tray_icon.show()
def init_data_and_timers(self):
# 初始化数据
self.init_table_data()
# 设置定时器
self.setup_date_update_timer()
self.setup_report_timer()
def load_config(self): def load_config(self):
config = configparser.ConfigParser() # 使用
config_file = 'config.ini' try:
self.username = self.config_manager.get('Credentials', 'username')
if not os.path.exists(config_file): self.password = self.config_manager.get('Credentials', 'password')
QMessageBox.warning(None, "警告", "用户信息获取失败!") self.minimum = self.config_manager.get('Minimum', 'minimum')
self.user = get_user_by_username_and_password(self.username, self.password)
except FileNotFoundError as e:
QMessageBox.warning(None, "警告", "配置文件信息加载失败!请检查文件是否存在")
return None, None return None, None
config.read(config_file)
username = config.get('Credentials', 'username')
password = config.get('Credentials', 'password')
minimum = config.get('Minimum', 'minimum')
self.username = username
self.password = password
self.user = get_user_by_username_and_password(username, password)
self.minimum = minimum
def init_table_data(self): def init_table_data(self):
# 初始化表格数据 # 初始化表格数据
data = self.query_initial_data(self.user) data = self.query_initial_data(self.user)
@ -124,14 +114,13 @@ class Application(QMainWindow):
self.update_table(row.agentCode, [time_str, row.registerMembers, row.firstDepositNum, row.netWinLose, self.update_table(row.agentCode, [time_str, row.registerMembers, row.firstDepositNum, row.netWinLose,
row.effectiveNew, row.activeMembers]) row.effectiveNew, row.activeMembers])
def query_initial_data(self, account): def query_initial_data(self, user):
# 实际实现应该根据您的业务逻辑来定义 return ReportTask.get_banner_info_by_user(user)
return ReportTask.query_data_for_user(account)
def setup_report_timer(self): def setup_report_timer(self):
self.report_timer = QTimer(self) self.report_timer = QTimer(self)
self.report_timer.timeout.connect(self.update_reports) self.report_timer.timeout.connect(self.update_reports)
self.report_timer.start(60000) # 每60秒触发一次 self.report_timer.start(60000)
def update_reports(self): def update_reports(self):
for account in self.user.accounts: for account in self.user.accounts:
@ -194,13 +183,12 @@ class Application(QMainWindow):
def start_date_update_timer(self): def start_date_update_timer(self):
now = QDateTime.currentDateTime() now = QDateTime.currentDateTime()
next_midnight = QDateTime(now.date().addDays(1), QTime(0, 0)) next_midnight = QDateTime(now.date().addDays(1), QTime(0, 0)) # 设置为次日的午夜 00:00
interval = now.msecsTo(next_midnight) interval = now.msecsTo(next_midnight)
self.date_update_timer.start(interval if interval > 0 else 86400000) # 86400000ms = 24小时 self.date_update_timer.start(interval if interval > 0 else 86400000) # 86400000ms = 24小时
def update_date_edit(self): def update_date_edit(self):
self.dateEdit.setDate(QDate.currentDate()) self.dateEdit.setDate(QDate.currentDate()) # 设置 QDateEdit 控件的日期为当前日期
self.dateEdit.update()
self.update_date_range() self.update_date_range()
self.start_date_update_timer() self.start_date_update_timer()
@ -287,7 +275,7 @@ class Application(QMainWindow):
if self.toaster_notify_enabled: if self.toaster_notify_enabled:
self.tray_icon.showMessage(f"{title}通知", msg, QSystemTrayIcon.MessageIcon.Information, 2000) self.tray_icon.showMessage(f"{title}通知", msg, QSystemTrayIcon.MessageIcon.Information, 2000)
if self.telegram_notify_enabled: if self.telegram_notify_enabled:
send_message(self.user.bot_token, self.chat_id, msg) send_message(self.user.bot_token, self.user.group_id, msg)
def on_report_clicked(self): def on_report_clicked(self):
try: try:
@ -323,35 +311,42 @@ class Application(QMainWindow):
# 获取当前的行数 # 获取当前的行数
row_count = table.rowCount() row_count = table.rowCount()
table.insertRow(row_count) table.insertRow(row_count)
notifications = []
notifications = []
for col, cell_data in enumerate(data): for col, cell_data in enumerate(data):
cell = self.create_table_cell(cell_data, table, col) self.set_table_item(table, row_count, col, cell_data)
# 使用 row_count 而不是 0l self.check_data_change_for_notifications(table, row_count, col, cell_data, account_username, notifications)
table.setItem(row_count, col, cell)
self.handle_data_change(table, cell_data, col, account_username, notifications)
self.send_all_notifications(notifications) self.send_all_notifications(notifications)
def create_table_cell(self, cell_data, table, col): def send_all_notifications(self, notifications):
"""发送所有通知"""
for notification in notifications:
self.send_notification(*notification)
def set_table_item(self, table, row, col, cell_data):
"""在表格指定行列设置单元格数据"""
cell = QTableWidgetItem(str(cell_data)) cell = QTableWidgetItem(str(cell_data))
cell.setTextAlignment(Qt.AlignmentFlag.AlignCenter) cell.setTextAlignment(Qt.AlignmentFlag.AlignCenter)
return cell table.setItem(row, col, cell)
def handle_data_change(self, table, cell_data, col, account_username, notifications): def check_data_change_for_notifications(self, table, row, col, new_data, account_username, notifications):
if table.rowCount() > 1 and col != 0: """检查数据变更并准备通知"""
old_data_str = table.item(table.rowCount() - 2, col).text() if row > 0 and col != 0: # 忽略第一列,通常是时间戳
old_data_str = table.item(row - 1, col).text()
old_data = convert_data(old_data_str) old_data = convert_data(old_data_str)
new_data = convert_data(cell_data) new_data = convert_data(new_data)
if old_data != new_data: if old_data != new_data:
count_change = new_data - old_data self.handle_data_change(table, col, new_data - old_data, account_username, notifications)
self.update_cell_color(table, col, count_change)
self.generate_notifications(account_username, col, cell_data, count_change, notifications)
def update_cell_color(self, table, col, count_change): def handle_data_change(self, table, col, count_change, account_username, notifications):
# 更新单元格颜色 """处理表格数据变更,更新单元格颜色,并生成通知"""
cell = table.item(table.rowCount() - 1, col) self.update_cell_color(table, table.rowCount() - 1, col, count_change)
self.generate_notifications(account_username, col, col, count_change, notifications)
def update_cell_color(self, table, row, col, count_change):
"""更新单元格颜色"""
cell = table.item(row, col)
if count_change > 0: if count_change > 0:
cell.setForeground(QColor(Qt.GlobalColor.green)) cell.setForeground(QColor(Qt.GlobalColor.green))
elif count_change < 0: elif count_change < 0:
@ -373,10 +368,6 @@ class Application(QMainWindow):
notifications.append( notifications.append(
('🎉', account.name, '首存', count_change, deposit_results, str(cell_data))) ('🎉', account.name, '首存', count_change, deposit_results, str(cell_data)))
def send_all_notifications(self, notifications):
for notification in notifications:
self.send_notification(*notification)
def addToggleButton(self, text, style): def addToggleButton(self, text, style):
toggleButton = QPushButton(text) toggleButton = QPushButton(text)
toggleButton.setCheckable(True) toggleButton.setCheckable(True)
@ -399,39 +390,29 @@ class Application(QMainWindow):
self.main_layout.addLayout(self.middle_panel) self.main_layout.addLayout(self.middle_panel)
def add_tabs(self, notebook): def add_tabs(self, notebook):
column_headers = ["时间", "注册", "首存", "负盈利", "有效", "活跃"] column_headers = ColumnHeaders.list()
for account in self.user.accounts: for account in self.user.accounts:
# 创建 Tab 和布局
tab = QWidget() tab = QWidget()
tab_layout = QVBoxLayout(tab) tab_layout = QVBoxLayout(tab)
notebook.addTab(tab, account.name) notebook.addTab(tab, account.name)
# 创建表格并设置列数和列标题 table = self.create_table_for_tab(column_headers)
table = QTableWidget()
table.setColumnCount(len(column_headers))
table.setHorizontalHeaderLabels(column_headers)
# 禁用表格的编辑功能
table.setEditTriggers(QTableWidget.EditTrigger.NoEditTriggers)
# 设置列宽
header = table.horizontalHeader()
# 设置所有列为自适应宽度
for i in range(len(column_headers)):
header.setSectionResizeMode(i, QHeaderView.ResizeMode.Stretch)
header.setSectionResizeMode(0, QHeaderView.ResizeMode.ResizeToContents)
# 将表格的大小调整策略设置为填充整个 Tab
table.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Expanding))
# 将表格添加到布局中
tab_layout.addWidget(table) tab_layout.addWidget(table)
# 保存表格引用以便稍后更新
self.tables[account.username] = table self.tables[account.username] = table
def create_table_for_tab(self, column_headers):
table = QTableWidget()
table.setColumnCount(len(column_headers))
table.setHorizontalHeaderLabels(column_headers)
table.setEditTriggers(QTableWidget.EditTrigger.NoEditTriggers)
header = table.horizontalHeader()
header.setSectionResizeMode(QHeaderView.ResizeMode.Stretch)
header.setSectionResizeMode(0, QHeaderView.ResizeMode.ResizeToContents)
table.setSizePolicy(QSizePolicy(QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Expanding))
return table
def mousePressEvent(self, event): def mousePressEvent(self, event):
if event.button() == Qt.MouseButton.LeftButton: if event.button() == Qt.MouseButton.LeftButton:
self.drag_position = event.globalPosition().toPoint() self.drag_position = event.globalPosition().toPoint()
@ -540,13 +521,40 @@ class Application(QMainWindow):
def tray_icon_clicked(self, reason): def tray_icon_clicked(self, reason):
if reason == QSystemTrayIcon.ActivationReason.Trigger: if reason == QSystemTrayIcon.ActivationReason.Trigger:
if self.isVisible(): if self.isMinimized() or not self.isVisible():
self.hide() self.showNormal() # 恢复窗口大小
self.activateWindow() # 激活窗口
else: else:
self.showNormal() self.hide() # 点击托盘图标再次隐藏窗口
def copy_to_clipboard(text): def copy_to_clipboard(text):
clipboard = QApplication.clipboard() clipboard = QApplication.clipboard()
clipboard.setText(text) clipboard.setText(text)
class SystemTrayIcon(QSystemTrayIcon):
def __init__(self, icon, parent=None):
super().__init__(icon, parent)
self.menu = QMenu(parent)
self.setContextMenu(self.menu)
self.create_actions(parent)
def create_actions(self, parent):
exit_action = QAction("Exit", parent)
exit_action.triggered.connect(parent.exit_application)
self.menu.addAction(exit_action)
class ColumnHeaders(Enum):
TIME = "时间"
REGISTER = "注册"
FIRST_DEPOSIT = "首存"
NET_PROFIT = "负盈利"
EFFECTIVE = "有效"
ACTIVE = "活跃"
@classmethod
def list(cls):
return [cls.TIME.value, cls.REGISTER.value, cls.FIRST_DEPOSIT.value,
cls.NET_PROFIT.value, cls.EFFECTIVE.value, cls.ACTIVE.value]

14
src/ui/config.py Normal file
View File

@ -0,0 +1,14 @@
import configparser
import os
from loguru import logger
class ConfigManager:
def __init__(self, config_path='config.ini'):
self.config = configparser.ConfigParser()
if not os.path.exists(config_path):
raise FileNotFoundError(f"配置文件 {config_path} 不存在。")
self.config.read(config_path, encoding='utf-8')
def get(self, section, option, fallback=None):
return self.config.get(section, option, fallback=fallback)

View File

@ -5,7 +5,7 @@ from PyQt6.QtCore import QObject, QRunnable, pyqtSignal
from src.entity.banner_info import get_banner_info, get_banner_info_by_user from src.entity.banner_info import get_banner_info, get_banner_info_by_user
from src.entity.finance import get_adjusted_salary, get_net_win_by_user from src.entity.finance import get_adjusted_salary, get_net_win_by_user
from src.entity.pay_record import get_pay_failed_by_user from src.entity.pay_record import get_pay_failed_by_user
from src.entity.visual_list import text_count_by_user from src.entity.visual_list import text_count_by_user, get_statics
class TaskSignals(QObject): class TaskSignals(QObject):
@ -31,8 +31,9 @@ class ReportTask(QRunnable):
return [time_str, banner_info.registerMembers, banner_info.firstDepositNum, banner_info.netWinLose, return [time_str, banner_info.registerMembers, banner_info.firstDepositNum, banner_info.netWinLose,
banner_info.effectiveNew, banner_info.activeMembers] banner_info.effectiveNew, banner_info.activeMembers]
@staticmethod @staticmethod
def query_data_for_user(user): def get_banner_info_by_user(user):
banner_info_res = get_banner_info_by_user(user) banner_info_res = get_banner_info_by_user(user)
return banner_info_res return banner_info_res

View File

@ -0,0 +1,15 @@
from PyQt6.QtWidgets import QSystemTrayIcon, QMenu
from PyQt6.QtGui import QIcon, QAction
class SystemTrayIcon(QSystemTrayIcon):
def __init__(self, icon, parent=None):
super().__init__(icon, parent)
self.menu = QMenu(parent)
self.setContextMenu(self.menu)
self.create_actions(parent)
def create_actions(self, parent):
exit_action = QAction("Exit", parent)
exit_action.triggered.connect(parent.exit_application)
self.menu.addAction(exit_action)

View File

@ -2,69 +2,58 @@ from PyQt6.QtCore import Qt
from PyQt6.QtGui import QFont, QIcon, QPixmap from PyQt6.QtGui import QFont, QIcon, QPixmap
from PyQt6.QtWidgets import QHBoxLayout, QLabel, QToolButton, QWidget from PyQt6.QtWidgets import QHBoxLayout, QLabel, QToolButton, QWidget
class CustomTitleBar(QWidget): class CustomTitleBar(QWidget):
def __init__(self, parent): def __init__(self, parent):
super().__init__(parent) super().__init__(parent)
self.parent = parent self.parent = parent
self.setup_ui()
self.mousePressed = False self.mousePressed = False
self.setup_ui()
def setup_ui(self): def setup_ui(self):
self.layout = QHBoxLayout() self.layout = QHBoxLayout()
self.layout.setContentsMargins(0, 0, 0, 0) # 设置布局的边距为0 self.layout.setContentsMargins(0, 0, 0, 0)
self.layout.setSpacing(0) # 设置按钮之间的间距为0 self.layout.setSpacing(0)
# 创建图标 QLabel self.setup_icon_label()
self.setup_title_label()
self.setup_buttons()
self.setLayout(self.layout)
def setup_icon_label(self):
self.iconLabel = QLabel(self) self.iconLabel = QLabel(self)
self.iconLabel.setFixedSize(32, 32) # 设置图标大小 self.iconLabel.setFixedSize(32, 32)
iconPixmap = QPixmap('icons:icon.png').scaled(24, 24, Qt.AspectRatioMode.KeepAspectRatio) iconPixmap = QPixmap('icons:icon.png').scaled(24, 24, Qt.AspectRatioMode.KeepAspectRatio)
self.iconLabel.setPixmap(iconPixmap) self.iconLabel.setPixmap(iconPixmap)
self.layout.addWidget(self.iconLabel) # 添加图标到布局 self.layout.addWidget(self.iconLabel)
# 创建标题 QLabel def setup_title_label(self):
font = QFont() font = QFont()
font.setPointSize(11) font.setPointSize(11)
self.titleLabel = QLabel("zayac的小工具") self.titleLabel = QLabel("zayacs Toolkit")
self.titleLabel.setFont(font) self.titleLabel.setFont(font)
self.titleLabel.setAlignment(Qt.AlignmentFlag.AlignLeft | Qt.AlignmentFlag.AlignVCenter) self.titleLabel.setAlignment(Qt.AlignmentFlag.AlignLeft | Qt.AlignmentFlag.AlignVCenter)
self.layout.addWidget(self.titleLabel, 1) self.layout.addWidget(self.titleLabel, 1)
# 使用图标按钮并应用样式 def setup_buttons(self):
self.stayOnTopButton = QToolButton() self.stayOnTopButton = self.create_tool_button('icons:top.svg', self.toggle_stay_on_top)
self.stayOnTopButton.setIcon(QIcon('icons:top.svg')) self.minimizeButton = self.create_tool_button('icons:min.svg', self.parent.showMinimized)
self.stayOnTopButton.setFixedSize(32, 32) # 设置按钮的固定大小 self.maximizeButton = self.create_tool_button('icons:max.svg', self.toggle_maximize)
self.stayOnTopButton.setCheckable(True) self.closeButton = self.create_tool_button('icons:close.svg', self.parent.close)
self.stayOnTopButton.clicked.connect(self.toggle_stay_on_top)
self.layout.addWidget(self.stayOnTopButton)
# 设置其他按钮
self.minimizeButton = QToolButton()
self.minimizeButton.setIcon(QIcon('icons:min.svg'))
self.minimizeButton.setFixedSize(32, 32)
self.minimizeButton.clicked.connect(self.parent.showMinimized)
self.layout.addWidget(self.minimizeButton)
self.maximizeButton = QToolButton()
self.maximizeButton.setIcon(QIcon('icons:max.svg'))
self.maximizeButton.setFixedSize(32, 32)
self.maximizeButton.clicked.connect(self.toggle_maximize)
self.layout.addWidget(self.maximizeButton)
self.closeButton = QToolButton()
self.closeButton.setIcon(QIcon('icons:close.svg'))
self.closeButton.setFixedSize(32, 32)
self.closeButton.clicked.connect(self.parent.close)
self.closeButton.setObjectName("closeButton") self.closeButton.setObjectName("closeButton")
self.layout.addWidget(self.closeButton)
# 在创建按钮后立即设置样式表 def create_tool_button(self, icon_path, callback):
button = QToolButton()
self.setLayout(self.layout) button.setIcon(QIcon(icon_path))
button.setFixedSize(32, 32)
button.clicked.connect(callback)
self.layout.addWidget(button)
return button
def mousePressEvent(self, event): def mousePressEvent(self, event):
self.mousePressed = True if event.buttons() == Qt.MouseButton.LeftButton:
self.mousePos = event.globalPosition().toPoint() self.mousePressed = True
self.mousePos = event.globalPosition().toPoint()
def mouseMoveEvent(self, event): def mouseMoveEvent(self, event):
if self.mousePressed: if self.mousePressed:
@ -75,20 +64,17 @@ class CustomTitleBar(QWidget):
self.mousePressed = False self.mousePressed = False
def toggle_stay_on_top(self): def toggle_stay_on_top(self):
current_flags = self.parent.windowFlags()
if self.stayOnTopButton.isChecked(): if self.stayOnTopButton.isChecked():
self.parent.setWindowFlags(self.parent.windowFlags() | Qt.WindowType.WindowStaysOnTopHint) self.parent.setWindowFlags(current_flags | Qt.WindowType.WindowStaysOnTopHint)
else: else:
self.parent.setWindowFlags(self.parent.windowFlags() & ~Qt.WindowType.WindowStaysOnTopHint) self.parent.setWindowFlags(current_flags & ~Qt.WindowType.WindowStaysOnTopHint)
self.parent.show() # 重新显示窗口以应用新的窗口标志 self.parent.show() # Re-show the window to apply new window flags
def enterEvent(self, event):
self.parent.reset_cursor_style() # 通知主窗口重置鼠标样式
def leaveEvent(self, event):
self.parent.reset_cursor_style() # 通知主窗口重置鼠标样式
def toggle_maximize(self): def toggle_maximize(self):
if self.parent.isMaximized(): if self.parent.isMaximized():
self.parent.showNormal() self.parent.showNormal()
self.maximizeButton.setIcon(QIcon('icons:max.svg')) # Update icon if needed
else: else:
self.parent.showMaximized() self.parent.showMaximized()
self.maximizeButton.setIcon(QIcon('icons:restore.svg')) # Update icon if needed