I have done a GUI interface with Qt designer and compiled the .ui file into a .py file. In main window I have this class:
class Projektdlg(QMainWindow, ui_Projekt.Ui_MainWindow):
def __init__(self, parent=None):
super(Projektdlg, self).__init__(parent)
self.setupUi(self)
self.connect(self.actionCalibration, SIGNAL("triggered()"), self.CalibrationSettings)
I want to open the QDialog from the generated ui_calibration file when clicking on calibration from the tool bar. How to do that?
def CalibrationSettings(self):
Dialog = ui_calibration.Ui_DialogCalibration()
All modules are imported
Try something like this:
class myDialog(QtGui.QDialog, Ui_DialogCalibration):
def __init__(self, parent=None):
super(myDialog, self).__init__(parent)
self.setupUi(self)
Then in your class:
Dialog = myDialog(self)
Then you can call Dialog.show() or Dialog.exec_()
Related
I started out with PyQt5 recently. I wanted to create a custom widget and then insert it into the main window of an application.
The custom Widget:
class ScoreCard(QtWidgets.QWidget):
def __init__(self, parent=None):
super(ScoreCard, self).__init__(parent=parent)
self.setWindowFlags(QtCore.Qt.CustomizeWindowHint)
self.pressing = False
self.init_ui()
self.show()
def init_ui(self):
# Layout in here
And this is the main Application:
from PyQt5.QtWidgets import *
from scorecard import ScoreCard
import sys
class MainWindow(QMainWindow):
def __init__(self):
super().__init__()
self.initUi()
self.show()
def initUi(self):
self.setGeometry(300,300,800,700)
window_layout = QVBoxLayout()
recent_playcard = ScoreCard()
window_layout.addWidget(recent_playcard)
self.setLayout(window_layout)
if __name__ == "__main__":
app = QApplication(sys.argv)
execute = MainWindow()
sys.exit(app.exec_())
Why is it that whenever I run the main Application, the custom widget appears in another window? I even tried removing the frame and setting the parent to none, but none of that changed this behavior. How do I fix this?
Looks like I mixed up QMainWindow and QDialog I should be using a central widget for the main application instead of setting a layout..
I have a main dialog window as shown below
Once the OK button is clicked, second window will open as shown below
I need to trigger the click event of login button frpm the second window. Below is my code. but i doesnt trigger any method.
from .gisedify_support_dialog_login import Ui_Dialog
FORM_CLASS, _ = uic.loadUiType(os.path.join(
os.path.dirname(__file__), 'gisedify_support_dialog_base.ui'))
class GisedifySupportDialog(QtWidgets.QDialog, FORM_CLASS):
def __init__(self, parent=None):
"""Constructor."""
super(GisedifySupportDialog, self).__init__(parent)
# Set up the user interface from Designer through FORM_CLASS.
# After self.setupUi() you can access any designer object by doing
# self.<objectname>, and you can use autoconnect slots - see
# http://qt-project.org/doc/qt-4.8/designer-using-a-ui-file.html
# #widgets-and-dialogs-with-auto-connect
self.setupUi(self)
def open_login_dialog(self):
Dialog = QtWidgets.QDialog()
ui = Ui_Dialog()
ui.setupUi(Dialog)
Dialog.exec_()
ui.login_button.clicked.connect(self.login)
def login(self):
print('success')
class Login_Dialog(QtWidgets.QDialog,Ui_Dialog):
def __init__(self, parent=None):
super(Login_Dialog, self).__init__(parent)
QDialog.exec_() will block until the dialog is closed by the user so you would need to set up any signal-slot connections before you call Dialog.exec_(). When a dialog is closed, it returns 1 when de dialog was accepted, and 0 if not. Closing the dialog does not detroy it (unless you set a flag to do so), so you can retrieve the data that was entered after Dialog.exec_() returns.
So, instead of connecting a slot to the dialog button buttonin the main window, you could instead subclass QDialog, setup the ui using your Qt Designer files, and connect the button.clicked signal to the QDialog.accept slot. Then in the main widget you can call Dialog.exec_() as before and retrieve the information afterwards, e.g.
from PyQt5 import QtWidgets, QtCore, QtGui
class Login_Dialog(QtWidgets.QDialog, Ui_Dialog):
def __init__(self, parent = None):
super().__init__(parent)
self.setupUi(self)
self.login_button.clicked.connect(self.accept)
class Widget(QtWidgets.QWidget):
def __init__(self, parent = None):
super().__init__(parent)
# setup ui as before
def get_login(self):
dialog = Login_Dialog(self)
if dialog.exec_():
# get activation key from dialog
# (I'm assuming here that the line edit in your dialog is assigned to dialog.line_edit)
self.activation_key = dialog.line_edit.text()
self.login()
def login(self)
print(f'The activation_key you entered is {self.activation_key}')
I've created an app which has an main window and the possibility to open an dialog (question, error and so on). I'm not using QMessageBox.warning() or QMessageBox.question() and so on because I wanted to customize the dialogs a bit.
But every time I open a new Dialog, in the Windows task bar (I'm working on Windows 10) a new 'tab' is opened, which is a little bit annoying.
My code (shortened):
from PySide import QtCore, QtGui
import sys
class MessageBox:
def __init__(self, title, message):
msg = QtGui.QMessageBox()
flags = QtCore.Qt.Dialog
flags |= QtCore.Qt.CustomizeWindowHint
flags |= QtCore.Qt.WindowTitleHint
msg.setWindowFlags(flags)
msg.setWindowTitle(title)
msg.setText(message)
msg.exec_()
class MainWindow(QtGui.QMainWindow):
def __init__(self):
super(MainWindow, self).__init__()
self.show()
MessageBox("Title", "My message here")
if __name__ == "__main__":
app = QtGui.QApplication([])
window = MainWindow()
sys.exit(app.exec_())
Note: Normally, the dialog is called from an menu or button.
Question: How can I make the dialog appear in the main window without creating a new 'task bar tab'?
The solution was quite simple: Passing an reference of QMainWindow to the constructor of QDialog will do the job, e.g:
class MessageBox(QtGui.QDialog):
def __init__(self, parent, title, message, icon="info"):
super(MessageBox, self).__init__(parent)
...
and then calling the dialog from an class that inherits from QMainWindow:
class MainWindow(QtGui.QMainWindow):
def __init__(self):
super(MainWindow, self).__init__()
#connect button with function, e.g.:
mybutton.clicked.connect(self.open_dialog)
def open_dialog(self):
MessageBox(self)
Maybe this helps anyone!
If you set the parent of the QDialog to the window, it will only show as one item on the task bar. This is generally the first argument to QMessageBox.
class MessageBox:
def __init__(self, parent, title, message):
msg = QtGui.QMessageBox(parent)
Also, if you really want to create a custom dialog, you might as well just subclass from QDialog.
I have a QMainWindow that launches a QDialog everytime I click on a button and I can't figure out why the python binary crashes when I close the QMainWindow while one or more dialogs are open.
It's not a complex Qt app and I'm really struggling trying to understand what happens.
Here's the code:
# dependency modules
from PyQt4 import QtGui
import sys
# custom modules
from ui import SingleOrderUI, DashBoardUI
class SingleOrder(QtGui.QDialog, SingleOrderUI.Ui_SingleOrder):
def __init__(self, parent=None):
QtGui.QDialog.__init__(self, parent)
self.setupUi(self)
class DashBoard(QtGui.QMainWindow, DashBoardUI.Ui_DashBoard):
def __init__(self):
QtGui.QMainWindow.__init__(self)
super(DashBoard, self).__init__()
# setup UI
self.setupUi(self)
self.newOrderBtn.clicked.connect(self.newOrder)
def newOrder(self):
print 'New order clicked'
so = SingleOrder(self)
so.show()
app = QtGui.QApplication(sys.argv)
window = DashBoard()
window.show()
sys.exit(app.exec_())
Any help would be appreciated.
EDIT: When launched using ipython, the dialogs are still showing after I close the QMainWindow, so that's maybe where the issue comes from.
I give the QMainWindow as a parent argument to the QDialog, I thought that was enough to have them killed when the QMainWindow is closed.
Okay, I've found a workaround for that but I'm not sure if it's the right way to do it.
On my DashBoard init method, I've added a python list that will store all the opened Dialogs:
def __init__(self):
QtGui.QMainWindow.__init__(self)
super(DashBoard, self).__init__()
# setup UI
self.setupUi(self)
self.newOrderBtn.clicked.connect(self.newOrder)
self.soTab = []
Then, in the same class, I defined a method to handle the closeEvent and close all the dialogs.
def closeEvent(self, event):
for so in self.soTab:
if so:
so.close()
event.accept()
I have Qdialog with that I open from main window:
Dialog = myDialog(self)
Here is the code from new opened Dialog:
class myDialog(QtGui.QDialog, Ui_DialogCalibration):
def __init__(self, parent=None):
super(myDialog, self).__init__(parent)
self.setupUi(self)
How can pass parameter(lint) from main window to this new window, something like
Dialog = myDialog(self, listInformation)
and then in myDialog class use that list
class myDialog(QtGui.QDialog, Ui_DialogCalibration):
def __init__(self, parent=None, listInfo):
super(myDialog, self).__init__(parent)
self.listInfo = listInfo
self.setupUi(self)
Then, when you go to create the myDialog, you can add the list as a parameter. When you need to use it inside of your myDialog, you would access it as self.listInfo.
EDIT: To further expand on the comments:
If you have def __init__(self, parent=None, listInfo=None), you would call it as Dialog = myDialog(parent=self, listInfo=listInfo). If you had it as def __init__(self, parent, listInfo) you would do Dialog = myDialog(self, listInfo). Hopefully you see the pattern here.