22
22
import re
23
23
24
24
import urwid
25
- try :
26
- from urwid .widget import SelectableIcon
27
- except ImportError :
28
- # BACK COMPAT: urwid.wimp
29
- # From: urwid 2.0
30
- # To: urwid 2.2
31
- from urwid .wimp import SelectableIcon
25
+ from urwid .canvas import CanvasCache
26
+ from urwid .widget import SelectableIcon
32
27
33
28
from cylc .flow .id import Tokens
34
29
from cylc .flow .task_state import (
@@ -515,8 +510,11 @@ def update(self, *_):
515
510
_ , old_node = self .listbox .body .get_focus ()
516
511
517
512
# nuke the tree
518
- self .tree_walker = urwid .TreeWalker (topnode )
519
- self .listbox .body = self .tree_walker
513
+ if not (self .tree_walker ):
514
+ self .tree_walker = urwid .TreeWalker (topnode )
515
+ self .listbox .body = self .tree_walker
516
+ else :
517
+ self .tree_walker .set_focus (topnode )
520
518
521
519
# get the new focus
522
520
_ , new_node = self .listbox .body .get_focus ()
@@ -538,6 +536,11 @@ def update(self, *_):
538
536
if self .loop :
539
537
self .loop .set_alarm_in (self .UPDATE_INTERVAL , self .update )
540
538
539
+ # NOTE: prevent a memory leak by clearing out any caches that urwid
540
+ # may have accumulated for the previous TuiNode instance
541
+ # (and its child widgets)
542
+ CanvasCache .clear ()
543
+
541
544
return True
542
545
543
546
def filter_by_task_state (self , filtered_state = None ):
0 commit comments