本篇介紹兩種實時自動更新界面的方法。
1.使用QTimer類(計時器)。用法詳見代碼和注釋:
from PyQt5.QtCore import QTimer
from PyQt5.QtWidgets import *
import sys
class TestWindow(QDialog):
def __init__(self):
super().__init__()
btn1 = QPushButton("Start", self)
btn2 = QPushButton("Stop", self)
self.sec_label = QLabel(self)
layout = QGridLayout(self)
layout.addWidget(btn1,0,0)
layout.addWidget(btn2,0,1)
layout.addWidget(self.sec_label,1,0,1,2)
timer = QTimer()#建立計時器
timer.timeout.connect(self.update) # 計時器逾時信号連接配接到用于更新界面的槽
btn1.clicked.connect(lambda :timer.start(1000))#每1000ms發射逾時信号
btn2.clicked.connect(timer.stop)#暫停計時器
self.sec = 0#
def update(self):
self.sec_label.setText(str(self.sec))
self.sec += 1
app=QApplication(sys.argv)
form=TestWindow()
form.show()
app.exec_()
2.使用QThread類建立多線程,使用子線程實時處理資料,最後将結果顯示到界面上,可以處理相對複雜一點的邏輯。用法詳見代碼和注釋:
from PyQt5.QtCore import *
from PyQt5.QtWidgets import *
import sys
class Test(QDialog):#自定義對話框
def __init__(self,parent=None):
super().__init__(parent)
self.file_list = QListWidget()
self.btn1 = QPushButton('Start')
self.btn2 = QPushButton('Stop')
layout = QGridLayout(self)
layout.addWidget(self.file_list,0,0,1,2)
layout.addWidget(self.btn1,1,0)
layout.addWidget(self.btn2,1,1)
self.thread = Worker()
self.thread.file_changed_signal.connect(self.update_file_list)
self.btn1.clicked.connect(self.thread_start)
self.btn2.clicked.connect(self.thread_stop)
def update_file_list(self, file_inf):
self.file_list.addItem(file_inf)
scrollbar =self.file_list.verticalScrollBar()
scrollbar.setValue(scrollbar.maximum())#調整滾動條滑塊位置
def thread_start(self):
self.btn1.setEnabled(False)#是按鈕1失活(不能被點選)
self.thread.start()#實質是調用線程的 run 方法
def thread_stop(self):
self.btn1.setEnabled(True)#激活按鈕1
self.thread.terminate()#停掉線程
def closeEvent(self,event):
self.thread.terminate()#結束背景程序
event.accept()#接受關閉
class Worker(QThread):
file_changed_signal = pyqtSignal(str) # 信号參數類型:str
def __init__(self, sec=0, parent=None):
super().__init__(parent)
self.working = True
self.sec = sec
def __del__(self):
self.working = False
self.wait()
def run(self):
while self.working == True:
self.sec += 1
self.file_changed_signal.emit('目前秒數:{}'.format(self.sec))
#三種等待方法都可以:
#self.sleep(1) #參數須為int,機關秒
self.msleep(1000) #參數須為int,機關毫秒
#import time; time.sleep(1.0)#參數為float,機關秒
app = QApplication(sys.argv)
dlg = Test()
dlg.show()
sys.exit(app.exec_())