When I work with QPropertyAnimation with 1D array, there is no problem. It accepts all the animation orders. However, I want to clearify my code, because I'll work many images. So I tried to use 2D array for images and its' animations.
Same logic with 1D array (not in the code):
self.animG = []
for i in range(3):
self.animG.append(QPropertyAnimation(self.welcome, b"geometry"))
...
...
...
for i in range(len(self.animG)):
if i == 0:
self.animG[i].setDuration(1000)
self.animG[i].setStartValue(QRect(-1920, 0, 1920, 1080))
self.animG[i].setEndValue(QRect(0, 0, 1920, 1080))
elif i == 1:
self.animG[i].setDuration(2000)
self.animG[i].setStartValue(QRect(0, 0, 1920, 1080))
self.animG[i].setEndValue(QRect(0, 0, 1920, 1080))
else:
self.animG[i].setDuration(1000)
self.animG[i].setStartValue(QRect(0, 0, 1920, 1080))
self.animG[i].setEndValue(QRect(1920, 0, 1920, 1080))
...
...
for i in range(3):
self.anim_group.addAnimation(self.animG[i])
The code above is works perfectly, but I dont want to create these theme for every images. So I think something like below (all code but needed part pointed):
from PyQt5 import QtGui, QtWidgets, QtCore
from PyQt5.QtWidgets import QApplication, QMainWindow, QPushButton, QFrame
from PyQt5.QtCore import QPropertyAnimation, QRect, QPoint
import sys, time
class Window(QMainWindow):
def __init__(self):
super().__init__()
self.title = "Image Slider with PyQt5"
self.InitWindow()
def InitWindow(self):
self.setWindowTitle(self.title)
screenx = QtWidgets.QDesktopWidget().screenGeometry()
print(screenx.width(), screenx.height())
self.welcome = QtWidgets.QLabel(self)
self.pixmapW = QtGui.QPixmap('Raspberry/WELCOME.jpg')
self.welcome.setPixmap(self.pixmapW)
self.label = QtWidgets.QLabel(self)
self.pixmap = QtGui.QPixmap('Raspberry/image.jpg')
self.label.setPixmap(self.pixmap)
self.label2 = QtWidgets.QLabel(self)
self.pixmap2 = QtGui.QPixmap('Raspberry/image2.jpg')
self.label2.setPixmap(self.pixmap2)
self.label.setGeometry(0, -1080, self.pixmap.width(), self.pixmap.height())
self.label2.setGeometry(0, -1080, self.pixmap2.width(), self.pixmap2.height())
self.welcome.setGeometry(0, 0, self.pixmapW.width(), self.pixmapW.height())
self.button = QPushButton("Start", self)
self.button.setGeometry(((screenx.width() - 120)//2), ((screenx.height() - 80)//2), 120, 80)
# QPropertyAnimation decleration
self.propAnim = []
self.propAnim.append(QPropertyAnimation(self.welcome, b"geometry"))
self.propAnim.append(QPropertyAnimation(self.label, b"geometry"))
self.propAnim.append(QPropertyAnimation(self.label2, b"geometry"))
# Defining 2D array for images, and to embed QPropertAnimations
self.imageCount, self.animCount = 3, 3
self.animations = [[0 for x in range(self.imageCount)] for y in range(self.animCount)]
# Embed 3 same animations scene to all images
for i in range(self.imageCount):
for j in range(self.animCount):
self.animations[i][j] = (self.propAnim[i])
self.anim_group = QtCore.QSequentialAnimationGroup()
self.button.clicked.connect(self.doAni)
self.anim_group.finished.connect(self.doAni)
self.showMaximized()
def doAni(self):
self.label.setGeometry(0, -1080, self.pixmap.width(), self.pixmap.height())
self.label2.setGeometry(0, -1080, self.pixmap2.width(), self.pixmap2.height())
self.welcome.setGeometry(0, -1080, self.pixmapW.width(), self.pixmapW.height())
for i in range(self.imageCount):
for j in range(self.animCount):
if j == 0:
self.animations[i][j].setDuration(2000)
self.animations[i][j].setStartValue(QRect(-1920, 0, 1920, 1080))
self.animations[i][j].setEndValue(QRect(0, 0, 1920, 1080))
elif j == 1:
self.animations[i][j].setDuration(2000)
self.animations[i][j].setStartValue(QRect(0, 0, 1920, 1080))
self.animations[i][j].setEndValue(QRect(0, 0, 1920, 1080))
elif j == 2:
self.animations[i][j].setDuration(2000)
self.animations[i][j].setStartValue(QRect(0, 0, 1920, 1080))
self.animations[i][j].setEndValue(QRect(1920, 0, 1920, 1080))
else:
pass
# HERE IS THE PROBLEMATIC PART, IT ONLY AND ONLY ACCEPTS 3rd ANIMATIONS FOR ALL IMAGES
# NORMALLY IT SHOULD MAKE 9 MOVEMENTS TO COMPLETE SCENE
# HOWEVER IT MAKES ONLY 3 MOVEMENTS
for i in range(self.imageCount):
for j in range(self.animCount):
self.anim_group.addAnimation(self.animations[i][j])
self.anim_group.start()
if __name__ == '__main__':
App = QApplication(sys.argv)
window = Window()
sys.exit(App.exec())
As you can see in the last comment part of the code, it have to make 9 animation movements, but it makes only 3 which is last animation of all images!
If you want to have 9 animations, you have to create 9 animations. You're just using 3 and constantly changing their start/end values.
Instead of creating unnecessary lists, just create a single list for the animations, and append them to each item. You also don't need to use instance attributes for the list counts, and you can use a predefined list of values along with zip()
to cycle through both animations and values.
self.animations = []
for i, widget in enumerate((self.welcome, self.label, self.label2)):
widgetAnimations = []
for j in range(self.animCount):
widgetAnimations.append(QPropertyAnimation(widget, b"geometry"))
self.animations.append(widgetAnimations)
# ...
def doAni(self):
values = (
(QRect(-1920, 0, 1920, 1080), QRect(0, 0, 1920, 1080)),
(QRect(0, 0, 1920, 1080), QRect(0, 0, 1920, 1080)),
(QRect(0, 0, 1920, 1080), QRect(1920, 0, 1920, 1080)),
)
for widgetAnimations in self.animations:
for animation, (start, end) in zip(widgetAnimations, values):
animation.setStartValue(start)
animation.setEndValue(end)
animation.setDuration(2000)
self.anim_group.addAnimation(animation)
Remember that if you want to add a "paused" animation, you should use QPauseAnimation.