Pushing the button starts 100 rounds cycle. With QLabel.setText()
we update self.label
from inside of scope of clicked()
function.
The code declares a local progressbar
object connected to a custom 'customSignal` using:
QtCore.QObject.connect(self, QtCore.SIGNAL("customSignal(int)"), progressbar, QtCore.SLOT("setValue(int)"))
with four arguments passed to QtCore.QObject.connect()
.
The first argument self
is the object that will be emitting the signal. Since the function that will do the "sleep-every-second-processing" is declared under the main Dialog
instance we pass self
here.
The second argument is the name of the signal itself: 'customSignal'.
The progressbar
object is used as third and its method setValue
as fourth last argument.
class ProgressBar(QtGui.QProgressBar):
def __init__(self, parent=None):
super(ProgressBar, self).__init__(parent=parent)
class Dialog(QtGui.QDialog):
def __init__(self):
super(QtGui.QDialog,self).__init__()
layout = QtGui.QVBoxLayout()
self.setLayout(layout)
self.label = QtGui.QLabel('idle...')
layout.addWidget(self.label)
progressbar = ProgressBar(self)
QtCore.QObject.connect(self, QtCore.SIGNAL("customSignal(int)"), progressbar, QtCore.SLOT("setValue(int)"))
layout.addWidget(progressbar)
button = QtGui.QPushButton('Process')
button.clicked.connect(self.clicked)
layout.addWidget(button)
def clicked(self):
for value in range(101):
message = '...processing %s of 100'%value
self.label.setText(message)
self.emit(QtCore.SIGNAL("customSignal(int)"), value)
QtGui.qApp.processEvents()
time.sleep(1)
if __name__ == '__main__':
app = QtGui.QApplication([])
dialog = Dialog()
dialog.resize(300, 100)
dialog.show()
app.exec_()
Here is variation of the same solution except linking to the progressbar method. import time
class ProgressBar(QtGui.QProgressBar):
def __init__(self, parent=None):
super(ProgressBar, self).__init__(parent=parent)
def set_to_value(self, value):
self.setValue(value)
QtGui.qApp.processEvents()
return True
def closeEvent(self, event):
self._active=False
class Dialog(QtGui.QDialog):
def __init__(self):
QtGui.QDialog.__init__(self, parent=None)
layout = QtGui.QVBoxLayout()
self.setLayout(layout)
self.label = QtGui.QLabel('idle...')
layout.addWidget(self.label)
progressbar = ProgressBar(self)
QtCore.QObject.connect(self, QtCore.SIGNAL("customSignal(int)"), progressbar.set_to_value )
layout.addWidget(progressbar)
button = QtGui.QPushButton('Process')
button.clicked.connect(self.clicked)
layout.addWidget(button)
def clicked(self):
for value in range(101):
message = '...processing %s of 100'%value
self.label.setText(message)
self.emit(QtCore.SIGNAL("customSignal(int)"), value)
QtGui.qApp.processEvents()
time.sleep(1)
if __name__ == '__main__':
app = QtGui.QApplication([])
dialog = Dialog()
dialog.resize(300, 100)
dialog.show()
app.exec_()
This code now links a custom signal to a function referred as Slot in Qt.
from PySide import QtCore, QtGui
import time
class ProgressBar(QtGui.QProgressBar):
def __init__(self, parent=None):
super(ProgressBar, self).__init__(parent=parent)
@QtCore.Slot(int)
def set_to_value(self, value):
self.setValue(value)
QtGui.qApp.processEvents()
return True
def closeEvent(self, event):
self._active=False
class Dialog(QtGui.QDialog):
def __init__(self):
QtGui.QDialog.__init__(self, parent=None)
layout = QtGui.QVBoxLayout()
self.setLayout(layout)
self.label = QtGui.QLabel('idle...')
layout.addWidget(self.label)
progressbar = ProgressBar(self)
# QtCore.QObject.connect(self, QtCore.SIGNAL("customSignal(int)"), progressbar.set_to_value )
QtCore.QObject.connect(self, QtCore.SIGNAL("customSignal(int)"), progressbar, QtCore.SLOT("set_to_value(int)"))
layout.addWidget(progressbar)
button = QtGui.QPushButton('Process')
button.clicked.connect(self.clicked)
layout.addWidget(button)
def clicked(self):
for value in range(101):
message = '...processing %s of 100'%value
self.label.setText(message)
self.emit(QtCore.SIGNAL("customSignal(int)"), value)
QtGui.qApp.processEvents()
time.sleep(1)
if __name__ == '__main__':
dialog = Dialog()
dialog.resize(300, 100)
dialog.show()