python - 更新 PyQt4 中的 n 个 PlotWidgets 以进行实时绘图

标签 python multithreading pyqt qthread pyqtgraph

我正在尝试制作一个应用程序,我想要有几个 PlotWidgets 来绘制我的 Arduino 中最多 5 个传感器的信号。一旦我有两个更新绘图,GUI 就不会响应,我需要暂停/重新启动绘图,并弹出某些值的警报。为了解决这个问题,我已经开始研究使用 QThread,但这对于 PyQtGraph 来说可能是不可能的,因为我们不能在多个线程中完成绘图?我的两个 PlotWidget 代码如下所示:

from PyQt4 import QtCore, QtGui
import pyqtgraph as pg
import random
import sys

class MainWindow(QtGui.QWidget):
   def __init__(self, parent=None):
        super(MainWindow, self).__init__(parent)
        layout = QtGui.QHBoxLayout()
        self.button = QtGui.QPushButton('Start Plotting Left')
        layout.addWidget(self.button)
        self.button.clicked.connect(self.plotter)
        self.button2 = QtGui.QPushButton('Start Plotting Right')
        layout.addWidget(self.button2)
        self.button2.clicked.connect(self.plotter2)
        self.plot = pg.PlotWidget()
        layout.addWidget(self.plot)
        self.plot2 = pg.PlotWidget()
        layout.addWidget(self.plot2)
        self.setLayout(layout)


    def plotter(self):
        self.data =[0]
        self.curve = self.plot.getPlotItem().plot()

        self.timer = QtCore.QTimer()
        self.timer.timeout.connect(self.updater)
        self.timer.start(0)

    def updater(self):
        self.data.append(self.data[-1]+0.2*(0.5-random.random()) )
        self.curve.setData(self.data)#Downsampling does not help

   def plotter2(self):
        self.data2 =[0]
        self.curve2 = self.plot2.getPlotItem().plot()

        self.timer = QtCore.QTimer()
        self.timer.timeout.connect(self.updater2)
        self.timer.start(0)

    def updater2(self):
        self.data2.append(self.data[-1]+0.2*(0.5-random.random()) )
        self.curve2.setData(self.data) #Downsampling does not help



if __name__ == '__main__':
    app = QtGui.QApplication([])
    window = MainWindow()
    window.show()
    app.exec_()

我已经准备好阅读 QThread 并进行大量尝试,但首先我需要知道这是否可能,或者我是否在浪费时间和 sleep 。有人告诉我如何让它工作吗?

最佳答案

您的代码有几个打印错误,导致其无法工作

updater2中,您使用的是self.data而不是self.data2。代码应该是:

def updater2(self):
    self.data2.append(self.data2[-1]+0.2*(0.5-random.random()) )
    self.curve2.setData(self.data2) #Downsampling does not help

此外,在创建第二个计时器时,您将其存储在与第一个计时器相同的变量中,这会导致它停止。更正后的代码应为:

def plotter2(self):
    self.data2 =[0]
    self.curve2 = self.plot2.getPlotItem().plot()

    self.timer2 = QtCore.QTimer()
    self.timer2.timeout.connect(self.updater2)
    self.timer2.start(0)

请注意,在计时器启动后“启动”计时器(即单击同一按钮两次)会导致程序崩溃。您可能应该禁用按钮,或者第二次单击停止计时器或其他东西。这取决于你。

关于线程,您可以通过在另一个线程中通过串行方式从 arduino 读取数据(GUI 不会锁定)来从线程中看到一些性能增益,但您需要通过 PyQt 发送数据向主线程发出信号并在那里运行绘图命令。 StackOverflow 上有很多关于如何使用 PyQt 正确进行线程处理的示例(例如 here )

关于python - 更新 PyQt4 中的 n 个 PlotWidgets 以进行实时绘图,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41746581/

相关文章:

python - 如何改进这种归并排序?

python - 在给定的时间后终止功能?

ios - 如何改进此 objective-c 代码( block 、RestKit、异步、线程)

python - QTableView 中的换行符

python - QHBoxLayout 以不同的顺序添加小部件

python - 如何在 PYQT 中创建标签按钮?

python - random_state 在 train_test_split 和分类器中的作用

python - 从列表元素中删除字符串 - Python

java - Tomcat 7 Servlet 产生一个线程

c# - 何时使用 Task.Run,​​何时使用 async-await 以及何时组合使用它们