Repository: nvaccess/nvda

Issue:
Context Sensitive Help in NVDA Dialogs
### Steps to reproduce:

* NVDA has a well thought out user guide, but it is prohibitively long for new users. A new user needs to be able to get help relevant to what they are doing while they are working in various dialogs and controls with NVDA.
* Some controls in NVDA preferences dialogs have long labels which cause them not to fit well visually (see #6345). These labels can be shortened if additional help for these controls is readily available with F1 or by pressing a Help button.

### Expected behavior:

1. Explicit anchors should be added to all sections of the NVDA User Guide so that it can be opened to the correct place when context help is invoked.
2. When in an NVDA preference dialog a Help button should be available to open the NVDA User Guide  for all controls in that dialog.
3. Optionally, pressing F1 on any control within an NVDA Preference dialog should open the NVDA User Guide to the section describing the function of that specific control if one exists, or for the dialog if no explicit help exists.

### Actual behavior:

Currently NVDA's preferences dialogs do not have a help button and do not respond to the F1 key. The NVDA User Guide explains NVDA's dialogs and controls in detail, but new users find it daunting to locate information quickly.

### Similar issues which this is not:

* Providing context sensitive help for NVDA's dialogs is not a tutor mode as in #3232.
* This issue is not intended to provide general Windows help as in #2699.


Discussion:
This sounds like a good idea. Happy to accept a PR for this, though I would suggest the work is split into 3 PR's one for each of the points listed under expected behaviour.
If we want to use context sensitive help from the user guide, I belief it would help a lot if we'd show the user guide in a ui.browseableMessage
@ThomasStivers commented:
> 3.	Optionally, pressing F1 on any control within an NVDA Preference dialog should open the NVDA User Guide to the section describing the function of that specific control if one exists, or for the dialog if no explicit help exists.

It seems like pulling up the entire user guide and pointing to specific sections for each control might be a more intensive process. I have thought for some time that NVDA help in the form of a long document, while extremely useful, is becoming less manageable from a usability perspective. I would encourage NVAccess to consider a modular approach to help and documentation that could support tutorial work as well as the current set of user documentation.
Hi, overall, this is similar in scope to (now discontinued) Control Usage Assistant add-on with help on NVDA options added. CC @DerekRiemer

Resolving patch:
diff --git a/source/gui/__init__.py b/source/gui/__init__.py
--- a/source/gui/__init__.py
+++ b/source/gui/__init__.py
@@ -80,7 +80,7 @@ def getDocFilePath(fileName, localized=True):
 				tryPath = os.path.join(tryDir, "%s.%s" % (fileName, tryExt))
 				if os.path.isfile(tryPath):
 					return tryPath
-
+		return None
 	else:
 		# Not localized.
 		if not hasattr(sys, "frozen") and fileName in ("copying.txt", "contributors.txt"):
diff --git a/source/gui/contextHelp.py b/source/gui/contextHelp.py
--- a/source/gui/contextHelp.py
+++ b/source/gui/contextHelp.py
@@ -6,6 +6,7 @@
 import os
 import tempfile
 import typing
+import queueHandler
 
 import gui
 import ui
@@ -29,16 +30,18 @@ def showHelp(helpId: str):
 	recognized control.
 	"""
 	if not helpId:
-		# Translators: Message indicating no context sensitive help is available.
-		noHelpMessage = _("No context sensitive help is available here at this time.")
-		ui.message(noHelpMessage)
+		# Translators: Message indicating no context sensitive help is available for the control or dialog.
+		noHelpMessage = _("No help available here.")
+		queueHandler.queueFunction(queueHandler.eventQueue, ui.message, noHelpMessage)
+		return
 	helpFile = gui.getDocFilePath("userGuide.html")
-	if not os.path.exists(helpFile):
+	if helpFile is None:
 		# Translators: Message shown when trying to display context sensitive help,
 		# indicating that	the user guide could not be found.
 		noHelpMessage = _("No user guide found.")
 		log.debugWarning("No user guide found: possible cause - running from source without building user docs")
-		ui.message(noHelpMessage)
+		queueHandler.queueFunction(queueHandler.eventQueue, ui.message, noHelpMessage)
+		return
 	log.debug(f"Opening help: helpId = {helpId}, userGuidePath: {helpFile}")
 
 	nvdaTempDir = os.path.join(tempfile.gettempdir(), "nvda")


Test patch: