切换按钮动画在 PyQt 中不起作用?
Toggle button animation not working in PyQt?
我正在关注有关创建动画切换按钮的 YouTube 教程。这是代码,但它不起作用。我想 @property
有问题,但我不确定。
import sys
from PyQt5.QtCore import *
from PyQt5.QtGui import *
from PyQt5.QtWidgets import *
class ToggleButton(QCheckBox):
def __init__(self,
width = 70,
bgColor = '#777',
circleColor = '#DDD',
activeColor = '#00BCff',
animationCurve = QEasingCurve.OutBounce
):
QCheckBox.__init__(self)
self.setFixedSize(width, 40)
self.setCursor(Qt.PointingHandCursor)
self._bg_color = bgColor
self._circle_color = circleColor
self._active_color = activeColor
self._circle_position = 3
self.animation = QPropertyAnimation(self, b"circle_position")
self.animation.setEasingCurve(animationCurve)
self.animation.setDirection(500)
self.stateChanged.connect(self.start_transition)
@property
def circle_position(self):
return self._circle_position
@circle_position.setter
def circle_position(self, pos):
self._circle_position = pos
self.update()
def start_transition(self, value):
print(self.isChecked())
self.animation.stop()
if value:
self.animation.setEndValue(self.width() - 26)
else:
self.animation.setEndValue(3)
self.animation.start()
def hitButton(self, pos: QPoint):
return self.contentsRect().contains(pos)
def paintEvent(self, e):
p = QPainter(self)
p.setRenderHint(QPainter.Antialiasing)
p.setPen(Qt.NoPen)
rect = QRect(0, 0, self.width(), self.height())
if not self.isChecked():
p.setBrush(QColor(self._bg_color))
p.drawRoundedRect(0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)
else:
p.setBrush(QColor(self._active_color))
p.drawRoundedRect(0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)
p.end()
class window(QMainWindow):
def __init__(self, parent = None):
super(window, self).__init__(parent)
self.resize(500,500)
self.setWindowTitle("PyQt5")
self.toggleBtn = ToggleButton()
self.container = QFrame()
self.layout = QVBoxLayout()
self.layout.addWidget(self.toggleBtn, Qt.AlignCenter, Qt.AlignCenter)
self.container.setLayout(self.layout)
self.setCentralWidget(self.container)
def main():
app = QApplication(sys.argv)
ex = window()
ex.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
感谢您的帮助
如果您 运行 代码,您将收到以下警告:
QPropertyAnimation: you're trying to animate a non-existing property circle_position of your QObject
QPropertyAnimation 仅适用于 Qt 属性,不适用于 python 属性,因此它会失败,我们会收到该警告。此外,在处理过渡时还有其他错误,还有一个错字,因为使用了方向而不是持续时间。
class ToggleButton(QCheckBox):
def __init__(
self,
width=70,
bgColor="#777",
circleColor="#DDD",
activeColor="#00BCff",
animationCurve=QEasingCurve.OutBounce,
):
QCheckBox.__init__(self)
self.setFixedSize(width, 40)
self.setCursor(Qt.PointingHandCursor)
self._bg_color = bgColor
self._circle_color = circleColor
self._active_color = activeColor
self._circle_position = 3
self.animation = QPropertyAnimation(self, b"circle_position")
self.animation.setEasingCurve(animationCurve)
self.animation.setDuration(500)
self.stateChanged.connect(self.start_transition)
@pyqtProperty(int)
def circle_position(self):
return self._circle_position
@circle_position.setter
def circle_position(self, pos):
self._circle_position = pos
self.update()
def start_transition(self, value):
self.animation.setStartValue(self.circle_position)
if value:
self.animation.setEndValue(self.width() - 35)
else:
self.animation.setEndValue(3)
self.animation.start()
def hitButton(self, pos: QPoint):
return self.contentsRect().contains(pos)
def paintEvent(self, e):
p = QPainter(self)
p.setRenderHint(QPainter.Antialiasing)
p.setPen(Qt.NoPen)
rect = QRect(0, 0, self.width(), self.height())
if not self.isChecked():
p.setBrush(QColor(self._bg_color))
p.drawRoundedRect(
0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2
)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)
else:
p.setBrush(QColor(self._active_color))
p.drawRoundedRect(
0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2
)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)
我正在关注有关创建动画切换按钮的 YouTube 教程。这是代码,但它不起作用。我想 @property
有问题,但我不确定。
import sys
from PyQt5.QtCore import *
from PyQt5.QtGui import *
from PyQt5.QtWidgets import *
class ToggleButton(QCheckBox):
def __init__(self,
width = 70,
bgColor = '#777',
circleColor = '#DDD',
activeColor = '#00BCff',
animationCurve = QEasingCurve.OutBounce
):
QCheckBox.__init__(self)
self.setFixedSize(width, 40)
self.setCursor(Qt.PointingHandCursor)
self._bg_color = bgColor
self._circle_color = circleColor
self._active_color = activeColor
self._circle_position = 3
self.animation = QPropertyAnimation(self, b"circle_position")
self.animation.setEasingCurve(animationCurve)
self.animation.setDirection(500)
self.stateChanged.connect(self.start_transition)
@property
def circle_position(self):
return self._circle_position
@circle_position.setter
def circle_position(self, pos):
self._circle_position = pos
self.update()
def start_transition(self, value):
print(self.isChecked())
self.animation.stop()
if value:
self.animation.setEndValue(self.width() - 26)
else:
self.animation.setEndValue(3)
self.animation.start()
def hitButton(self, pos: QPoint):
return self.contentsRect().contains(pos)
def paintEvent(self, e):
p = QPainter(self)
p.setRenderHint(QPainter.Antialiasing)
p.setPen(Qt.NoPen)
rect = QRect(0, 0, self.width(), self.height())
if not self.isChecked():
p.setBrush(QColor(self._bg_color))
p.drawRoundedRect(0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)
else:
p.setBrush(QColor(self._active_color))
p.drawRoundedRect(0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)
p.end()
class window(QMainWindow):
def __init__(self, parent = None):
super(window, self).__init__(parent)
self.resize(500,500)
self.setWindowTitle("PyQt5")
self.toggleBtn = ToggleButton()
self.container = QFrame()
self.layout = QVBoxLayout()
self.layout.addWidget(self.toggleBtn, Qt.AlignCenter, Qt.AlignCenter)
self.container.setLayout(self.layout)
self.setCentralWidget(self.container)
def main():
app = QApplication(sys.argv)
ex = window()
ex.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
感谢您的帮助
如果您 运行 代码,您将收到以下警告:
QPropertyAnimation: you're trying to animate a non-existing property circle_position of your QObject
QPropertyAnimation 仅适用于 Qt 属性,不适用于 python 属性,因此它会失败,我们会收到该警告。此外,在处理过渡时还有其他错误,还有一个错字,因为使用了方向而不是持续时间。
class ToggleButton(QCheckBox):
def __init__(
self,
width=70,
bgColor="#777",
circleColor="#DDD",
activeColor="#00BCff",
animationCurve=QEasingCurve.OutBounce,
):
QCheckBox.__init__(self)
self.setFixedSize(width, 40)
self.setCursor(Qt.PointingHandCursor)
self._bg_color = bgColor
self._circle_color = circleColor
self._active_color = activeColor
self._circle_position = 3
self.animation = QPropertyAnimation(self, b"circle_position")
self.animation.setEasingCurve(animationCurve)
self.animation.setDuration(500)
self.stateChanged.connect(self.start_transition)
@pyqtProperty(int)
def circle_position(self):
return self._circle_position
@circle_position.setter
def circle_position(self, pos):
self._circle_position = pos
self.update()
def start_transition(self, value):
self.animation.setStartValue(self.circle_position)
if value:
self.animation.setEndValue(self.width() - 35)
else:
self.animation.setEndValue(3)
self.animation.start()
def hitButton(self, pos: QPoint):
return self.contentsRect().contains(pos)
def paintEvent(self, e):
p = QPainter(self)
p.setRenderHint(QPainter.Antialiasing)
p.setPen(Qt.NoPen)
rect = QRect(0, 0, self.width(), self.height())
if not self.isChecked():
p.setBrush(QColor(self._bg_color))
p.drawRoundedRect(
0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2
)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)
else:
p.setBrush(QColor(self._active_color))
p.drawRoundedRect(
0, 0, rect.width(), self.height(), self.height() / 2, self.height() / 2
)
p.setBrush(QColor(self._circle_color))
p.drawEllipse(self._circle_position, 3, 32, 32)