I'm new to QT Designer and PyQt, but I seem to be trying to do something either too simple to be mentioned or too rare!
I created a simple window using QT Designer. In that window there is two menu options; one should close the window, the other should open another window.
I converted the ui into a python file with the pyuic5 command.
This is the code I get:
# -*- coding: utf-8 -*-
# Form implementation generated from reading ui file 'Win1.ui'
#
# Created by: PyQt5 UI code generator 5.15.7
#
# WARNING: Any manual changes made to this file will be lost when pyuic5 is
# run again. Do not edit this file unless you know what you are doing.
from PyQt5 import QtCore, QtGui, QtWidgets
class Ui_MainWindow(object):
def setupUi(self, MainWindow):
MainWindow.setObjectName("MainWindow")
MainWindow.resize(441, 305)
self.centralwidget = QtWidgets.QWidget(MainWindow)
self.centralwidget.setObjectName("centralwidget")
MainWindow.setCentralWidget(self.centralwidget)
self.menubar = QtWidgets.QMenuBar(MainWindow)
self.menubar.setGeometry(QtCore.QRect(0, 0, 441, 22))
self.menubar.setObjectName("menubar")
self.menuClosing = QtWidgets.QMenu(self.menubar)
self.menuClosing.setObjectName("menuClosing")
self.menuOpen_Win_2 = QtWidgets.QMenu(self.menubar)
self.menuOpen_Win_2.setObjectName("menuOpen_Win_2")
MainWindow.setMenuBar(self.menubar)
self.statusbar = QtWidgets.QStatusBar(MainWindow)
self.statusbar.setObjectName("statusbar")
MainWindow.setStatusBar(self.statusbar)
self.menubar.addAction(self.menuClosing.menuAction())
self.menubar.addAction(self.menuOpen_Win_2.menuAction())
self.retranslateUi(MainWindow)
self.menuClosing.triggered['QAction*'].connect(MainWindow.close) # type: ignore
self.menuOpen_Win_2.triggered['QAction*'].connect(MainWindow.open) # type: ignore
QtCore.QMetaObject.connectSlotsByName(MainWindow)
def retranslateUi(self, MainWindow):
_translate = QtCore.QCoreApplication.translate
MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
self.menuClosing.setTitle(_translate("MainWindow", "Closing"))
self.menuOpen_Win_2.setTitle(_translate("MainWindow", "Open Win #2"))
if __name__ == "__main__":
import sys
app = QtWidgets.QApplication(sys.argv)
MainWindow = QtWidgets.QMainWindow()
ui = Ui_MainWindow()
ui.setupUi(MainWindow)
MainWindow.show()
sys.exit(app.exec_())
New in QT Designer I have assigned the "close()" slot to Closing and I created a new slot "open()" that I linked to Open Win #2.
Obviously, neither work.
It seems there is a different logic than there is when assigning functions to submenus (where linking close() to it does work).
Does anyone knows how I should go about to do this?
Designer doesn't allow to add basic actions to a QMenuBar.
In fact, both the "Edit Signals/Slots" mode and the "Signal/Slot Editor" only allow interacting with widgets: QActions are not widgets.
The only way to achieve this is by code, and by directly adding a real QAction to the menubar.
Remove those (probably empty) menus from the UI, rebuild the code with pyuic
and then do something like this after (assuming that the output file is named win1.py
):
from PyQt5 import QtWidgets
from win1 import Ui_MainWindow
from win2 import Ui_MainWindow2
class Window(QtWidgets.QMainWindow, Ui_MainWindow):
def __init__(self, parent=None):
super().__init__(parent=parent)
self.setupUi(self)
self.closeAction = QtWidgets.QAction('Closing', self)
self.menuBar().addAction(self.closeAction)
self.openWin2Action = QtWidgets.QAction('Open Win #2', self)
self.menuBar().addAction(self.openWin2Action)
self.closeAction.triggered.connect(self.close)
self.openWin2Action.triggered.connect(self.openWin2)
def openWin2(self):
self.win2 = Window2()
self.win2.show()
class Window2(QtWidgets.QMainWindow, Ui_MainWindow2):
def __init__(self):
super().__init__()
self.setupUi(self)
if __name__ == '__main__':
import sys
app = QtWidgets.QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec())
Notes:
pyuic
output, which, in case you didn't know, must never be directly used or edited, if not for debugging or studying purposes; the above code uses the common practice of multiple inheritance as explained in the official guidelines about using Designer;.ui
file, so it's not a pyuic
fault);triggered
signal of QMenu (similarly to that of QMenuBar) is emitted only when one of its actions is triggered (not the action of the menu itself);MainWindow2
; while you could do from win2 import Ui_MainWindow as Ui_MainWindow2
, it's good practice to set unique object names of top level windows: the output of pyuic
will always be Ui_<objectNameOfTopLevelWindow>
;QApplication.quit
signal;