Mayavi:帮助重置鼠标选择器和连接wx事件到@on_trait_change



我正在制作一个UI,其中包括在带有控件的wx框架中嵌入Mayavi视图,并且我遇到了一些问题。为了解决这个问题,我编写了一个工作脚本,结合了wx嵌入和红球拾取器的例子;我的项目是一个更复杂的版本。

我有两个问题:

  1. 如果用户选择了不同数量的球,我想清除图形并使用一组新的球重新绘制。然而,从我从google中收集到的信息来看,我需要在clf()调用之后重置选择器。我所见过的类似示例使用了场景的@on_trait_change装饰器。激活的特征,但我不确定如何做到这一点时,场景没有被激活,而只是更新。
  2. 如果用户选择一个不同的球的颜色,我想简单地改变颜色的地方,而不重新创建场景。看来我可以通过使用字形的mlab_source的set方法来做到这一点,我认为最好使用@on_trait_change来调用它。但是,我不知道如何最好地将wx触发事件连接到允许触发@on_trait_change的trait类型。

提前感谢。

注:我本想把这篇文章放在预想的邮件列表上,但这个网站似乎已经关闭了一段时间。有人注意到了吗?

我不确定我明白问题是什么。要使代码正常工作,在wx通知器中调用场景(您可以参考它)并进行必要的调整似乎很简单。像这样:

def on_number_of_balls_selected():
  n = self.get_selected_ball_number()
  clear_figure()
  #mlab.clf(scene = self.mayavi_view.scene.mayavi_scene )
  # make some new points
  new_points = somehow_make_some_new_points(n)
  mlab.points3d( new_points, scene=self.mayavi_view.scene.mayavi_scene )
  # reattach the picker
  picker = self.mayavi_view.figure.on_mouse_pick(self.mayavi_view.picker_callback)

等等,这些调用可能不是很正确地放在一起,但这是基本的思想。

如果你使用traitsui,解决方案在概念上并没有什么不同,但我很好奇为什么如果你要使用traitsui来渲染mayavi场景,为什么不也用它来显示GUI中的枚举?这确实是traitsui的预期用例(用于简单的应用程序)。如果您有理由不这样做——很好,当然在许多用例中,traitsui并不是最好的工具,使用工具包(或搪瓷,我个人并没有真正公平地尝试过)可以使您更灵活地控制布局并提供更广泛的小部件。但是traitsui提供了一个稍微更好的解决方案,当用户在GUI中更改某些数字时提供通知(尽管您仍然必须编写侦听器)。

编辑:事实证明,tvtk拾取器在mlab.clf上分离自己(合理),并防止侦听相同事件的新拾取器被重新连接(不太合理)。我认为这是tvtk的一个bug,我无法在30分钟内将其隔离。因此,现在我建议完全避免使用mlab.clf(我已经调整了上面的代码以反映这一点)。相反,调用每个源模块的remove方法,这将导致源从场景中删除自己:

def clear_figure(self):
  for child in self.scene.mayavi_scene.children:
    child.remove()

之后,选择器将被断开连接,但是您可以创建新对象,然后像往常一样通过调用on_mouse_pick将选择器重新附加到新对象上。

相关内容

  • 没有找到相关文章

最新更新