Skip to content

bpo-39781: Do not jump when select in IDLE codecontext #18683

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 6 commits into from
Feb 28, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions Lib/idlelib/NEWS.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ Released on 2020-10-05?
======================================


bpo-39781: Selecting code context lines no longer causes a jump.

bpo-39663: Add tests for pyparse find_good_parse_start().

bpo-39600: Remove duplicate font names from configuration list.
Expand Down
44 changes: 25 additions & 19 deletions Lib/idlelib/codecontext.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
enclosing block. The number of hint lines is determined by the maxlines
variable in the codecontext section of config-extensions.def. Lines which do
not open blocks are not shown in the context hints pane.

"""
import re
from sys import maxsize as INFINITY
Expand All @@ -17,8 +16,8 @@

from idlelib.config import idleConf

BLOCKOPENERS = {"class", "def", "elif", "else", "except", "finally", "for",
"if", "try", "while", "with", "async"}
BLOCKOPENERS = {'class', 'def', 'if', 'elif', 'else', 'while', 'for',
'try', 'except', 'finally', 'with', 'async'}


def get_spaces_firstword(codeline, c=re.compile(r"^(\s*)(\w*)")):
Expand Down Expand Up @@ -84,7 +83,7 @@ def __del__(self):
if self.t1 is not None:
try:
self.text.after_cancel(self.t1)
except tkinter.TclError:
except tkinter.TclError: # pragma: no cover
pass
self.t1 = None

Expand Down Expand Up @@ -112,19 +111,19 @@ def toggle_code_context_event(self, event=None):
padx += widget.tk.getint(info['padx'])
padx += widget.tk.getint(widget.cget('padx'))
border += widget.tk.getint(widget.cget('border'))
self.context = tkinter.Text(
context = self.context = tkinter.Text(
self.editwin.text_frame,
height=1,
width=1, # Don't request more than we get.
highlightthickness=0,
padx=padx, border=border, relief=SUNKEN, state='disabled')
self.update_font()
self.update_highlight_colors()
self.context.bind('<ButtonRelease-1>', self.jumptoline)
context.bind('<ButtonRelease-1>', self.jumptoline)
# Get the current context and initiate the recurring update event.
self.timer_event()
# Grid the context widget above the text widget.
self.context.grid(row=0, column=1, sticky=NSEW)
context.grid(row=0, column=1, sticky=NSEW)

line_number_colors = idleConf.GetHighlight(idleConf.CurrentTheme(),
'linenumber')
Expand Down Expand Up @@ -215,18 +214,25 @@ def update_code_context(self):
self.context['state'] = 'disabled'

def jumptoline(self, event=None):
"Show clicked context line at top of editor."
lines = len(self.info)
if lines == 1: # No context lines are showing.
newtop = 1
else:
# Line number clicked.
contextline = int(float(self.context.index('insert')))
# Lines not displayed due to maxlines.
offset = max(1, lines - self.context_depth) - 1
newtop = self.info[offset + contextline][0]
self.text.yview(f'{newtop}.0')
self.update_code_context()
""" Show clicked context line at top of editor.

If a selection was made, don't jump; allow copying.
If no visible context, show the top line of the file.
"""
try:
self.context.index("sel.first")
except tkinter.TclError:
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Everything after this is the old code indented.

lines = len(self.info)
if lines == 1: # No context lines are showing.
newtop = 1
else:
# Line number clicked.
contextline = int(float(self.context.index('insert')))
# Lines not displayed due to maxlines.
offset = max(1, lines - self.context_depth) - 1
newtop = self.info[offset + contextline][0]
self.text.yview(f'{newtop}.0')
self.update_code_context()

def timer_event(self):
"Event on editor text widget triggered every UPDATEINTERVAL ms."
Expand Down
8 changes: 8 additions & 0 deletions Lib/idlelib/idle_test/test_codecontext.py
Original file line number Diff line number Diff line change
Expand Up @@ -332,6 +332,14 @@ def test_jumptoline(self):
jump()
eq(cc.topvisible, 8)

# Context selection stops jump.
cc.text.yview('5.0')
cc.update_code_context()
cc.context.tag_add('sel', '1.0', '2.0')
cc.context.mark_set('insert', '1.0')
jump() # Without selection, to line 2.
eq(cc.topvisible, 5)

@mock.patch.object(codecontext.CodeContext, 'update_code_context')
def test_timer_event(self, mock_update):
# Ensure code context is not active.
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Selecting code context lines no longer causes a jump.