搅拌桨旋转(目前上料斗左移到搅拌楼下时触发)
This commit is contained in:
@ -197,6 +197,8 @@ class MainWindow(QWidget):
|
||||
# 以下为模拟:
|
||||
# 假设两秒种之后,移动到了搅拌机下 (这里需要根据实际情况修改)
|
||||
QTimer.singleShot(2000, self.conveyor_system_widget.moveHopperBelowMixer)
|
||||
# 移动到搅拌楼下,搅拌桨就开始旋转
|
||||
QTimer.singleShot(2100, self.mixer_widget.startBladeMix)
|
||||
# 料斗左移完成,恢复料斗右移按钮
|
||||
QTimer.singleShot(2100, lambda: self.conveyor_system_widget.right_btn.setEnabled(True))
|
||||
|
||||
@ -205,8 +207,12 @@ class MainWindow(QWidget):
|
||||
# 演示效果
|
||||
self.conveyor_system_widget.moveHopperToTransition() # 移动到过渡的位置
|
||||
self.hopper_widget.upper_clamp_widget.set_angle(0) # 上料斗向右移动到目的地时,夹爪的角度一定是0
|
||||
# 按钮状态:点击料斗右移按钮后,禁用料斗左移按钮
|
||||
# 按钮状态:点击料斗右移按钮后,禁用料斗左移按钮
|
||||
self.conveyor_system_widget.left_btn.setEnabled(False)
|
||||
|
||||
# 开始右移,搅拌桨就停止转动
|
||||
self.mixer_widget.stopBladeMix()
|
||||
|
||||
# 以下为模拟:
|
||||
# 假设两秒后,传送带中 料斗向右移动完成 (这里需要根据实际情况修改)
|
||||
QTimer.singleShot(1900, self.conveyor_system_widget.hideHopper) # 料斗向右移动完成,隐藏料斗
|
||||
|
||||
@ -1,14 +1,88 @@
|
||||
from PySide6.QtWidgets import QWidget, QLabel, QHBoxLayout
|
||||
from PySide6.QtGui import QPixmap, QFont
|
||||
from PySide6.QtCore import Qt
|
||||
from PySide6.QtGui import QPixmap, QFont, QTransform
|
||||
from PySide6.QtCore import Qt, QPropertyAnimation, QEasingCurve, Property
|
||||
|
||||
import resources.resources_rc
|
||||
from utils.image_paths import ImagePaths
|
||||
|
||||
class BladeLabel(QLabel):
|
||||
def __init__(self, parent=None):
|
||||
super().__init__(parent)
|
||||
self._rotation = 0.0
|
||||
self._original_pixmap = None
|
||||
self._original_center_x = 0.0 # 原始图片自身中心点x
|
||||
self._original_center_y = 0.0 # 原始图片自身中心点y
|
||||
self._fixed_center_in_parent_x = 0 # 父容器中的固定中心点x(关键)
|
||||
self._fixed_center_in_parent_y = 0 # 父容器中的固定中心点y(关键)
|
||||
# self.setFixedSize(50, 54)
|
||||
|
||||
def set_original_pixmap(self, pixmap, fixed_center_x, fixed_center_y):
|
||||
"""
|
||||
:param pixmap: 原始图片
|
||||
:param fixed_center_x: 父容器中固定的中心点x坐标(绝对位置)
|
||||
:param fixed_center_y: 父容器中固定的中心点y坐标(绝对位置)
|
||||
"""
|
||||
self._original_pixmap = pixmap
|
||||
if pixmap.isNull():
|
||||
print("错误:搅拌桨图片加载失败!")
|
||||
return
|
||||
# 记录原始图片自身的中心点(用于旋转计算)
|
||||
self._original_center_x = 28 # 图片的中心点为 28,28
|
||||
self._original_center_y = 28
|
||||
# 记录在父容器中的固定中心点(旋转时始终对齐这个点)
|
||||
self._fixed_center_in_parent_x = fixed_center_x
|
||||
self._fixed_center_in_parent_y = fixed_center_y
|
||||
# 初始显示图片
|
||||
self.setPixmap(pixmap)
|
||||
# 初始位置:让原始图片的中心点与固定中心点对齐
|
||||
self._update_position(pixmap.width(), pixmap.height())
|
||||
|
||||
def _update_position(self, current_w, current_h):
|
||||
"""根据当前图片尺寸,计算位置使中心点与固定坐标对齐"""
|
||||
# 当前图片的中心点坐标(自身坐标系)
|
||||
current_center_x = current_w / 2
|
||||
current_center_y = current_h / 2
|
||||
# 计算左上角坐标:固定中心点 - 当前图片中心点
|
||||
x = self._fixed_center_in_parent_x - current_center_x
|
||||
y = self._fixed_center_in_parent_y - current_center_y
|
||||
self.move(round(x), round(y)) # 取整避免浮点数位置偏差
|
||||
self.setFixedSize(current_w, current_h)
|
||||
|
||||
def get_rotation(self):
|
||||
return self._rotation
|
||||
|
||||
def set_rotation(self, angle):
|
||||
self._rotation = angle
|
||||
if self._original_pixmap is None:
|
||||
return
|
||||
|
||||
# 生成旋转后的图片(保持旋转中心为原始图片中心)
|
||||
transform = QTransform()
|
||||
transform.translate(self._original_center_x, self._original_center_y)
|
||||
transform.rotate(angle)
|
||||
transform.translate(-self._original_center_x, -self._original_center_y)
|
||||
rotated_pixmap = self._original_pixmap.transformed(transform, Qt.SmoothTransformation)
|
||||
|
||||
# 强制对齐固定中心点(关键:无论尺寸如何变化,中心点不变)
|
||||
self._update_position(rotated_pixmap.width(), rotated_pixmap.height())
|
||||
self.setPixmap(rotated_pixmap)
|
||||
|
||||
rotation = Property(float, get_rotation, set_rotation)
|
||||
|
||||
def reset_to_original(self):
|
||||
self._rotation = 0.0 # 重置旋转角度为0°
|
||||
if self._original_pixmap is not None:
|
||||
self.setPixmap(self._original_pixmap) # 恢复原始图片
|
||||
# 恢复初始位置(基于原始图片尺寸)
|
||||
self._update_position(self._original_pixmap.width(), self._original_pixmap.height())
|
||||
|
||||
class MixerWidget(QWidget):
|
||||
def __init__(self, parent=None):
|
||||
super().__init__(parent)
|
||||
|
||||
# 两个搅拌桨的转动的动画引用
|
||||
self.animations = [] # 保存动画引用
|
||||
|
||||
# 初始化布局
|
||||
layout = QHBoxLayout(self)
|
||||
layout.setContentsMargins(0, 0, 0, 0)
|
||||
@ -28,35 +102,71 @@ class MixerWidget(QWidget):
|
||||
""")
|
||||
layout.addWidget(self.text_label, alignment=Qt.AlignLeft)
|
||||
|
||||
# 2. 创建搅拌机设备及搅拌桨图标
|
||||
# 2. 创建搅拌机设备
|
||||
self.device_label = QLabel()
|
||||
device_pixmap = QPixmap(ImagePaths.MIXER)
|
||||
self.device_label.setPixmap(device_pixmap)
|
||||
layout.addWidget(self.device_label, alignment=Qt.AlignLeft)
|
||||
|
||||
# 3. 叠加两个搅拌桨图标
|
||||
self.blade1 = QLabel(self.device_label) # 从左往右第一个搅拌桨
|
||||
blade1_pixmap = QPixmap(ImagePaths.MIXER_PADDLE)
|
||||
self.blade1.setPixmap(blade1_pixmap)
|
||||
self.blade1.move(
|
||||
(device_pixmap.width() - blade1_pixmap.width()) // 2 - 26,
|
||||
(device_pixmap.height() - blade1_pixmap.height()) // 2 - 4
|
||||
)
|
||||
# 3. 初始化两个搅拌桨
|
||||
self._init_blades()
|
||||
|
||||
self.blade2 = QLabel(self.device_label)
|
||||
blade2_pixmap = QPixmap(ImagePaths.MIXER_PADDLE) # 从左往右第二个搅拌桨
|
||||
self.blade2.setPixmap(blade2_pixmap)
|
||||
self.blade2.move(
|
||||
(device_pixmap.width() - blade2_pixmap.width()) // 2 + 31,
|
||||
(device_pixmap.height() - blade2_pixmap.height()) // 2 - 4
|
||||
)
|
||||
def _init_blades(self):
|
||||
blade_pixmap = QPixmap(ImagePaths.MIXER_PADDLE)
|
||||
if blade_pixmap.isNull():
|
||||
return
|
||||
|
||||
# 测试代码
|
||||
if __name__ == "__main__":
|
||||
import sys
|
||||
from PySide6.QtWidgets import QApplication, QMainWindow
|
||||
# 设备背景的尺寸(用于计算固定中心点)
|
||||
device_pixmap = self.device_label.pixmap()
|
||||
if not device_pixmap:
|
||||
return
|
||||
device_w = device_pixmap.width()
|
||||
device_h = device_pixmap.height()
|
||||
|
||||
app = QApplication(sys.argv)
|
||||
mixer_widget = MixerWidget()
|
||||
mixer_widget.show()
|
||||
sys.exit(app.exec())
|
||||
# --------------------------
|
||||
# 左搅拌桨:计算固定中心点
|
||||
# --------------------------
|
||||
left_center_x = (device_w // 2) - 26 # 左桨中心点x(示例值,需根据实际调整)
|
||||
left_center_y = device_h // 2 - 5 # 左桨中心点y(示例值,需根据实际调整)
|
||||
self.blade1 = BladeLabel(self.device_label)
|
||||
self.blade1.set_original_pixmap(blade_pixmap, left_center_x, left_center_y)
|
||||
|
||||
# --------------------------
|
||||
# 右搅拌桨:计算固定中心点
|
||||
# --------------------------
|
||||
right_center_x = (device_w // 2) + 30 # 右桨中心点x(示例值,需根据实际调整)
|
||||
right_center_y = device_h // 2 - 5 # 右桨中心点y(与左桨对齐)
|
||||
self.blade2 = BladeLabel(self.device_label)
|
||||
self.blade2.set_original_pixmap(blade_pixmap, right_center_x, right_center_y)
|
||||
|
||||
def _start_animation(self, blade: BladeLabel, duration: int, reverse: bool = False):
|
||||
"""
|
||||
Args:
|
||||
blade: 所需旋转的搅拌桨标签
|
||||
duration 一次搅拌桨旋转所需的时间,值越小,旋转越快
|
||||
reverse: 是否反转(逆时针转)
|
||||
"""
|
||||
animation = QPropertyAnimation(blade, b"rotation")
|
||||
animation.setStartValue(360 if reverse else 0)
|
||||
animation.setEndValue(0 if reverse else 360)
|
||||
animation.setDuration(duration)
|
||||
animation.setEasingCurve(QEasingCurve.Linear)
|
||||
animation.setLoopCount(-1)
|
||||
self.animations.append(animation)
|
||||
animation.start()
|
||||
|
||||
# 搅拌桨开始搅拌
|
||||
def startBladeMix(self, duration=700):
|
||||
self.animations.clear()
|
||||
# 备注:duration控制搅拌桨旋转的速度,值越小旋转得越快
|
||||
self._start_animation(self.blade1, duration)
|
||||
self._start_animation(self.blade2, duration)
|
||||
|
||||
def stopBladeMix(self):
|
||||
for animation in self.animations:
|
||||
animation.stop()
|
||||
|
||||
if self.blade1:
|
||||
self.blade1.reset_to_original()
|
||||
if self.blade2:
|
||||
self.blade2.reset_to_original()
|
||||
|
||||
Reference in New Issue
Block a user