This question already has answers here:
Autocomplete from .ui
(4 answers)
reading UI file and connecting elements such as buttons, text, etc
(1 answer)
Closed 2 years ago.
I am working on pyqt5 project where I am designing the ui in qt designer and writing its python code in pycharm. Ui has a button and label. Once button is clicked, label value is changed. Below is the code:
import sys
from PyQt5.uic import loadUi
from PyQt5.QtWidgets import QApplication, QMainWindow
class ROCKET(QMainWindow):
def __init__(self):
super(ROCKET, self).__init__()
loadUi('ui/gui.ui', self)
self.pushButton.clicked.connect(self.btn_click)
def btn_click(self):
self.label.setText("CLICKED")
app = QApplication(sys.argv)
window = ROCKET()
window.show()
app.exec_()
Pycharm gives warning for pushButton and label:
Unresolved attribute reference 'pushButton' for class 'ROCKET'
but if I am running the code, I am getting correct output. How can I remove these warnings and make the code correct.
The fact that you can refer to your widgets as attributes of the main window is a convenience that is offered by PyQt5 via loadUi. PyCharm is complaining because it didn't see you explicitly define the pushButton attribute for your class.
One way you can get around the warning would be to explicitly define the attribute:
self.pushButton = self.findChild(QPushButton, "name_of_push_button")
self.pushButton.clicked.connect(self.btn_click)
Related
This question already has answers here:
What is the rule for choosing "central widget" in QMainWindow? and why is it important?
(2 answers)
Closed 1 year ago.
I am trying to learn PyQt to develop a GUI for viewing images. I found some code that looked like It could be easily converted to fit my use case. Figured going line by line to check the logic would help me understand PyQt.
I am getting stuck at this line in the following class
from PyQt5 import QtCore, QtGui, QtWidgets
from PyQt5.QtCore import Qt
from PyQt5.QtWidgets import QFileDialog
class Ui_MainWindow(QtWidgets.QMainWindow):
def __init__(self, imgs_path,masks_path, pred_path, study):
super(Ui_MainWindow, self).__init__()
# sets up ui
self.setObjectName("MainWindow")
self.resize(1440, 1000)
self.centralwidget = QtWidgets.QWidget()
self.centralwidget.setObjectName("centralwidget")
....
self.setCentralWidget(self.centralwidget)
The line which goes self.setCentralWidget(self.centralwidget), what exactly is being set as the central widget? I tried to look at the documentation but wasn't able to understand what was being set as the central widget. It looks like QtWidgets.QtWidget() is just a class containing methods for user interface?
The tutorial I was following introduced self.centralwidget in the context of setting it to some type of widget like QtWidgets.Qlabel() etc, so I am not sure what is actually being set as the central widget in this case.
I'll try to explain it to you visually:
In the picture, you can see the main frame, your QtWidgets.QMainWindow which, in this case, is the parent container to all the objects you'll place in your UI.
Then you have that highlighted rectangle in the middle, which is actually a QtWidgets.QWidget(). The fact that you are setting it as Centralwidget I think is more of a positional constrain/indication. In turn, QtWidgets.QWidget() can contains other elements (even another QtWidgets.QWidget() for example).
I created UI using Qt Designer. Then I converted the ui file to a .py file (pyuic -x) - it works fine if launched directly. Then I tried to subclass my ui in a separate file to implement additional logic. And this is where things start to go wrong. Inheriting from QMainWindow and my Qt Designer file works OK with no issues, as expected. However, the moment I set any WindowFlag for my QMainWindow (any flag - I tried these: StaysOnTop, FramelessWindowHint) and run the file, the window appears and instantly disappears. The program continues to run in a console window, or as a PyCharm process, but the window is gone. It looks to me like it is getting out of scope - but why setting a simple flag would make any difference to the garbage collector? Could someone explain this behaviour?
Minimum code required to reproduce this phenomenon:
from ui import Ui_MainWindow
from PyQt5 import QtCore, QtWidgets, QtGui
import sys
class Logic(QtWidgets.QMainWindow, Ui_MainWindow):
def __init__(self):
QtWidgets.QMainWindow.__init__(self)
self.setupUi(self)
self.show()
# self.setWindowFlags(QtCore.Qt.WindowStaysOnTopHint)
# self.setWindowFlags(QtCore.Qt.FramelessWindowHint)
self.setAttribute(QtCore.Qt.WA_NoSystemBackground, True)
self.setAttribute(QtCore.Qt.WA_TranslucentBackground, True)
if __name__ == "__main__":
app = QtWidgets.QApplication(sys.argv)
window = Logic()
sys.exit(app.exec_())
The window should appear and stay on the screen until one (or more) of the flags are uncommented. I use Python 3.8 (32-bit) with PyQt5. Run environment provided by PyCharm. Windows 10.
From the documentation of setWindowFlags():
Note: This function calls setParent() when changing the flags for a window, causing the widget to be hidden. You must call show() to make the widget visible again..
So, just move self.show() after setting the flags, or call it from outside the __init__ (after the instance is created), which is the most common and suggested way to do so, as it's considered good practice to show a widget only after it has been instanciated.
Don't critisize me using different classes - the reasons for his is becausethere will be more GUIs in my project created by the QtDesigner, but this should not be important for now.
In general, I have two Python scripts:
main.py:
from PyQt5 import QtCore, QtWidgets, QtGui
import sys
import time
from gui_class import Gui
app = QtWidgets.QApplication(sys.argv)
gui = Gui()
sys.exit(app.exec_())
gui_class.py:
from PyQt5 import QtWidgets
class Gui():
def __init__(self):
w = QtWidgets.QWidget()
w.resize(500, 500)
self.button = QtWidgets.QPushButton(w)
self.button.setGeometry(100, 100, 300, 300)
w.show()
If I run the main.py-script, then the window appears for a split second and disappears right away. I can't see it, I can't click it. The code does not terminate, though. It's still waiting for the application to finish - I can't do anything, though.
If I put a breakpoint before the line saying w.show() in the gui_class.py and simply continue the code after it stopped in that line, then the GUI is visible and I can click the button and the code terminates after I close the window - everything works as expected.
I am using PyQt5: 5.15.2 with Python3.7.
The problem is that w is a local variable that will be destroyed when the scope where it was created finishes executing. The solution is to extend its life cycle by increasing its scope by making it an attribute of the class, for this you must change w with self.w.
Context
I code with pyqt5 and python. Recently, I couldn't get autocompletion working for the objects inside the imported .ui > .py files from qtdesigner. I'd like to know how to get that autocompletion back on PyCharm 2019.
Code
from PyQt5 import uic
from PyQt5.QtWidgets import QWidget
someWidgetPath= os.path.dirname(os.path.realpath(__file__)) + '\\someWidgetUi.ui'
Ui_someWidget, QtBaseClass = uic.loadUiType(someWidgetPath)
class SomeNewWidget(QWidget, Ui_someWidget):
def __init__(self):
super(GraphManagerWidget, self).__init__()
self.setupUi()
self.XXX
There is no autocompletion on this XXX. In my .ui, I have a textEdit named te_name, but it doesn't appear. Thus, I always have to go back to my qtdesigner, lookup the name I gave the QObjects and then write it in the code. Sometimes, I find this time consuming.
Setup
Windows==10.0.1
Python==3.7.6
PyQt5==5.14.1
QtDesigner==5.11.1
PyCharm==2019.3.3
This question already has an answer here:
pyqt5 not showing window [duplicate]
(1 answer)
Closed 3 years ago.
I'm getting an unknown error 'Badly placed ()'s' when attempting to build a QT widget .
from PyQt4 import QtGui
import sys
app = QtGui.QApplication(sys.argv)
window = QtGui.QWidget()
window.setGeometry(50,50,500,300)
window.setWindowTitle("pyqt window")
window.show()
A empty window with "pyqt window" as title
It worked after adding sys.exit(app.exec_()) to the code