2016-03-21 11 views
0

Ich muss Signale mit einer großen Anzahl von Samples plotten (bis zu 4e6 Samples). Ich verwende python 2.7, Qt 4.8 und pyqtgraph 0.9.10.scypy.signal.ecimate() friert GUI ein

Ich habe so etwas wie dies:

  1. Signale generieren und dezimieren sie (in getrennten QThread)
  2. Plot Signale und rufen setDownsample() und clipToView() (Methoden der pyqtgraph)

Das Problem ist, dass GUI friert, wenn QThread für Dezimate berechnet. Hier ist mein Code:

class TestDecimate(QDialog): 

    def __init__(self, parent=None): 
     super(TestDecimate, self).__init__(parent) 

     self.decimate_thread = GenerateBigPlotThread() 

     layout = QGridLayout() 

     graph_widget = pg.GraphicsLayoutWidget() 
     graph_layout = graph_widget.addLayout() 

     self.p = graph_layout.addPlot(title="Plot 2", col=1, row=2) 
     self.curve1 = self.p.plot([], pen=(255, 0, 0)) 
     self.curve2 = self.p.plot([], pen=(255, 255, 0)) 
     self.curve3 = self.p.plot([], pen=(255, 0, 255)) 
     self.curve4 = self.p.plot([], pen=(0, 0, 255)) 
     self.p.showGrid(True, True, 0.3) 

     self.legend = pg.LegendItem(offset=(-10,10)) 
     self.legend.addItem(self.curve1, name="Test") 
     self.legend.addItem(self.curve2, name="Test1") 
     self.legend.addItem(self.curve3, name="Test2") 
     self.legend.addItem(self.curve4, name="Test3") 
     self.legend.setParentItem(self.p.getViewBox()) 

     self.start_pb = QPushButton("Generate") 

     layout.addWidget(graph_widget, 1, 1) 
     layout.addWidget(self.start_pb, 2, 1) 

     self.setLayout(layout) 

     self.start_pb.clicked.connect(self.start_thread_for_decimate) 
     self.decimate_thread.newData.connect(self.set_data) 

    def set_data(self, y, z, n, m): 
     print "Plotting" 
     self.curve1.setData(y) 
     self.curve2.setData(z) 
     self.curve3.setData(n) 
     self.curve4.setData(m) 

     self.p.setDownsampling(ds=True, auto=True, mode='peak') 
     self.p.setClipToView(clip=True) 
     self.p.getViewBox().enableAutoRange(axis=ViewBox.XYAxes) 
     print "Plotting done" 


    def start_thread_for_decimate(self): 
     self.decimate_thread.start() 

if __name__ == "__main__": 
    app = QApplication(sys.argv) 
    main = TestDecimate() 
    main.show() 
    sys.exit(app.exec_()) 

Thema für die Berechnung und Dezimierung:

class GenerateBigPlotThread(QThread): 

    newData = QtCore.pyqtSignal("PyQt_PyObject","PyQt_PyObject","PyQt_PyObject","PyQt_PyObject") 

    def __init__(self,*arg,**kwargs): 
     super(GenerateBigPlotThread, self).__init__(*arg,**kwargs) 

    def run(self): 

     self.num_points = 4e6 

     x = np.arange(self.num_points) 
     y = np.sin(3.14159 * x * 10/self.num_points) 
     z = np.cos(3.14159 * x * 10/self.num_points) 
     n = np.sin(3.14159 * x * 5/self.num_points) 
     m = np.cos(3.14159 * x * 5/self.num_points) 
     print "Decimate" 
     y = decimate(y, 4, ftype='fir') 
     z = decimate(z, 4, ftype='fir') 
     n = decimate(n, 4, ftype='fir') 
     m = decimate(m, 4, ftype='fir') 
     print "Done!" 

     self.newData.emit(y, z, n, m) 

Wenn Thread die beste Art und Weise gestartet, um das Problem zu sehen ist Legende zu bewegen. Ich habe auch versucht scipy.signal.resample (4e6 Proben zu 1e6 Proben) statt dezimieren und das gleiche Problem ist aufgetreten. Kann mir jemand sagen, was der Grund für diese Art von Verhalten ist?

Antwort

0

Nun, das Problem war in der Version von scipy. Ich hatte scipy 0.13.2 und nachdem ich auf 0.17.0 aufgerüstet habe, scheint das Problem gelöst zu sein. Trotzdem würde ich gerne wissen, warum so etwas überhaupt möglich war.