Repository: nvaccess/nvda

Issue:
Bug using routing cursor in latest alpha
<!-- Please read the text in this edit field before filling it in.
Please thoroughly read NVDA's wiki article on how to fill in this template, including how to provide the required files.
Issues may be closed if the required information is not present.
https://github.com/nvaccess/nvda/wiki/Github-issue-template-explanation-and-examples
Please also note that the NVDA project has a Citizen and Contributor Code of Conduct which can be found at https://github.com/nvaccess/nvda/blob/master/CODE_OF_CONDUCT.md. NV Access expects that all contributors and other community members read and abide by the rules set out in this document while participating or contributing to this project. This includes creating or commenting on issues and pull requests. 
-->

### Steps to reproduce:
- Select a text (for example in a text editor)
- Try to move cursor in a cell using routing cursor on braille display

### Actual behavior:
- Cursor doesn't move, and selection is still present

### Expected behavior:
- Moving cursor to cell and deselect text

### System configuration
#### NVDA installed/portable/running from source:
- Installed

#### NVDA version:
- alpha-21668,e8f14f9a

#### Windows version:
- 10.0.19042.746

#### Name and version of other software in use when reproducing the issue:
- Notepad for example

#### Other information about your system:

### Other questions
#### Does the issue still occur after restarting your computer?
- Yes

#### Have you tried any other versions of NVDA? If so, please report their behaviors.
- No

#### If addons are disabled, is your problem still occuring?
- Yes

#### Did you try to run the COM registry fixing tool in NVDA menu / tools?
- No



Discussion:
Regarding routing cursors, #11922 was merged quite recently.
@JulienCochuyt may this be related?

@Oreonan (or anyone else able to reproduce), would you be able to test on source code the following commits:
* code based on commit 5daf693f3aae504c414b3b62a7f651af929952aa: the build just before #11922 was merged
* code based on commit 33cd507817fbefbc0d1c46db13ea8768cde00c25: first build including #11922

I do not have any braille display here at home to try to reproduce.


Yes, I think it's this PR who cause problems.
Confirmed as a regression from #11922. The following is in the log  after pressing a routing button:

ERROR - scriptHandler.executeScript (17:41:20.708) - MainThread (3856):
error executing script: <bound method GlobalCommands.script_braille_routeTo of <globalCommands.GlobalCommands object at 0x05445050>> with gesture 'routing'
Traceback (most recent call last):
  File "scriptHandler.pyc", line 208, in executeScript
  File "globalCommands.pyc", line 2735, in script_braille_routeTo
  File "braille.pyc", line 1852, in routeTo
  File "braille.pyc", line 1449, in routeTo
  File "braille.pyc", line 1095, in routeTo
  File "braille.pyc", line 1069, in getTextInfoForBraillePos
TypeError: list indices must be integers or slices, not NoneType


cc @JulienCochuyt 
Another, hard to reproduce, bug that might be related is the cursor routing in textareas on Chromium-based browsers. In many textareas pressing a routing button routes to the wrong location within that textarea. Usually a few lines above where the cursor should route.
@feerrenrut, @seanbudd, would you consider labeling this issue for NVDA 2021.1, since it is a regression in current alpha stage (already present befor py38)?
Thanks.


I can also confirm both routing key problems, that in NotePad and that in Chromium-based browsers.
I would add that this is a very annoying problem.
I can reproduce this issue with the braille viewer and notepad.exe, using the hover mouse to route option.

Resolving patch:
diff --git a/source/braille.py b/source/braille.py
--- a/source/braille.py
+++ b/source/braille.py
@@ -407,8 +407,7 @@ def __init__(self):
 		#: @type: [int, ...]
 		self.brailleToRawPos = []
 		#: The position of the cursor in L{brailleCells}, C{None} if the cursor is not in this region.
-		#: @type: int
-		self.brailleCursorPos = None
+		self.brailleCursorPos: Optional[int] = None
 		#: The position of the selection start in L{brailleCells}, C{None} if there is no selection in this region.
 		#: @type: int
 		self.brailleSelectionStart = None
@@ -1094,15 +1093,20 @@ def routeTo(self, braillePos):
 			return
 
 		dest = self.getTextInfoForBraillePos(braillePos)
-		cursor = self.getTextInfoForBraillePos(self.brailleCursorPos)
-		if dest.compareEndPoints(cursor, "startToStart") == 0:
-			# The cursor is already at this position,
-			# so activate the position.
-			try:
-				self._getSelection().activate()
-			except NotImplementedError:
-				pass
-			return
+		# When there is a selection, brailleCursorPos will be None
+		# Don't activate, but move the cursor to the new cell (dropping the
+		# selection). An alternative behavior may be to activate on the selection.
+		# Moving the cursor was considered more intuitive.
+		if self.brailleCursorPos is not None:
+			cursor = self.getTextInfoForBraillePos(self.brailleCursorPos)
+			if dest.compareEndPoints(cursor, "startToStart") == 0:
+				# The cursor is already at this position,
+				# so activate the position.
+				try:
+					self._getSelection().activate()
+				except NotImplementedError:
+					pass
+				return
 		self._setCursor(dest)
 
 	def nextLine(self):


Test patch: