[英]How do I update the progress bar on my Pyside2 GUI?
我一直在嘗試更新我的 GUI 上的進度條,但我不知道該怎么做......我提供的代碼顯示了進度更新 - 我只需要該值來更新我的 GUI 上的進度條也。 這是來自 Qt Creator 的 QML 文件。
主文件
import os
import sys
import time
from PySide2.QtGui import QGuiApplication
from PySide2.QtQml import QQmlApplicationEngine, qmlRegisterType
from PySide2.QtCore import QObject, Slot, Signal, QTimer, QUrl, QThread
from pathlib import Path
from multiprocessing.pool import ThreadPool
class MainWindow(QObject):
def __init__(self):
QObject.__init__(self)
@Slot()
def thread_progress(self):
print("Worker")
self.worker = Worker()
self.thread = QThread()
self.worker.moveToThread(self.thread)
self.thread.start()
self.worker.run()
class Worker(QObject):
progress_value = Signal(float)
@Slot()
def run(self):
self.progress = 0
self.total = 100
for i in range(0, self.total):
self.update_progress()
def update_progress(self):
print(f"{self.progress} / {self.total}")
self.progress += 1
self.progress_value.emit(self.progress)
time.sleep(1)
if __name__ == "__main__":
app = QGuiApplication(sys.argv)
engine = QQmlApplicationEngine()
# Get Context
main = MainWindow()
engine.rootContext().setContextProperty("backend", main)
# Set App Extra Info
app.setOrganizationName("zardoss")
app.setOrganizationDomain("N/A")
engine.load(os.fspath(Path(__file__).resolve().parent / "main.qml"))
if not engine.rootObjects():
sys.exit(-1)
sys.exit(app.exec_())
main.py 文件與 main.qml 文件連接。 GUI 有一個按鈕、進度條和一個文本輸入元素。 我只關心按下生成按鈕后進度條會填滿。 按下生成按鈕后,您可以從控制台看到 1-100 的值正在填充,但它沒有填充進度條,因為我不確定如何填充。
main.qml
import QtQuick 2.15
import QtQuick.Window 2.15
import QtQuick.Controls 2.15
import QtGraphicalEffects 1.15
import QtQuick.Shapes 1.15
Window {
id: mainWindow
width: 750
height: 500
visible: true
color: "#00000000"
// Remove title bar
flags: Qt.Window | Qt.FramelessWindowHint
// Properties
property int windowStatus: 0
property int windowMargin: 10
title: qsTr("Progress Bar")
Rectangle {
id: bg
color: "#2c313c"
border.color: "#f12c313c"
border.width: 1
anchors.left: parent.left
anchors.right: parent.right
anchors.top: parent.top
anchors.bottom: parent.bottom
anchors.rightMargin: windowMargin
anchors.leftMargin: windowMargin
anchors.bottomMargin: windowMargin
anchors.topMargin: windowMargin
z:1
Rectangle {
id: appContainer
height: 480
color: "#00000000"
anchors.left: parent.left
anchors.right: parent.right
anchors.top: parent.top
anchors.bottom: parent.bottom
anchors.rightMargin: 1
anchors.leftMargin: 1
anchors.bottomMargin: 1
anchors.topMargin: 1
Rectangle {
id: content
color: "#00000000"
anchors.left: parent.left
anchors.right: parent.right
anchors.top: topBar.bottom
anchors.bottom: parent.bottom
anchors.topMargin: 0
Button {
id: btnGenerate
x: 265
y: 44
width: 200
height: 50
text: "Generate"
anchors.verticalCenter: parent.verticalCenter
anchors.right: parent.right
anchors.horizontalCenterOffset: 0
anchors.horizontalCenter: parent.horizontalCenter
anchors.verticalCenterOffset: 165
// colorPressed: "#1e5425"
// colorMouseOver: "#42b852"
font.pointSize: 14
display: AbstractButton.TextBesideIcon
font.bold: false
// colorDefault: "#328a3f"
anchors.rightMargin: 250
onPressed: {
// backend.generate()
backend.thread_progress()
}
}
ProgressBar{
id: progressBar
x: 239
y: 64
visible: true
width: 661
height: 250
// text: "%"
anchors.verticalCenter: parent.verticalCenter
value: 0
//bgColor: "#00000/*000"
//dropShadowColor: "#20000000"
//samples: 16
anchors.verticalCenterOffset: -15
anchors.horizontalCenter: parent.horizontalCenter
}
}
}
}
DropShadow{
anchors.fill: bg
horizontalOffset: 0
verticalOffset: 0
radius: 10
samples: 16
color: "#80000000"
source:bg
z: 0
}
Connections{
target: backend
function onLinkValid(valid) {
if(valid === true) {
textField.textColor = "#00FF00"
} else {
textField.textColor = "#FF00FF"
}
}
}
}
您的問題是具有進度值的信號未連接到 GUI 的任何元素。
在這種情況下,必須在與 ProgressBar 連接的 QML 暴露的 class 中創建一個信號,並且該信號必須從 Worker 的信號中接收信息。 另一方面,您不應直接調用“run()”方法,因為它將在調用它的線程中執行,在您的情況下是主線程,因此它將阻塞 GUI,而您必須調用它間接地用信號或使用QTimer。
import os
import sys
import time
from pathlib import Path
from PySide2.QtGui import QGuiApplication
from PySide2.QtQml import QQmlApplicationEngine
from PySide2.QtCore import QObject, Slot, Signal, QTimer, QUrl, QThread
class Backend(QObject):
progress_changed = Signal(float, name="progressChanged")
def __init__(self, parent=None):
super().__init__(parent)
self.worker = Worker()
self.worker.progress_changed.connect(self.progress_changed)
self.worker_thread = QThread()
self.worker.moveToThread(self.worker_thread)
self.worker_thread.start()
@Slot()
def start_worker(self):
QTimer.singleShot(0, self.worker.run)
class Worker(QObject):
progress_changed = Signal(float)
@Slot()
def run(self):
self.progress = 0
self.total = 100
for i in range(0, self.total):
self.update_progress()
def update_progress(self):
print(f"{self.progress} / {self.total}")
self.progress += 1
self.progress_changed.emit(self.progress)
time.sleep(1)
if __name__ == "__main__":
app = QGuiApplication(sys.argv)
engine = QQmlApplicationEngine()
backend = Backend()
engine.rootContext().setContextProperty("backend", backend)
engine.load(os.fspath(Path(__file__).resolve().parent / "main.qml"))
if not engine.rootObjects():
sys.exit(-1)
ret = app.exec_()
# backend.worker_thread.quit()
# backend.worker_thread.wait()
sys.exit(ret)
import QtQuick 2.15
import QtQuick.Controls 2.15
import QtQuick.Window 2.15
Window {
id: mainWindow
width: 750
height: 500
visible: true
color: "#00000000"
title: qsTr("Progress Bar")
Row {
spacing: 10
anchors.centerIn: parent
Button {
id: btnGenerate
text: "start"
onClicked: backend.start_worker()
}
ProgressBar {
id: progressBar
from: 0
to: 100.0
}
}
Connections {
target: backend
function onProgressChanged(progress) {
progressBar.value = progress;
}
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.