Skip to content

Commit 2bb94a9

Browse files
authored
Merge 214d09e into 9f8fff8
2 parents 9f8fff8 + 214d09e commit 2bb94a9

8 files changed

Lines changed: 56 additions & 31 deletions

File tree

source/NVDAObjects/IAccessible/winConsole.py

Lines changed: 1 addition & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -27,15 +27,7 @@ class LegacyWinConsole(winConsole.WinConsole, IAccessible):
2727
NVDA's original console support, used by default on Windows versions
2828
before 1607.
2929
"""
30-
31-
def _get_diffAlgo(self):
32-
# Non-enhanced legacy consoles use caret proximity to detect
33-
# typed/deleted text.
34-
# Single-character changes are not reported as
35-
# they are confused for typed characters.
36-
# Force difflib to keep meaningful edit reporting in these consoles.
37-
from diffHandler import get_difflib_algo
38-
return get_difflib_algo()
30+
pass
3931

4032

4133
def findExtraOverlayClasses(obj, clsList):

source/NVDAObjects/UIA/winConsoleUIA.py

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
import UIAHandler
1111

1212
from comtypes import COMError
13+
from diffHandler import prefer_difflib
1314
from logHandler import log
1415
from UIAUtils import _getConhostAPILevel
1516
from _UIAConstants import WinConsoleAPILevel
@@ -379,6 +380,14 @@ def _get_devInfo(self):
379380
info.append(f"API level: {self.apiLevel} ({self.apiLevel.name})")
380381
return info
381382

383+
def _get_diffAlgo(self):
384+
if self.apiLevel < WinConsoleAPILevel.FORMATTED:
385+
# #12974: These consoles are constrained to onscreen text.
386+
# Use Difflib to reduce choppiness in reading.
387+
return prefer_difflib()
388+
else:
389+
return super().diffAlgo
390+
382391
def detectPossibleSelectionChange(self):
383392
try:
384393
return super().detectPossibleSelectionChange()

source/NVDAObjects/behaviors.py

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -266,17 +266,20 @@ def event_textChange(self):
266266
"""
267267
self._event.set()
268268

269-
def _get_diffAlgo(self):
269+
def _get_diffAlgo(self) -> Union[diffHandler.prefer_difflib, diffHandler.prefer_dmp]:
270270
"""
271271
This property controls which diffing algorithm should be used by
272-
this object. Most subclasses should simply use the base
273-
implementation, which returns DMP (character-based diffing).
272+
this object. If the object contains a strictly contiguous
273+
span of text (i.e. textInfos.POSITION_ALL refers to the entire
274+
contents of the object and not just one visible screen of text),
275+
then diffHandler.prefer_dmp (character-based diffing) is suitable.
276+
Otherwise, use diffHandler.prefer_difflib.
274277
275-
@Note: DMP is experimental, and can be disallowed via user
276-
preference. In this case, the prior stable implementation, Difflib
277-
(line-based diffing), will be used.
278+
@Note: Return either diffHandler.prefer_dmp() or
279+
diffHandler.prefer_difflib() so that the diffAlgo user
280+
preference can override this choice.
278281
"""
279-
return diffHandler.get_dmp_algo()
282+
return diffHandler.prefer_dmp()
280283

281284
def _get_devInfo(self):
282285
info = super().devInfo

source/NVDAObjects/window/__init__.py

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
from NVDAObjects.behaviors import EditableText, EditableTextWithoutAutoSelectDetection, LiveText
2020
import watchdog
2121
from locationHelper import RectLTWH
22+
from diffHandler import prefer_difflib
2223

2324
re_WindowsForms=re.compile(r'^WindowsForms[0-9]*\.(.*)\.app\..*$')
2425
re_ATL=re.compile(r'^ATL:(.*)$')
@@ -413,6 +414,12 @@ def stopMonitoring(self):
413414
super(DisplayModelLiveText, self).stopMonitoring()
414415
displayModel.requestTextChangeNotifications(self, False)
415416

417+
def _get_diffAlgo(self):
418+
# #12974: The display model gives us only one screen of text at a time.
419+
# Use Difflib to reduce choppiness in reading.
420+
return prefer_difflib()
421+
422+
416423
windowClassMap={
417424
"EDIT":"Edit",
418425
"TTntEdit.UnicodeClass":"Edit",

source/NVDAObjects/window/winConsole.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
import core
1111
from scriptHandler import script
1212
import speech
13+
from diffHandler import prefer_difflib
1314

1415
class WinConsole(Terminal, EditableTextWithoutAutoSelectDetection, Window):
1516
"""
@@ -36,6 +37,11 @@ def _get_TextInfo(self):
3637
return winConsoleHandler.WinConsoleTextInfo
3738
return super(WinConsole,self).TextInfo
3839

40+
def _get_diffAlgo(self):
41+
# #12974: Legacy consoles contain only one screen of text at a time.
42+
# Use Difflib to reduce choppiness in reading.
43+
return prefer_difflib()
44+
3945
def event_becomeNavigatorObject(self, isFocus=False):
4046
if winConsoleHandler.consoleObject is not self:
4147
if winConsoleHandler.consoleObject:

source/diffHandler.py

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -176,7 +176,7 @@ def _getText(self, ti: TextInfo) -> str:
176176
return "\n".join(ti.getTextInChunks(UNIT_LINE))
177177

178178

179-
def get_dmp_algo():
179+
def prefer_dmp():
180180
"""
181181
This function returns a Diff Match Patch object if allowed by the user.
182182
DMP is new and can be explicitly disabled by a user setting. If config
@@ -189,9 +189,17 @@ def get_dmp_algo():
189189
)
190190

191191

192-
def get_difflib_algo():
193-
"Returns an instance of the difflib diffAlgo."
194-
return _difflib
192+
def prefer_difflib():
193+
"""
194+
This function returns a Difflib object if allowed by the user.
195+
Difflib can be explicitly disabled by a user setting. If config
196+
does not allow Difflib, this function returns a DMP instance instead.
197+
"""
198+
return (
199+
_dmp
200+
if config.conf["terminals"]["diffAlgo"] == "dmp"
201+
else _difflib
202+
)
195203

196204

197205
_difflib = Difflib()

source/gui/settingsDialogs.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2730,21 +2730,21 @@ def __init__(self, parent):
27302730
# Translators: This is the label for a combo box for selecting a
27312731
# method of detecting changed content in terminals in the advanced
27322732
# settings panel.
2733-
# Choices are automatic, allow Diff Match Patch, and force Difflib.
2733+
# Choices are automatic, Diff Match Patch, and Difflib.
27342734
diffAlgoComboText = _("&Diff algorithm:")
27352735
diffAlgoChoices = [
27362736
# Translators: A choice in a combo box in the advanced settings
27372737
# panel to have NVDA determine the method of detecting changed
27382738
# content in terminals automatically.
2739-
_("Automatic (Diff Match Patch)"),
2739+
_("Automatic (prefer Diff Match Patch)"),
27402740
# Translators: A choice in a combo box in the advanced settings
27412741
# panel to have NVDA detect changes in terminals
2742-
# by character when supported, using the diff match patch algorithm.
2743-
_("allow Diff Match Patch"),
2742+
# by character, using the diff match patch algorithm.
2743+
_("Diff Match Patch"),
27442744
# Translators: A choice in a combo box in the advanced settings
27452745
# panel to have NVDA detect changes in terminals
27462746
# by line, using the difflib algorithm.
2747-
_("force Difflib")
2747+
_("Difflib")
27482748
]
27492749
#: The possible diffAlgo config values, in the order they appear
27502750
#: in the combo box.

user_docs/en/userGuide.t2t

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1901,14 +1901,14 @@ In untrusted environments, you may temporarily disable [speak typed characters #
19011901
==== Diff algorithm ====[DiffAlgo]
19021902
This setting controls how NVDA determines the new text to speak in terminals.
19031903
The diff algorithm combo box has three options:
1904-
- Automatic: as of NVDA 2021.2, this option is equivalent to "allow Diff Match Patch".
1905-
- allow Diff Match Patch: This option causes NVDA to calculate changes to terminal text by character.
1904+
- Automatic: This option causes NVDA to prefer Diff Match Patch in most situations, but fall back to Difflib in problematic applications, such as older versions of the Windows Console and Mintty.
1905+
- Diff Match Patch: This option causes NVDA to calculate changes to terminal text by character, even in situations where it is not recommended.
19061906
It may improve performance when large volumes of text are written to the console and allow more accurate reporting of changes made in the middle of lines.
1907-
However, it may be incompatible with some applications, so Diff Match Patch is not always used.
1908-
This feature is supported in Windows Console on Windows 10 versions 1607 and later.
1909-
Additionally, it may be available in other terminals on earlier Windows releases.
1910-
- force Difflib: this option causes NVDA to calculate changes to terminal text by line.
1907+
However, in some applications, reading of new text may be choppy or inconsistent.
1908+
- Difflib: this option causes NVDA to calculate changes to terminal text by line, even in situations where it is not recommended.
19111909
It is identical to NVDA's behaviour in versions 2020.4 and earlier.
1910+
This setting may stabilize reading of incoming text in some applications.
1911+
However, in terminals, when inserting or deleting a character in the middle of a line, the text after the caret will be read out.
19121912
-
19131913

19141914
==== Attempt to cancel speech for expired focus events ====[CancelExpiredFocusSpeech]

0 commit comments

Comments
 (0)