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 (
@@ -516,8 +511,11 @@ def update(self, *_):
516
511
_ , old_node = self .listbox .body .get_focus ()
517
512
518
513
# nuke the tree
519
- self .tree_walker = urwid .TreeWalker (topnode )
520
- self .listbox .body = self .tree_walker
514
+ if not (self .tree_walker ):
515
+ self .tree_walker = urwid .TreeWalker (topnode )
516
+ self .listbox .body = self .tree_walker
517
+ else :
518
+ self .tree_walker .set_focus (topnode )
521
519
522
520
# get the new focus
523
521
_ , new_node = self .listbox .body .get_focus ()
@@ -539,6 +537,11 @@ def update(self, *_):
539
537
if self .loop :
540
538
self .loop .set_alarm_in (self .UPDATE_INTERVAL , self .update )
541
539
540
+ # NOTE: prevent a memory leak by clearing out any caches that urwid
541
+ # may have accumulated for the previous TuiNode instance
542
+ # (and its child widgets)
543
+ CanvasCache .clear ()
544
+
542
545
return True
543
546
544
547
def filter_by_task_state (self , filtered_state = None ):
0 commit comments