PyQt5 按钮点击动画

Posted

技术标签:

【中文标题】PyQt5 按钮点击动画【英文标题】:PyQt5 button click animation 【发布时间】:2017-05-18 11:31:43 【问题描述】:

早上好。

问题 1 在我的代码中,我试图让它当你点击一个按钮时,它会闪烁红色几毫秒。

如你所见,我有一个淡入淡出和不淡出的功能。淡入淡出函数如何知道它必须更改调用该函数的按钮的样式表?

from PyQt5.QtCore import (Qt, QTimer)
from PyQt5.QtWidgets import (QWidget, QLCDNumber, QSlider, QVBoxLayout, QApplication, QPushButton, QGridLayout, QHBoxLayout, QLabel)
from PyQt5.QtGui import (QFont, QPainter, QColor)


# Font declaration
mainFont = QFont("arial", 18, QFont.Bold)


# Color declaration
"""

backgroundColor = "#2e3436"
buttonColor = "#729fcf"
textColor = "#2e3436"
greenColor = "#27bc10"
redColor = "#d81711"

"""

backgroundColor = "#2e3436"
buttonColor = "#ffffff"
textColor = "#000000"

greenColor = "#27bc10"
redColor = "#d81711"

# main buttons size
mainWidth = 160
mainHeight = 80


# Variable declaration
CurrentSpeed = 1


class MainInterface(QWidget):

    def __init__(self):

        super().__init__()
        self.initUI()

    def initUI(self):




        b1 = QPushButton('Start')
        b1.setFixedWidth(mainWidth)
        b1.setFixedHeight(mainHeight)
        b1.setStyleSheet("background-color: %s; color: %s" % (greenColor, textColor))
        b1.setFont(mainFont)
        b1.clicked.connect(self.fade)

        b2 = QPushButton('Stop')
        b2.setFixedWidth(mainWidth)
        b2.setFixedHeight(mainHeight)
        b2.setStyleSheet("background-color: %s; color: %s" % (redColor, textColor))
        b2.setFont(mainFont)

        b3 = QPushButton('Speed -')
        b3.setFixedWidth(mainWidth)
        b3.setFixedHeight(mainHeight)
        b3.setStyleSheet("background-color: %s; color: %s" % (buttonColor, textColor))
        b3.setFont(mainFont)

        l1 = QLabel(str(CurrentSpeed))
        l1.setStyleSheet("color: white; margin: 15px; border: 2px solid white")
        l1.setFont(mainFont)
        l1.setAlignment(Qt.AlignCenter)

        b4 = QPushButton('Speed +')
        b4.setFixedWidth(mainWidth)
        b4.setFixedHeight(mainHeight)
        b4.setStyleSheet("background-color: %s; color: %s" % (buttonColor, textColor))
        b4.setFont(mainFont)



        grid = QGridLayout()
        grid.setColumnMinimumWidth(50, 400)
        grid.setRowMinimumHeight(10, 250)

        grid.addWidget(b1, 0, 0)
        grid.addWidget(b2, 0, 2)
        grid.addWidget(b3, 1, 0)
        grid.addWidget(l1, 1, 1)
        grid.addWidget(b4, 1, 2)




        self.setStyleSheet("background-color: %s" % backgroundColor)    
        self.setLayout(grid)

        self.setGeometry(300, 200, 850, 450)
        self.setWindowTitle('Signal & slot')
        self.show()

    def fade(self, button):
        button.setWindowOpacity(0.5)
        button.setStyleSheet("background-color: red")
        QTimer.singleShot(300, self.unfade)

    def unfade(self):
        button.setWindowOpacity(1)
        button.setStyleSheet("background-color: #2e3436")







if __name__ == '__main__':
    import sys
    app = QApplication(sys.argv)    
    ex = MainInterface()
    sys.exit(app.exec_())

问题 2

更高级,如何在按钮上制作类似于点击手机锁屏时的动画?

提前致谢。

【问题讨论】:

【参考方案1】:

首先,slots 可以调用self.sender() 来找出发出信号的对象。

接下来,您必须注意信号有效负载,在这种情况下,它是可选的“已检查 True/False”,因此 button 不是 fade() 插槽的有效参数。

也建议用pyqtSlot装饰槽,没有缺点,即使它的优点现在不相关,它们也会在以后(并且在不使用装饰器时为您节省一些与信号处理相关的错误,如贴在邮件列表中)。正如ehkumoro所指出的,由于checked是可选的并且你不使用它,所以用pyqtSlot()来装饰就足够了。

最后,unfade() 需要知道要取消淡化哪个按钮;由 eyllanesc 完成的 lambda 很好,但我将展示如何使用数据成员执行此操作,其优点是它在 MainInterface 上扮演“状态标志”的角色。 IE。当不是 None 时,表示MainInterface 小部件“当前正在淡出一个按钮”;当您的小部件响应在fade() 结束和unfade() 开始之间发生的事件时,这通常会派上用场,例如再次单击(小部件需要测试它是否已经淡出另一个按钮)。

def __init__(self):
    ...
    self.__fading_button = None

@pyqtSlot()
def fade(self):
    self.__fading_button = self.sender()  # enter the "fading button" state
    self.__fading_button.setWindowOpacity(0.5)
    self.__fading_button.setStyleSheet("background-color: red")
    QTimer.singleShot(300, self.unfade)

def unfade(self):
    self.__fading_button.setWindowOpacity(1)
    self.__fading_button.setStyleSheet("background-color: #2e3436")
    self.__fading_button = None  # exit the "fading button" state

【讨论】:

对于像clicked(bool checked=false) 这样的信号,可以使用@pyqtSlot(),这样可以消除死参数。

以上是关于PyQt5 按钮点击动画的主要内容,如果未能解决你的问题,请参考以下文章

PyQt5:在 Qmovie 中重新加载 gif

PyQt5 样式表动画

PyQt5 无需点击任何按钮或点击任何内容即可终止应用程序

PYQT5中如何将按钮点击连接的结果输出到界面上

PyQt5使用多线程防止卡死

PyQt5 QDialog隐藏问号按钮