diff --git a/src/timelineEvent.py b/src/timelineEvent.py index 6ac61df..7e0d3a5 100644 --- a/src/timelineEvent.py +++ b/src/timelineEvent.py @@ -4,7 +4,7 @@ import json from PyQt5.QtWidgets import (QApplication, QWidget, QGraphicsView, QGraphicsScene, QGraphicsTextItem, QToolTip, QVBoxLayout, QTabWidget, QLabel) -from PyQt5.QtCore import Qt, QEvent +from PyQt5.QtCore import Qt, QEvent, QTimer, QPoint from PyQt5.QtGui import QPen, QBrush, QColor, QFont, QPainter class TimelineEvent: @@ -15,6 +15,41 @@ class TimelineEvent: self.title = title self.details = details # 详细信息字典 +class CustomTooltip(QWidget): + """自定义提示框,支持设置显示时长""" + def __init__(self, parent=None): + super().__init__(parent, Qt.ToolTip | Qt.FramelessWindowHint) + self.setWindowOpacity(0.95) # 半透明 + + # 设置样式 + self.setStyleSheet(""" + background-color: #f5f5f5; + border: 1px solid #ccc; + border-radius: 4px; + padding: 8px; + """) + + self.layout = QVBoxLayout(self) + self.label = QLabel() + self.label.setFont(QFont("SimHei", 10)) + self.label.setTextInteractionFlags(Qt.TextSelectableByMouse) # 允许选中文本 + self.layout.addWidget(self.label) + + # 定时器控制隐藏 + self.hide_timer = QTimer(self) + self.hide_timer.setSingleShot(True) + self.hide_timer.timeout.connect(self.hide) + + def setText(self, text): + self.label.setText(text) + self.adjustSize() # 自动调整大小以适应内容 + + def showAt(self, pos, duration=10000): + """在指定位置显示,duration为显示时长(毫秒)""" + self.move(pos) + self.show() + self.hide_timer.start(duration) # 10秒后自动隐藏 + class TimelineGraphicsView(QGraphicsView): """时间线视图,实现3个事件一组的高度调整和间隔时间戳显示""" def __init__(self, parent=None): @@ -54,6 +89,10 @@ class TimelineGraphicsView(QGraphicsView): (0, 0, 150) # 组6 :浅蓝 ] + # 初始化自定义提示框 + self.tooltip = CustomTooltip(self) + self.hovered_event = None # 当前悬停的事件 + def wheelEvent(self, event): """鼠标滚轮缩放""" delta = event.angleDelta().y() @@ -69,23 +108,45 @@ class TimelineGraphicsView(QGraphicsView): self.current_scale = new_scale def eventFilter(self, obj, event): - """事件悬停提示""" - if obj == self.viewport() and event.type() == QEvent.MouseMove: - scene_pos = self.mapToScene(event.pos()) - - for item, event_data in self.event_items: - if item.contains(item.mapFromScene(scene_pos)): - details_text = f"{event_data.title}
" - details_text += f"时间: {event_data.timestamp.strftime('%Y-%m-%d %H:%M:%S')}

" - for key, value in event_data.details.items(): - details_text += f"{key}: {value}
" - - QToolTip.showText(event.globalPos(), details_text) - return True - - QToolTip.hideText() + """事件过滤器,处理鼠标移动和离开""" + if obj == self.viewport(): + if event.type() == QEvent.MouseMove: + self.handle_mouse_move(event) + elif event.type() == QEvent.Leave: + # 鼠标离开视图时隐藏提示 + self.tooltip.hide() + self.hovered_event = None return super().eventFilter(obj, event) + + def handle_mouse_move(self, event): + """处理鼠标移动,显示/隐藏提示""" + scene_pos = self.mapToScene(event.pos()) + current_hover = None + + # 检查是否悬停在事件上 + for item, event_data in self.event_items: + if item.contains(item.mapFromScene(scene_pos)): + current_hover = event_data + break + + if current_hover: + if current_hover != self.hovered_event: + # 显示新的提示(10秒后自动隐藏) + self.hovered_event = current_hover + details_text = f"{current_hover.title}
" + details_text += f"时间: {current_hover.timestamp.strftime('%Y-%m-%d %H:%M:%S')}

" + for key, value in current_hover.details.items(): + details_text += f"{key}: {value}
" + + # 在鼠标位置附近显示提示 + global_pos = event.globalPos() + self.tooltip.setText(details_text) + self.tooltip.showAt(QPoint(global_pos.x() + 10, global_pos.y() + 10), 10000) + else: + # 没有悬停在事件上,隐藏提示 + self.tooltip.hide() + self.hovered_event = None def add_events(self, events): """添加事件并按组布局"""