Reputation: 477
Here is my code:
from PyQt5.QtCore import (
QDir
)
from PyQt5.QtWidgets import(
QApplication,QDialog,
QVBoxLayout,QGridLayout,QPushButton,QFileDialog
)
class DicAsk(object):
def __init__(self):
super(DicAsk, self).__init__()
self.button = QPushButton("ButtonB")
self.button.clicked.connect(self.browse)
# self.button.clicked.connect(lambda:QFileDialog.getExistingDirectory(None, "Find Files",
# QDir.currentPath()))
def browse(self):
directory = QFileDialog.getExistingDirectory(None, "Find Files",
QDir.currentPath())
class Window(QDialog):
def __init__(self, parent=None):
super(Window, self).__init__(parent)
buttonA = QPushButton("ButtonA")
buttonA.clicked.connect(self.browse)
dicAsk = DicAsk()
mainLayout = QVBoxLayout()
mainLayout.addWidget(buttonA)
mainLayout.addWidget(dicAsk.button)
self.setLayout(mainLayout)
def browse(self):
directory = QFileDialog.getExistingDirectory(None, "Find Files",
QDir.currentPath())
if __name__ == '__main__':
import sys
app = QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec_())
There are two buttons in the window: "buttonA" and "button B".
Button A works fine, it can successfully open a QFileDialog
.
Button B is defined in a class and should work like button A, but it doesn't open a QFileDialog
. It works if the browse
method is changed into a lambda function. Why doesn't the browse
method work?
Upvotes: 0
Views: 356
Reputation: 6075
The problem is that DicAsk
is not define as a PyQt object. It's only define as a basic python class, so its methods can't be slots. DicAsk.browse
is never called when you click button B.
The real problem is that you don't keep a reference to dicAsk
. It is defined locally in Window.__init__
, and then destroyed. You can still use dicAsk.buttton
because it was added to the layout (window
becomes the parent of dicAsk.button
, and so keeps a reference to the button)
To fix the issue you can keep a reference with self.dicAsk=DicAsk()
, or modify the class to have a parent:
class DicAsk(QtCore.Qobject):
def __init__(self,parent):
super(DicAsk, self).__init__(parent)
#in Window
dicAsk=DicAsk(self)
Another way to solve your issue is to subclass QPushButton
:
class MyButton(QPushButton):
def __init__(self,parent=None):
super(MyButton, self).__init__(parent)
self.setText("ButtonB")
self.clicked.connect(self.browse)
def browse(self):
print("browse")
It makes more sense since what you want is a customized button.
Upvotes: 2