bpo-37530: simplify, optimize and clean up IDLE code context (GH-14675)
* Only create CodeContext instances for "real" editors windows, but
not e.g. shell or output windows.
* Remove configuration update Tk event fired every second, by having
the editor window ask its code context widget to update when
necessary, i.e. upon font or highlighting updates.
* When code context isn't being shown, avoid having a Tk event fired
every 100ms to check whether the code context needs to be updated.
* Use the editor window's getlineno() method where applicable.
* Update font of the code context widget before the main text widget
diff --git a/Lib/idlelib/editor.py b/Lib/idlelib/editor.py
index 9b5364f..b972e3d 100644
--- a/Lib/idlelib/editor.py
+++ b/Lib/idlelib/editor.py
@@ -62,6 +62,8 @@
filesystemencoding = sys.getfilesystemencoding() # for file names
help_url = None
+ allow_codecontext = True
+
def __init__(self, flist=None, filename=None, key=None, root=None):
# Delay import: runscript imports pyshell imports EditorWindow.
from idlelib.runscript import ScriptBinding
@@ -247,6 +249,7 @@
self.good_load = False
self.set_indentation_params(False)
self.color = None # initialized below in self.ResetColorizer
+ self.codecontext = None
if filename:
if os.path.exists(filename) and not os.path.isdir(filename):
if io.loadfile(filename):
@@ -312,8 +315,10 @@
text.bind("<<refresh-calltip>>", ctip.refresh_calltip_event)
text.bind("<<force-open-calltip>>", ctip.force_open_calltip_event)
text.bind("<<zoom-height>>", self.ZoomHeight(self).zoom_height_event)
- text.bind("<<toggle-code-context>>",
- self.CodeContext(self).toggle_code_context_event)
+ if self.allow_codecontext:
+ self.codecontext = self.CodeContext(self)
+ text.bind("<<toggle-code-context>>",
+ self.codecontext.toggle_code_context_event)
def _filename_to_unicode(self, filename):
"""Return filename as BMP unicode so displayable in Tk."""
@@ -773,6 +778,9 @@
self._addcolorizer()
EditorWindow.color_config(self.text)
+ if self.codecontext is not None:
+ self.codecontext.update_highlight_colors()
+
IDENTCHARS = string.ascii_letters + string.digits + "_"
def colorize_syntax_error(self, text, pos):
@@ -790,7 +798,12 @@
"Update the text widgets' font if it is changed"
# Called from configdialog.py
- self.text['font'] = idleConf.GetFont(self.root, 'main','EditorWindow')
+ new_font = idleConf.GetFont(self.root, 'main', 'EditorWindow')
+ # Update the code context widget first, since its height affects
+ # the height of the text widget. This avoids double re-rendering.
+ if self.codecontext is not None:
+ self.codecontext.update_font(new_font)
+ self.text['font'] = new_font
def RemoveKeybindings(self):
"Remove the keybindings before they are changed."