使用 Python 在 VTK-7 中选取 2D 演员
2D Actor Picking in VTK-7 with Python
我在 Python-VTK(7) 中有一个简单的程序,它有三个二维磁盘,可以点击和移动。
我通过制作自定义交互器样式来做到这一点,在该样式中我将所选元素存储在 LeftButtonClick
事件中,更改先前所选元素在 MouseMove
事件中的位置并将所选元素设置为None
在 LeftButtonRelease
事件中。
下面是完整的 VTK 代码,(理想情况下)应该这样做:
import vtk
class CustomInteractor(vtk.vtkInteractorStyleTrackballCamera):
def __init__(self, renderer, renWin):
self.AddObserver('LeftButtonPressEvent', self.OnLeftButtonDown)
self.AddObserver('LeftButtonReleaseEvent', self.OnLeftButtonRelease)
self.AddObserver('MouseMoveEvent', self.OnMouseMove)
self.renderer = renderer
self.chosenPiece = None
self.renWin = renWin
def OnLeftButtonRelease(self, obj, eventType):
self.chosenPiece = None
vtk.vtkInteractorStyleTrackballCamera.OnLeftButtonUp(self)
def OnLeftButtonDown(self, obj, eventType):
clickPos = self.GetInteractor().GetEventPosition()
picker = vtk.vtkPropPicker()
picker.Pick(clickPos[0], clickPos[1], 0, self.renderer)
actor = picker.GetActor2D()
self.chosenPiece = actor
vtk.vtkInteractorStyleTrackballCamera.OnLeftButtonDown(self)
def OnMouseMove(self, obj, eventType):
if self.chosenPiece is not None:
mousePos = self.GetInteractor().GetEventPosition()
self.chosenPiece.SetPosition(mousePos[0], mousePos[1])
self.renWin.Render()
else :
vtk.vtkInteractorStyleTrackballCamera.OnMouseMove(self)
def buildDiskActor(inner_radius = 10, outer_radius = 20, position = (100, 20), color = (1, 1, 1)):
disk = vtk.vtkDiskSource()
disk.SetInnerRadius(inner_radius)
disk.SetOuterRadius(outer_radius)
disk.SetRadialResolution(100)
disk.SetCircumferentialResolution(100)
disk.Update()
mapper = vtk.vtkPolyDataMapper2D()
mapper.SetInputConnection(disk.GetOutputPort())
actor = vtk.vtkActor2D()
actor.SetMapper(mapper)
actor.SetPosition(position[0], position[1])
actor.GetProperty().SetColor(color)
return actor
ren = vtk.vtkRenderer()
renWin = vtk.vtkRenderWindow()
renWin.AddRenderer(ren)
renWin.SetSize(600, 600)
elements = [
buildDiskActor(position = (200, 400), color=(1, 0, 0)),
buildDiskActor(position = (400, 400), color=(0, 1, 0)),
buildDiskActor(position = (300, 200), color=(0, 0, 1)),
]
for actor in elements:
ren.AddActor(actor)
iren = vtk.vtkRenderWindowInteractor()
iren.SetRenderWindow(renWin)
inStyle = CustomInteractor(ren, renWin)
iren.SetInteractorStyle(inStyle)
renWin.Render()
iren.Start()
结果如下所示:
也就是说,无论我选择哪个磁盘,vtkPropPicker
只选择绿色的磁盘。
出于某种原因,当我使用 Python2-VTK6.3.0 而不是 Python3-VTK7 时,一切正常。这是 VTK7 中的错误吗?或者实施是否以某种方式改变了?还是其他原因?
VTK 7 切换到新的渲染后端。在 7.0 中,渲染后端在拾取 2D actor 时存在错误。
该bug在7.1中已修复;参见 Kitware/VTK@5559c11
。
我在 Python-VTK(7) 中有一个简单的程序,它有三个二维磁盘,可以点击和移动。
我通过制作自定义交互器样式来做到这一点,在该样式中我将所选元素存储在 LeftButtonClick
事件中,更改先前所选元素在 MouseMove
事件中的位置并将所选元素设置为None
在 LeftButtonRelease
事件中。
下面是完整的 VTK 代码,(理想情况下)应该这样做:
import vtk
class CustomInteractor(vtk.vtkInteractorStyleTrackballCamera):
def __init__(self, renderer, renWin):
self.AddObserver('LeftButtonPressEvent', self.OnLeftButtonDown)
self.AddObserver('LeftButtonReleaseEvent', self.OnLeftButtonRelease)
self.AddObserver('MouseMoveEvent', self.OnMouseMove)
self.renderer = renderer
self.chosenPiece = None
self.renWin = renWin
def OnLeftButtonRelease(self, obj, eventType):
self.chosenPiece = None
vtk.vtkInteractorStyleTrackballCamera.OnLeftButtonUp(self)
def OnLeftButtonDown(self, obj, eventType):
clickPos = self.GetInteractor().GetEventPosition()
picker = vtk.vtkPropPicker()
picker.Pick(clickPos[0], clickPos[1], 0, self.renderer)
actor = picker.GetActor2D()
self.chosenPiece = actor
vtk.vtkInteractorStyleTrackballCamera.OnLeftButtonDown(self)
def OnMouseMove(self, obj, eventType):
if self.chosenPiece is not None:
mousePos = self.GetInteractor().GetEventPosition()
self.chosenPiece.SetPosition(mousePos[0], mousePos[1])
self.renWin.Render()
else :
vtk.vtkInteractorStyleTrackballCamera.OnMouseMove(self)
def buildDiskActor(inner_radius = 10, outer_radius = 20, position = (100, 20), color = (1, 1, 1)):
disk = vtk.vtkDiskSource()
disk.SetInnerRadius(inner_radius)
disk.SetOuterRadius(outer_radius)
disk.SetRadialResolution(100)
disk.SetCircumferentialResolution(100)
disk.Update()
mapper = vtk.vtkPolyDataMapper2D()
mapper.SetInputConnection(disk.GetOutputPort())
actor = vtk.vtkActor2D()
actor.SetMapper(mapper)
actor.SetPosition(position[0], position[1])
actor.GetProperty().SetColor(color)
return actor
ren = vtk.vtkRenderer()
renWin = vtk.vtkRenderWindow()
renWin.AddRenderer(ren)
renWin.SetSize(600, 600)
elements = [
buildDiskActor(position = (200, 400), color=(1, 0, 0)),
buildDiskActor(position = (400, 400), color=(0, 1, 0)),
buildDiskActor(position = (300, 200), color=(0, 0, 1)),
]
for actor in elements:
ren.AddActor(actor)
iren = vtk.vtkRenderWindowInteractor()
iren.SetRenderWindow(renWin)
inStyle = CustomInteractor(ren, renWin)
iren.SetInteractorStyle(inStyle)
renWin.Render()
iren.Start()
结果如下所示:
也就是说,无论我选择哪个磁盘,vtkPropPicker
只选择绿色的磁盘。
出于某种原因,当我使用 Python2-VTK6.3.0 而不是 Python3-VTK7 时,一切正常。这是 VTK7 中的错误吗?或者实施是否以某种方式改变了?还是其他原因?
VTK 7 切换到新的渲染后端。在 7.0 中,渲染后端在拾取 2D actor 时存在错误。
该bug在7.1中已修复;参见 Kitware/VTK@5559c11
。