[vtkusers] vtk with Qt4 -> vtk window freezes

alex amstolz at gmail.com
Mon Apr 16 11:56:08 EDT 2012


Hello folks!

First of all: English is not my native language, so please excuse any errors!

I have a problem with pyqt4 and vtk which bothers me for weeks now.. I try to 
open a vtkContextView window as a seperate window besides a Qt4 window in a new 
thread using the threading module. Everything works as it should but when I try 
to close the vtk window it just freezes and stays open until I close the main 
window (Qt4). In the vtk window runs an animated chartXY which is updated every 
XX milliseconds triggered by a timer event.

I figured out that if I comment out the timer everything works just fine.

To demonstrate my problem I reproduced this effect by altering a simple example 
program I found on the internet:

------------------------------------------------------------------------

#!/usr/bin/env python

import numpy as N 
import vtk 
import vtk.util.numpy_support as VN 
import threading 
import time 

import sys
from PyQt4 import QtCore, QtGui, Qt
from vtk.qt4 import QVTKRenderWindowInteractor


class vtkthread():
	def __init__(self, parent=None):
		self.run()

	def generatedata(self): 	
		while (self.update_on): 
			time.sleep(0.001) 
	
			# Generate new positions             
			self.threadLock.acquire() 
			self.amp += 0.02*N.random.randn(500) 
			self.table.Modified() 
			self.threadLock.release() 
            


	def animate(self, obj=None, event=None): 
		# print 'Screen Update' 
		time.sleep(0.003) 
	
		self.threadLock.acquire() 
		self.view.Render() 
		self.threadLock.release() 


	def run(self):
		## the following lines just produce some randomn data
		dt = 30
		num_pts = 500 

		self.view = vtk.vtkContextView() 
		self.view.GetRenderer().SetBackground(1.0, 1.0, 1.0) 
		self.view.GetRenderWindow().SetSize(900, 450) 
		
		self.chart = vtk.vtkChartXY() 
		self.view.GetScene().AddItem(self.chart) 
		
		self.amp = N.random.randn(num_pts) 
		self.amp_vtk = VN.numpy_to_vtk(self.amp) 
		self.amp_vtk.SetName('Amplitude') 
		
		self.X_vtk = VN.numpy_to_vtk(N.arange(num_pts, dtype='f'), 
deep=True) 
		self.X_vtk.SetName('X') 
		
		self.table = vtk.vtkTable() 
		self.table.AddColumn(self.X_vtk) 
		self.table.AddColumn(self.amp_vtk) 
	
		self.line0 = self.chart.AddPlot(0) 
		self.line0.SetInput(self.table, 0, 1) 
		self.line0.SetColor(100, 100, 100, 255) 
		self.line0.SetWidth(2.0) 
	
		self.view.Render() 
		
		## now the animation part
		self.update_on = True 
		self.threadLock = threading.Lock() 
		self.trun = threading.Thread(target=self.generatedata, args=())
		self.trun.start()
	
		self.iren = self.view.GetInteractor() 
		
		## the following line causes the error
		self.iren.AddObserver("TimerEvent", self.animate) 

		self.timer_id = self.iren.CreateRepeatingTimer(dt) 
		
		self.iren.Start() 
		self.update_on = False 
		self.iren.DestroyTimer(self.timer_id) 

		
		# =========================== 	
	

class myQtApp(QtGui.QMainWindow):
	def __init__(self):
		QtGui.QMainWindow.__init__(self)
		self.setGeometry(100,100,800,600)
		self.setWindowTitle('testwindow')

		## textbox to show that nothings yet freezing
		self.main_frame=QtGui.QWidget()
		self.textedit=QtGui.QTextEdit()
		self.textedit.setLineWrapMode(QtGui.QTextEdit.NoWrap)
		hbox1=QtGui.QHBoxLayout()
		hbox1.addWidget(self.textedit)
		self.main_frame.setLayout(hbox1)
		self.setCentralWidget(self.main_frame)

		self.loadthread()

	def loadthread(self):
		a = threading.Thread(target=vtkthread,args=())
		a.start()

		

app = QtGui.QApplication(sys.argv)

myapp = myQtApp()
myapp.show()

sys.exit(app.exec_())

------------------------------------------------------------------------


I tried to embed the vtk window in a Qt-window to solve the problem but I did 
not figure out how.

Thank you very very much in advance!!!



PS:
Is it somehow possible to zoom in the graph while the animation is on?




More information about the vtkusers mailing list