Python Objektorientierung, PyQt6, Button-Objekte in Listen speichern funktioniert, aber nicht in Matrixen

_anonymous0815_

Lt. Commander
Registriert
Aug. 2020
Beiträge
1.406
Hallo liebes Forum,

ich habe seit Ewigkeiten nicht mehr mit Python programmiert und dann auch noch nicht so ausführlich objektorientiert, ich habe es geschafft, Objekte (Qt-Buttons) in Listen zu speichern. Das ist für horizontale, wie vertikale Menüs/Layouts durchaus ausreichend, aber es gibt noch das sog. Grid-Layout, welches eine Matrix erstellt. Dafür möchte ich auch eine Matrix an die erstellende Funktion übergeben, die mir die Objekte dann auch wieder als Matrix in einer Variable anlegt, damit ich im weiteren Verlauf darauf einzeln zugreifen kann.

Python:
from PyQt6.QtCore import QSize, Qt, QThread, QObject, pyqtSignal, pyqtSlot
from PyQt6.QtWidgets import QApplication, QMainWindow, QPushButton, QWidget, QGridLayout, QHBoxLayout, QVBoxLayout, QLabel
from PyQt6.QtGui import QPalette, QColor

class Buttons():
            def __init__(self, isFlat=False, btnText="empty", sizeWidth=250, sizeHeight=100):
                self.button = QPushButton()
                self.button.setFlat(isFlat)
                self.button.setText(btnText)
                self.button.setGeometry(400, 200, sizeWidth, sizeHeight)
                self.button.setStyleSheet("""
                    QPushButton {
            
                    }

                    QPushButton:active {

                    }
                """)
  
        def createButtonObjects(BtnTxtLst, BtnObjLst, PosLayout, isGrid=False):
            if isGrid == True:
                for idrow, row in enumerate(BtnTxtLst):
                    for idcol, col in enumerate(row):
                        BtnObjLst.append(Buttons(False, col))
                        PosLayout.addWidget(BtnObjLst[idcol].button, idrow, idcol) #To be fixed
                print(BtnObjLst)
            else:
                for id_menu_button, menu_button in enumerate(BtnTxtLst):
                    BtnObjLst.append(Buttons(False, menu_button))
                    PosLayout.addWidget(BtnObjLst[id_menu_button].button)                     

        g_layout = QGridLayout()
    
        GridMenuBtnText = [
            ["Element 0", "Element 1", "Element 2", "Element 3"],
            ["Element 4", "Element 5", "Element 6", "Element 7"],
            ["Element 8", "Element 9", "Element 10", "Element 11"]
        ]

        self.g_m_btnList = []
   
        createButtonObjects(GridMenuBtnText, self.g_m_btnList, g_layout, True)

Und das ist auch der Teil, welcher nicht funktioniert.

Hier z.B. wie die Funktion mit normalen, nicht verschachtelten Listen (Matrixen) umgeht:
Python:
        h_layout = QHBoxLayout()

        HeaderMenuBtnText = ["Menü", "Dies", "Das", "Ananas"]
        self.h_m_btnList = []
        createButtonObjects(HeaderMenuBtnText, self.h_m_btnList, h_layout)

        h_widget = QWidget()
        h_widget.setLayout(h_layout)

Und so sieht das in der Liste aus (einfache Liste):
Code:
[<__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fe8ea286d10>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fe8e2153c50>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fe8e2153e10>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fe8e2153dd0>]

So in der Matrix:
Code:
[<__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03551710>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03551ad0>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553850>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553890>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec035538d0>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553950>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553990>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec035539d0>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553a10>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553910>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553ad0>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fec03553b50>]

Und so als Ausgabe in der GUI:
1728820996704.png


Wie man sieht, spuckt der Code eben nicht alle Reihen der Matrix aus, sondern nur die erste, obwohl alle 12 Buttons als Objekt in der entsprechenden Liste angelegt sind.

Und an dieser Stelle hoffe ich, dass jemand für mich einen Tipp hat, wie genau ich hier die Struktur aus-/einlesen muss, damit ich auf alle Objekte in der Matrix zugreifen kann und diese aber auch in der GUI erstellt werden.

Falls noch weitere Fragen bestehen, dann bitte stellen, falls noch wichtige Infos fehlen, bitte auch darauf aufmerksam machen, dann reiche ich diese nach.

Vielen Dank und viele Grüße!
 
Zuletzt bearbeitet:
So kannst du dir das letzte Element holen: BtnObjLst[-1]

Oder besser einfach lokal zwischenspeichern, um das unnötige erneute auslesen aus der Liste zu ersparen:
button = Buttons(False, col)
BtnObjLst.append(button)
PosLayout.addWidget(button.button, idrow, idcol) #To be fixed
 
  • Gefällt mir
Reaktionen: _anonymous0815_ und tollertyp
Wo bin ich hier schrieb:
So kannst du dir das letzte Element holen: BtnObjLst[-1]
Du hast es gelöst!
Ich sitze hier ungelogen seit mehreren Stunden an diesem einen spezifischen Problem.

Wo bin ich hier schrieb:
Oder besser einfach lokal zwischenspeichern, um das unnötige erneute auslesen aus der Liste zu ersparen:
button = Buttons(False, col)
BtnObjLst.append(button)
PosLayout.addWidget(button.button, idrow, idcol) #To be fixed
Und dann auch noch gleich effiziente Variante! :love:
Erst mal: VIELEN DANK!

1728828308885.png


Und dann bleibt mir noch eine Frage:

Wenn ich an addWidget das temporäre Objekt übergebe, kann ich dieses Objekt dann noch sicher über BtnObjLst erreichen, also bekomme ich mit dem
Code:
BtnObjLst.append(tmpObj)
Die Speicheradresse vom tmpObj in BtnObjLst und hält sich das erstellte Objekt im Speicher, wenn tmpObj mit Beendigung der for-Schleife wieder freigegeben wird?
Ergänzung ()

_anonymous0815_ schrieb:
und hält sich das erstellte Objekt im Speicher, wenn tmpObj mit Beendigung der for-Schleife wieder freigegeben wird
Code:
[<__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070266a10>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070265810>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc0702675d0>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070267610>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070267650>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc0702676d0>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070267710>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070267750>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070267790>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070267690>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc070267850>, <__main__.MainWindow.__init__.<locals>.Buttons object at 0x7fc0702678d0>]
Nice, sieht ganz danach aus!
Ergänzung ()

tollertyp schrieb:
Eine Liste hat auch nur eine Dimension
Bin mir gerade nicht sicher, ob ich Dich richtig verstehe, aber ich kann dennoch eine Liste in einer Liste speichern und so mit:

Liste[0] das erste Feld der Liste lesen
UND mit:
Liste[0][0] das erste Feld der Liste in dem ersten Feld der Liste

Damit ist es nach meinem eingerostetem Verständnis zweidimensional.
 
Zuletzt bearbeitet:
_anonymous0815_ schrieb:
Damit ist es nach meinem eingerostetem Verständnis zweidimensional.
Verschachtelte Listen ermöglichen mehrere Dimensionen, ja.
Jedoch ist jede Liste für sich immer noch eindimensional.
 
  • Gefällt mir
Reaktionen: tollertyp und _anonymous0815_
Kannst du machen. Eine Liste in der Liste bleibt aber eine Liste. Und du müsstest dazu die Liste in einer Liste speichern, was du nicht machst.
BtnObjLst.append(Buttons(False, col))
 
Zuletzt bearbeitet:
  • Gefällt mir
Reaktionen: _anonymous0815_
tollertyp schrieb:
BtnObjLst.append(Buttons(False, col))
Richtig, weil die Instanzvariablen der Klasse damit nicht klar kommen, da ich diese Klasse eigentlich nur für eindimensionale Listen angelegt habe und aber auch den Fall für Grids/Matrixes... whatever abdecken wollte. Eigentlich ging es dann wohl eher darum:

zweidimensionale Namensliste Reihe für Reihe als normale Liste übergeben ---> Objekte anlegen und in zweiter, eindimensionaler Liste speichern ---> aus eindimensionaler Objektliste die sichtbaren Buttons in der GUI erstellen...

Aber ich habe mich da wohl deutlich verrannt.
 
Zuletzt bearbeitet:
Zurück
Oben