0

I'm currently writing an PYQT5 GUI Application, where it is possible to switch between multiple widgets in the same Main Window. I'm using a QStackedWidget for that, where I've added all the other Widgets. For switching between them, I just set the current Widget of the QStackedWidget. The QStackedWidget is the central Widget of the Main Window. One of the Widgets available in the QStackedWidget has a QListWidget, where I can add multiple custom objects.

The Problem now is, if i add more than one object to the list and then try to change the current Widget of the QStackedWidget, the Application crashes with no error Message.

I'm using Pyqt 5 in Python 3.9.13.

Also I've written a code example, in which the described problem occures. I would really appreciated, if somebody could help me!

Reproduce the Error:

1.) Press the pushButton --> a new View shows up

2.) Add one Item to the List with the Button at the Bottom

3.) Press the pushButton at the Top --> FirstView shows up, everything works fine

4.) Press again the pushButton in the Center

5.) Add further Objects to the List

6.) Press the Button at the Top again --> the Application crashes with no error...

My example Code to reproduce the Error:

App

from PyQt5.QtWidgets import *

from PyQt5.QtWidgets import *

class App(QApplication):
    def __init__(self, argv):
        super().__init__(argv)
        self.setApplicationName("Test")
        self.setOrganizationName("Kai Industries")

Controller View 1

from PyQt5 import *
from PyQt5.QtWidgets import *
from PyQt5 import QtCore
from PyQt5.QtCore import *
from PyQt5.QtGui import *
from Ui_view1 import Ui_View1
from controller_view2 import Controller_View2

class Controller_View1(QWidget, Ui_View1):

    def __init__(self, main, model,previous):
        super().__init__(main)
        QWidget.__init__(self)
        Ui_View1.__init__(self)
        self.setupUi(self)
        self._main = main
        self._model = model
        self._previous = previous
        self._main._controller_view2=Controller_View2(self._main,self._model,self)
        self._main._central_widget.addWidget(self._main._controller_view2)

        self.pushButton_forward.clicked.connect(self.execute_forward)

    def execute_forward(self):
        self._main._central_widget.setCurrentWidget(self._main._controller_view2)

Controller View 2

from PyQt5 import *
from PyQt5.QtWidgets import *
from PyQt5.QtCore import *
from PyQt5.QtGui import *
from Ui_view2 import Ui_View2
from submodel import Submodel
from controller_widget_submodel import Controller_Widget_Submodel

class Controller_View2(QWidget, Ui_View2):

    def __init__(self, main, model,previous):
        super().__init__(main)
        QWidget.__init__(self)
        Ui_View2.__init__(self)
        self.setupUi(self)
        self._main = main
        self._model = model
        self._previous = previous

        self.pushButton_add.clicked.connect(self.execute_add)
        self.pushButton_back.clicked.connect(self.execute_back)

    def execute_add(self):
        submodels = self._model.get_submodels()
        submodel=Submodel()
        submodel.set_value1=1
        submodel.set_value2=2
        submodels.insert(len(submodels),submodel)
        self.actualize_list()

    def execute_back(self):
        self._main._central_widget.setCurrentWidget(self._previous)

    def actualize_list(self):
        self.listWidget.clear()
        submodels = self._model.get_submodels()
        i=0
        for submodel in submodels: 
            list_widget_item = QListWidgetItem(self.listWidget)    
            controller_widget_submodel = Controller_Widget_Submodel(self._main,submodel)
            list_widget_item.setSizeHint(controller_widget_submodel.sizeHint())
            self.listWidget.insertItem(i,list_widget_item)
            self.listWidget.setItemWidget(list_widget_item,controller_widget_submodel)
            i=i+1

Controller widget for ListWidgetItem

from PyQt5 import *
from PyQt5.QtWidgets import *
from PyQt5.QtCore import *
from PyQt5.QtGui import *
from Ui_widget_submodel import Ui_widget_submodel

class Controller_Widget_Submodel(QWidget, Ui_widget_submodel):

    def __init__(self, main, model):
        super().__init__(main)
        QWidget.__init__(self)
        Ui_widget_submodel.__init__(self)
        self.setupUi(self)
        self._main = main
        self._model = model
        self.label_value1.setText(self._model.get_value1())
        self.label_value2.setText(self._model.get_value2())

Controller Main Window

from PyQt5 import *
from PyQt5.QtWidgets import *
from PyQt5.QtCore import *

from controller_view1 import Controller_View1
from model import Model

class Controller_Main(QMainWindow):
    def __init__(self):
        QMainWindow.__init__(self)
        self.showFullScreen()
        self.setFixedSize(QSize(800,480))
        self._model=Model()
        self._central_widget = QStackedWidget()
        self._controller_view1 = Controller_View1(self,self._model,self)
        self._central_widget.addWidget(self._controller_view1)
        self._central_widget.setCurrentWidget(self._controller_view1)

        self.setCentralWidget(self._central_widget)
        self.show()

Main

import sys
from PyQt5.QtCore import *
from app import *
from controller_window import Controller_Main
import cgitb 

cgitb.enable(format = 'text')
QApplication.setAttribute(Qt.AA_EnableHighDpiScaling, True)
QApplication.setAttribute(Qt.AA_UseHighDpiPixmaps, True)
if __name__ == "__main__":
    sys.excepthook = lambda exctype, value, traceback: sys.__excepthook__(exctype, value, traceback)
    app = App(sys.argv)
    #if frozen: _MEIPASS path and every error as messagebox
    try:
        controller_main = Controller_Main()
        sys.exit(app.exec())
    except Exception as e:
        QMessageBox.critical(None , "Error", "An Error occured: " + str(e))

Model

from submodel import Submodel

class Model():
    def __init__(self):
        self._submodels = list()

    def add_submodel(self,submodel:Submodel):
        self._submodels.append(submodel)

    def get_submodels(self):
        return self._submodels   

Submodel

class Submodel():
    def __init__(self):
        self._value1="Test1"
        self._value2="Test2"

    def set_value1(self,value:int):
        self._value1 = value

    def set_value2(self,value:int):
        self._value2 = value

    def get_value2(self):
        return self._value2

    def get_value1(self):
        return self._value1

Ui View 1

from PyQt5 import QtCore, QtGui, QtWidgets

class Ui_View1(object):
    def setupUi(self, View1):
        View1.setObjectName("View1")
        View1.resize(400, 300)
        self.verticalLayout = QtWidgets.QVBoxLayout(View1)
        self.verticalLayout.setObjectName("verticalLayout")
        self.pushButton_forward = QtWidgets.QPushButton(View1)
        self.pushButton_forward.setObjectName("pushButton_forward")
        self.verticalLayout.addWidget(self.pushButton_forward)

        self.retranslateUi(View1)
        QtCore.QMetaObject.connectSlotsByName(View1)

    def retranslateUi(self, View1):
        _translate = QtCore.QCoreApplication.translate
        View1.setWindowTitle(_translate("View1", "Form"))
        self.pushButton_forward.setText(_translate("View1", "PushButton"))

Ui View 2

from PyQt5 import QtCore, QtGui, QtWidgets

class Ui_View2(object):
    def setupUi(self, View2):
        View2.setObjectName("View2")
        View2.resize(400, 300)
        self.verticalLayout = QtWidgets.QVBoxLayout(View2)
        self.verticalLayout.setObjectName("verticalLayout")
        self.pushButton_back = QtWidgets.QPushButton(View2)
        self.pushButton_back.setObjectName("pushButton_back")
        self.verticalLayout.addWidget(self.pushButton_back)
        self.listWidget = QtWidgets.QListWidget(View2)
        self.listWidget.setObjectName("listWidget")
        self.verticalLayout.addWidget(self.listWidget)
        self.pushButton_add = QtWidgets.QPushButton(View2)
        self.pushButton_add.setObjectName("pushButton_add")
        self.verticalLayout.addWidget(self.pushButton_add)

        self.retranslateUi(View2)
        QtCore.QMetaObject.connectSlotsByName(View2)

    def retranslateUi(self, View2):
        _translate = QtCore.QCoreApplication.translate
        View2.setWindowTitle(_translate("View2", "Form"))
        self.pushButton_back.setText(_translate("View2", "Back"))
        self.pushButton_add.setText(_translate("View2", "Add"))

Ui submodel

from PyQt5 import QtCore, QtGui, QtWidgets

class Ui_widget_submodel(object):
    def setupUi(self, widget_submodel):
        widget_submodel.setObjectName("widget_submodel")
        widget_submodel.resize(120, 33)
        self.horizontalLayout_2 = QtWidgets.QHBoxLayout(widget_submodel)
        self.horizontalLayout_2.setObjectName("horizontalLayout_2")
        self.horizontalLayout = QtWidgets.QHBoxLayout()
        self.horizontalLayout.setObjectName("horizontalLayout")
        self.label_value1 = QtWidgets.QLabel(widget_submodel)
        self.label_value1.setObjectName("label_value1")
        self.horizontalLayout.addWidget(self.label_value1)
        self.label_value2 = QtWidgets.QLabel(widget_submodel)
        self.label_value2.setObjectName("label_value2")
        self.horizontalLayout.addWidget(self.label_value2)
        self.horizontalLayout_2.addLayout(self.horizontalLayout)

        self.retranslateUi(widget_submodel)
        QtCore.QMetaObject.connectSlotsByName(widget_submodel)

    def retranslateUi(self, widget_submodel):
        _translate = QtCore.QCoreApplication.translate
        widget_submodel.setWindowTitle(_translate("widget_submodel", "Form"))
        self.label_value1.setText(_translate("widget_submodel", "TextLabel"))
        self.label_value2.setText(_translate("widget_submodel", "TextLabel"))

Ui Main Window

from PyQt5 import QtCore, QtGui, QtWidgets


class Ui_MainWindow(object):
    def setupUi(self, MainWindow):
        MainWindow.setObjectName("MainWindow")
        MainWindow.resize(800, 600)
        self.centralwidget = QtWidgets.QWidget(MainWindow)
        self.centralwidget.setObjectName("centralwidget")
        self.verticalLayout_2 = QtWidgets.QVBoxLayout(self.centralwidget)
        self.verticalLayout_2.setObjectName("verticalLayout_2")
        MainWindow.setCentralWidget(self.centralwidget)

        self.retranslateUi(MainWindow)
        QtCore.QMetaObject.connectSlotsByName(MainWindow)

    def retranslateUi(self, MainWindow):
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
  • Please provide a [mre], not the *full* code. Also, remove all those `__init__()` after each `super` call, as they are wrong. – musicamante Oct 06 '22 at 22:36
  • Please trim your code to make it easier to find your problem. Follow these guidelines to create a [minimal reproducible example](https://stackoverflow.com/help/minimal-reproducible-example). – Community Oct 07 '22 at 04:14
  • @musicamante Hi; While I was writting a smaller Example, I recognized, that removing those inits solved my Problem. Thank you very much! – Kai Schneider Oct 07 '22 at 13:11

0 Answers0