Как проверить, закрыт ли QWidget в QMainWindow?

#python #python-3.x #pyqt #pyqt5

Вопрос:

У меня есть два файла:

main.py

 from un import Ui_Form
...
class ExampleApp(QtWidgets.QMainWindow, design.Ui_MainWindow):
   def __init__(self):
     super().__init__()
     self.show_btn.clicked.connect(self.show_btn_fun)
     ...
   def double_opening(self):
     #this method passes data for my requests to self.window 
     for idx in self.tableView.selectionModel().selectedIndexes():
        row_number = idx.row()
        column_number = idx.column()
        self.window = QtWidgets.QWidget()
        self.text_to_change = format(self.tableView.model().index(row_number, 2).data())
        self.ui = Ui_Form(self.text_to_change)
        self.ui.setupUi(self.window)
        self.window.setWindowModality(QtCore.Qt.ApplicationModal)
        self.window.show()

    def show_btn_fun(self):  
        #show the entire existing table
...
def main():
app = QtWidgets.QApplication(sys.argv)  
window = ExampleApp()  
window.show() 
app.exec_()
if __name__ == '__main__':  
main() 
 

и un.py:

 class Ui_Form(object):
   def setupUi(self, Form):
      Form.setObjectName("Form")
      ...
      self.button_changes_confirm.clicked.connect(self.changes)
      self.button_changes_confirm.clicked.connect(Form.close)
      ...
   def changes(self):
      #makes my update to the database
 

после того, как я нажму «button_changes_confirm», данные в моей базе данных будут обновлены

но чтобы увидеть, что данные обновлены, мне нужно вызвать метод «show_bug_fun» с помощью кнопки «show_btn» .

как вызвать метод «show_btn_fun», когда «self.window» закрывается?

Комментарии:

1. Я вижу цикл for double_opening , вы уверены, что хотите показать окно для каждого выбранного индекса? В любом случае, для этого вам следует использовать QDialog, так как это упростит задачу. Кроме того, вы не должны редактировать файлы, созданные pyuic. Читать с помощью конструктора

2. я показываю окно для выбранного индекса. «Кроме того, вы не должны редактировать файлы, созданные pyuic» — почему?

3. Существуют различные причины: 1. всякий раз, когда вам нужно изменить пользовательский интерфейс в конструкторе, вам приходится перестраивать файл, поэтому вы либо рискуете перезаписать и потерять свои изменения, либо вам придется каждый раз объединять изменения (что означает, что вы потенциально можете вносить ошибки из-за опечаток, неправильного копирования/вставки или забытых функций); 2. нет никакой пользы в изменении этих файлов, так как рано или поздно вам все равно понадобится подкласс; 3. это обычно приводит к недоразумениям и неожиданному поведению в структуре объекта; 4. они не являются классами на основе Qt (QObject), поэтому у них не может быть сигналов и свойства;

4. 5. поскольку они не являются классами Qt, они не позволяют переопределять методы виджетов Qt, поэтому вам все равно нужно подкласс виджета Qt; 6. они не содержат ссылки на виджет, на котором они построены, поэтому реализация функций, требующих ссылки, делает вещи излишне сложными. Редактирование этих файлов (или имитация их поведения, или «слияние» их функций) считается плохой практикой, поскольку это не дает никакой реальной выгоды и только создает вышеуказанные проблемы. Вы должны рассматривать их просто как «файлы ресурсов», которые используются вашей программой и используются такими, какие они есть, не более того.

5. не уверен в этом, но мог бы переопределить вашу Ui_Form(объект) —> def closeEvent(self, событие): для вызова вашего метода. Смотрите здесь в качестве примера learndataanalysis.org/…

Ответ №1:

вот моя попытка, вызов кнопки, когда форма закрыта:

 mainwin.py  (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.pushButton_1 = QtWidgets.QPushButton(self.centralwidget)
        self.pushButton_1.setGeometry(QtCore.QRect(280, 30, 261, 131))
        self.pushButton_1.setObjectName("pushButton_1")
        self.pushButton_2 = QtWidgets.QPushButton(self.centralwidget)
        self.pushButton_2.setGeometry(QtCore.QRect(280, 220, 261, 131))
        self.pushButton_2.setObjectName("pushButton_2")
        MainWindow.setCentralWidget(self.centralwidget)
        self.menubar = QtWidgets.QMenuBar(MainWindow)
        self.menubar.setGeometry(QtCore.QRect(0, 0, 800, 29))
        self.menubar.setObjectName("menubar")
        MainWindow.setMenuBar(self.menubar)
        self.statusbar = QtWidgets.QStatusBar(MainWindow)
        self.statusbar.setObjectName("statusbar")
        MainWindow.setStatusBar(self.statusbar)

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

    def retranslateUi(self, MainWindow):
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
        self.pushButton_1.setText(_translate("MainWindow", "PushButton"))
        self.pushButton_2.setText(_translate("MainWindow", "PushButton"))
 

форма, скопированная с https://gitpress.io/u/1155/pyqt-example-ui_form

 form3      :
 
 """

copied from https://gitpress.io/u/1155/pyqt-example-ui_form

"""

from PyQt5 import QtCore, QtGui, QtWidgets

class Ui_Form(object):
    def setupUi(self, Form):
        
        Form.setWindowModality(QtCore.Qt.ApplicationModal)
        
        Form.setObjectName("Form")
        Form.resize(545, 471)
        self.gridLayout = QtWidgets.QGridLayout(Form)
        self.gridLayout.setObjectName("gridLayout")
        self.easingCurvePicker = QtWidgets.QListWidget(Form)
        sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Preferred)
        sizePolicy.setHorizontalStretch(0)
        sizePolicy.setVerticalStretch(0)
        sizePolicy.setHeightForWidth(self.easingCurvePicker.sizePolicy().hasHeightForWidth())
        self.easingCurvePicker.setSizePolicy(sizePolicy)
        self.easingCurvePicker.setMaximumSize(QtCore.QSize(16777215, 120))
        self.easingCurvePicker.setVerticalScrollBarPolicy(QtCore.Qt.ScrollBarAlwaysOff)
        self.easingCurvePicker.setMovement(QtWidgets.QListView.Static)
        self.easingCurvePicker.setProperty("isWrapping", False)
        self.easingCurvePicker.setViewMode(QtWidgets.QListView.IconMode)
        self.easingCurvePicker.setSelectionRectVisible(False)
        self.easingCurvePicker.setObjectName("easingCurvePicker")
        self.gridLayout.addWidget(self.easingCurvePicker, 0, 0, 1, 2)
        self.verticalLayout = QtWidgets.QVBoxLayout()
        self.verticalLayout.setObjectName("verticalLayout")
        self.groupBox_2 = QtWidgets.QGroupBox(Form)
        self.groupBox_2.setMaximumSize(QtCore.QSize(16777215, 16777215))
        self.groupBox_2.setObjectName("groupBox_2")
        self.gridLayout_2 = QtWidgets.QGridLayout(self.groupBox_2)
        self.gridLayout_2.setObjectName("gridLayout_2")
        self.lineRadio = QtWidgets.QRadioButton(self.groupBox_2)
        self.lineRadio.setMaximumSize(QtCore.QSize(16777215, 40))
        self.lineRadio.setLayoutDirection(QtCore.Qt.LeftToRight)
        self.lineRadio.setChecked(True)
        self.lineRadio.setObjectName("lineRadio")
        self.buttonGroup = QtWidgets.QButtonGroup(Form)
        self.buttonGroup.setObjectName("buttonGroup")
        self.buttonGroup.addButton(self.lineRadio)
        self.gridLayout_2.addWidget(self.lineRadio, 0, 0, 1, 1)
        self.circleRadio = QtWidgets.QRadioButton(self.groupBox_2)
        self.circleRadio.setMaximumSize(QtCore.QSize(16777215, 40))
        self.circleRadio.setObjectName("circleRadio")
        self.buttonGroup.addButton(self.circleRadio)
        self.gridLayout_2.addWidget(self.circleRadio, 1, 0, 1, 1)
        self.verticalLayout.addWidget(self.groupBox_2)
        self.groupBox = QtWidgets.QGroupBox(Form)
        sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Fixed, QtWidgets.QSizePolicy.Preferred)
        sizePolicy.setHorizontalStretch(0)
        sizePolicy.setVerticalStretch(0)
        sizePolicy.setHeightForWidth(self.groupBox.sizePolicy().hasHeightForWidth())
        self.groupBox.setSizePolicy(sizePolicy)
        self.groupBox.setObjectName("groupBox")
        self.formLayout = QtWidgets.QFormLayout(self.groupBox)
        self.formLayout.setFieldGrowthPolicy(QtWidgets.QFormLayout.AllNonFixedFieldsGrow)
        self.formLayout.setObjectName("formLayout")
        self.label = QtWidgets.QLabel(self.groupBox)
        sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Preferred, QtWidgets.QSizePolicy.Preferred)
        sizePolicy.setHorizontalStretch(0)
        sizePolicy.setVerticalStretch(0)
        sizePolicy.setHeightForWidth(self.label.sizePolicy().hasHeightForWidth())
        self.label.setSizePolicy(sizePolicy)
        self.label.setMinimumSize(QtCore.QSize(0, 30))
        self.label.setObjectName("label")
        self.formLayout.setWidget(0, QtWidgets.QFormLayout.LabelRole, self.label)
        self.periodSpinBox = QtWidgets.QDoubleSpinBox(self.groupBox)
        self.periodSpinBox.setEnabled(False)
        sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Minimum, QtWidgets.QSizePolicy.Fixed)
        sizePolicy.setHorizontalStretch(0)
        sizePolicy.setVerticalStretch(0)
        sizePolicy.setHeightForWidth(self.periodSpinBox.sizePolicy().hasHeightForWidth())
        self.periodSpinBox.setSizePolicy(sizePolicy)
        self.periodSpinBox.setMinimumSize(QtCore.QSize(0, 30))
        self.periodSpinBox.setMinimum(-1.0)
        self.periodSpinBox.setSingleStep(0.1)
        self.periodSpinBox.setProperty("value", -1.0)
        self.periodSpinBox.setObjectName("periodSpinBox")
        self.formLayout.setWidget(0, QtWidgets.QFormLayout.FieldRole, self.periodSpinBox)
        self.amplitudeSpinBox = QtWidgets.QDoubleSpinBox(self.groupBox)
        self.amplitudeSpinBox.setEnabled(False)
        self.amplitudeSpinBox.setMinimumSize(QtCore.QSize(0, 30))
        self.amplitudeSpinBox.setMinimum(-1.0)
        self.amplitudeSpinBox.setSingleStep(0.1)
        self.amplitudeSpinBox.setProperty("value", -1.0)
        self.amplitudeSpinBox.setObjectName("amplitudeSpinBox")
        self.formLayout.setWidget(2, QtWidgets.QFormLayout.FieldRole, self.amplitudeSpinBox)
        self.label_3 = QtWidgets.QLabel(self.groupBox)
        self.label_3.setMinimumSize(QtCore.QSize(0, 30))
        self.label_3.setObjectName("label_3")
        self.formLayout.setWidget(4, QtWidgets.QFormLayout.LabelRole, self.label_3)
        self.overshootSpinBox = QtWidgets.QDoubleSpinBox(self.groupBox)
        self.overshootSpinBox.setEnabled(False)
        self.overshootSpinBox.setMinimumSize(QtCore.QSize(0, 30))
        self.overshootSpinBox.setMinimum(-1.0)
        self.overshootSpinBox.setSingleStep(0.1)
        self.overshootSpinBox.setProperty("value", -1.0)
        self.overshootSpinBox.setObjectName("overshootSpinBox")
        self.formLayout.setWidget(4, QtWidgets.QFormLayout.FieldRole, self.overshootSpinBox)
        self.label_2 = QtWidgets.QLabel(self.groupBox)
        self.label_2.setMinimumSize(QtCore.QSize(0, 30))
        self.label_2.setObjectName("label_2")
        self.formLayout.setWidget(2, QtWidgets.QFormLayout.LabelRole, self.label_2)
        self.verticalLayout.addWidget(self.groupBox)
        spacerItem = QtWidgets.QSpacerItem(20, 40, QtWidgets.QSizePolicy.Minimum, QtWidgets.QSizePolicy.Expanding)
        self.verticalLayout.addItem(spacerItem)
        self.gridLayout.addLayout(self.verticalLayout, 1, 0, 1, 1)
        self.graphicsView = QtWidgets.QGraphicsView(Form)
        sizePolicy = QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Expanding)
        sizePolicy.setHorizontalStretch(0)
        sizePolicy.setVerticalStretch(0)
        sizePolicy.setHeightForWidth(self.graphicsView.sizePolicy().hasHeightForWidth())
        self.graphicsView.setSizePolicy(sizePolicy)
        self.graphicsView.setObjectName("graphicsView")
        self.gridLayout.addWidget(self.graphicsView, 1, 1, 1, 1)


        self.pushButton_1 = QtWidgets.QPushButton(self)
        self.pushButton_1.setObjectName("pushButton_1") 
        self.pushButton_1.setMinimumSize(QtCore.QSize(0, 30))
        self.pushButton_1.setGeometry(QtCore.QRect(20, 390, 120, 60))
        self.pushButton_1.setObjectName("pushButton_1")
 
        self.retranslateUi(Form)
        QtCore.QMetaObject.connectSlotsByName(Form)

    def retranslateUi(self, Form):
        _translate = QtCore.QCoreApplication.translate
        Form.setWindowTitle(_translate("Form", "Easing curves"))
        self.groupBox_2.setTitle(_translate("Form", "Path type"))
        self.lineRadio.setText(_translate("Form", "Line"))
        self.circleRadio.setText(_translate("Form", "Circle"))
        self.groupBox.setTitle(_translate("Form", "Properties"))
        self.label.setText(_translate("Form", "Period"))
        self.label_3.setText(_translate("Form", "Overshoot"))
        self.label_2.setText(_translate("Form", "Amplitude"))
        
        self.pushButton_1.setText(_translate("Form", "Close Here"))


 

мой код , main.py :

 import sys 

from mainwin import Ui_MainWindow

from form3b import Ui_Form

from PyQt5 import QtWidgets



class Form(QtWidgets.QWidget, Ui_Form):
    def __init__(self, *args, **kwargs):
        super(Form, self).__init__(*args, **kwargs)
        self.setupUi(self)
        
        self.show()   
        
        self.pushButton_1.clicked.connect(self.pushButton_1_Pressed)
        
    def pushButton_1_Pressed(self):
        
        self.close()
        
    def closeEvent(self, event):
        
        MainWindow.pushButton_2_Pressed(self)
        
        print('closing')
        

class MainWindow(QtWidgets.QMainWindow, Ui_MainWindow):
    def __init__(self, *args, **kwargs):
        super(MainWindow, self).__init__(*args, **kwargs)
        self.setupUi(self)
        
        self.pushButton_1.clicked.connect(self.pushButton_1_Pressed)
        
        self.pushButton_2.clicked.connect(self.pushButton_2_Pressed)
        
        

        
    def pushButton_1_Pressed(self):
        
        self.x = Form()
        
        # self.x.show() # its in Form init already
    
    
    def pushButton_2_Pressed(self):
        
        print('button 2 pressed')
        

                
if __name__ == "__main__":
    
    app = QtWidgets.QApplication(sys.argv)

    window = MainWindow()
    window.show()
    
    sys.exit(app.exec_())
 

нажатие верхней кнопки открывает форму, при закрытии формы (X в правом верхнем углу) получаем print('closing') и открываем нижнюю кнопку print('button 2 pressed') главного окна , нажатие кнопки на форме («Закрыть здесь») похоже на закрытие формы.