【发布时间】:2018-01-29 19:45:42
【问题描述】:
我尝试实施here 提到的解决方法,以解决当用户放大绘图时触发draw_event 时图形无法正确更新的问题。这是为了改进this answer。在解决方案中,在Figure 的Canvas 中添加了一个Timer,这会延迟绘制功能一小会儿。
在链接的答案中,这是针对单个图形完成的,对计时器的引用存储为 self.timer 到包含更新函数的类。我希望有一些更一般的行为,并允许对许多 Figure 实例进行此操作。因此我尝试不保存Timer 参考(我不再需要它了)。但是当我这样做时,脚本会因分段错误(无回溯)而崩溃。这是我的代码:
from matplotlib import pyplot as plt
import numpy as np
##plt.switch_backend('TkAgg')
class DrawEventHandler:
def __init__(self):
x = np.linspace(0,1,10)
y = np.sin(x)
self.fig, self.ax = plt.subplots()
self.ax.plot(x,y)
self.ax.figure.canvas.mpl_connect('draw_event', self.update)
def update(self, event = None):
self._redraw_later_ok()
##self._redraw_later_not_ok(self.fig)
def _redraw_later_ok(self):
self.timer = self.fig.canvas.new_timer(interval=10)
self.timer.single_shot = True
self.timer.add_callback(lambda : self.fig.canvas.draw_idle())
self.timer.start()
def _redraw_later_not_ok(self, fig):
print('start')
timer = fig.canvas.new_timer(interval=10)
timer.single_shot = True
timer.add_callback(lambda : fig.canvas.draw_idle())
timer.start()
print('stop')
if __name__ == '__main__':
my_handler = DrawEventHandler()
plt.show()
原始解决方案实现为_redraw_later_ok(),对我来说效果很好。有问题的解决方案称为 `_redraw_later_not_ok()',它会产生以下输出:
start
stop
Segmentation fault: 11
我使用带有 High Sierra、Python 3.6.4 或 Python 2.7.14 和 Matplotlib 2.1.1 以及 MacOSX 后端的 Mac。当我切换到TkAgg 后端(非常慢)时,代码工作正常。谁能解释一下是怎么回事?
【问题讨论】:
-
为什么需要上交
self.fig作为参数?您可以随时直接访问它。 -
@MikeMüller 在这种情况下是的,但这只是为了 MCVE。我的真实例子更复杂。我会将其链接到问题。
标签: python macos matplotlib