class BrailleViewerSpy:
    postBrailleUpdate = extensionPoints.Action()

    def __init__(self):
        self._last = ""

    def updateBrailleDisplayed(
            self,
            cells,  # ignored
            rawText,
            currentCellCount,  # ignored
    ):
        rawText = rawText.strip()
        if rawText and rawText != self._last:
            self._last = rawText
            self.postBrailleUpdate.notify(rawText=rawText)

    isDestroyed: bool = False

    def saveInfoAndDestroy(self):
        if not self.isDestroyed:
            self.isDestroyed = True
            import brailleViewer
            brailleViewer._onGuiDestroyed()
Beispiel #2
0
import sys
import winVersion
import threading
import nvwave
import os
import time
import ctypes
import logHandler
import globalVars
from logHandler import log
import addonHandler
import extensionPoints
import garbageHandler  # noqa: E402

# inform those who want to know that NVDA has finished starting up.
postNvdaStartup = extensionPoints.Action()

PUMP_MAX_DELAY = 10

#: The thread identifier of the main thread.
mainThreadId = threading.get_ident()

#: Notifies when a window message has been received by NVDA.
#: This allows components to perform an action when several system events occur,
#: such as power, screen orientation and hardware changes.
#: Handlers are called with three arguments.
#: @param msg: The window message.
#: @type msg: int
#: @param wParam: Additional message information.
#: @type wParam: int
#: @param lParam: Additional message information.
Beispiel #3
0
import tempfile
import hashlib
import wx
import gui
from gui import guiHelper
from logHandler import log
import addonHandler
import updateCheck
import core
import extensionPoints
from gui.nvdaControls import AutoWidthColumnCheckListCtrl
from .skipTranslation import translate
# Temporary
addonHandler.initTranslation()

AddonUpdaterManualUpdateCheck = extensionPoints.Action()

_progressDialog = None

# The following event handler comes from a combination of StationPlaylist Studio and Windows 10 App Essentials.


def onAddonUpdateCheck(evt):
    AddonUpdaterManualUpdateCheck.notify()
    global _progressDialog
    _progressDialog = gui.IndeterminateProgressDialog(
        gui.mainFrame,
        # Translators: The title of the dialog presented while checking for add-on updates.
        _("Add-on update check"),
        # Translators: The message displayed while checking for add-on updates.
        _("Checking for add-on updates..."))
Beispiel #4
0
from . import profileUpgrader
from .configSpec import confspec
from typing import Any, Dict, List, Optional, Set

#: True if NVDA is running as a Windows Store Desktop Bridge application
isAppX=False

#: The active configuration, C{None} if it has not yet been loaded.
#: @type: ConfigManager
conf = None

#: Notifies when the configuration profile is switched.
#: This allows components and add-ons to apply changes required by the new configuration.
#: For example, braille switches braille displays if necessary.
#: Handlers are called with no arguments.
post_configProfileSwitch = extensionPoints.Action()
#: Notifies when NVDA is saving current configuration.
#: Handlers can listen to "pre" and/or "post" action to perform tasks prior to and/or after NVDA's own configuration is saved.
#: Handlers are called with no arguments.
pre_configSave = extensionPoints.Action()
post_configSave = extensionPoints.Action()
#: Notifies when configuration is reloaded from disk or factory defaults are applied.
#: Handlers can listen to "pre" and/or "post" action to perform tasks prior to and/or after NVDA's own configuration is reloaded.
#: Handlers are called with a boolean argument indicating whether this is a factory reset (True) or just reloading from disk (False).
pre_configReset = extensionPoints.Action()
post_configReset = extensionPoints.Action()

def initialize():
	global conf
	conf = ConfigManager()
Beispiel #5
0
import appModules
import exceptions
import extensionPoints
from fileUtils import getFileVersionInfo

# Dictionary of processID:appModule pairs used to hold the currently running modules
runningTable: Dict[int, AppModule] = {}
#: The process ID of NVDA itself.
NVDAProcessID = None
_importers = None
_getAppModuleLock = threading.RLock()
#: Notifies when another application is taking foreground.
#: This allows components to react upon application switches.
#: For example, braille triggers bluetooth polling for braille displaysf necessary.
#: Handlers are called with no arguments.
post_appSwitch = extensionPoints.Action()


class processEntry32W(ctypes.Structure):
    _fields_ = [("dwSize", ctypes.wintypes.DWORD),
                ("cntUsage", ctypes.wintypes.DWORD),
                ("th32ProcessID", ctypes.wintypes.DWORD),
                ("th32DefaultHeapID", ctypes.wintypes.DWORD),
                ("th32ModuleID", ctypes.wintypes.DWORD),
                ("cntThreads", ctypes.wintypes.DWORD),
                ("th32ParentProcessID", ctypes.wintypes.DWORD),
                ("pcPriClassBase", ctypes.c_long),
                ("dwFlags", ctypes.wintypes.DWORD),
                ("szExeFile", ctypes.c_wchar * 260)]

Beispiel #6
0
	This is what happens by default.
	However, Speech itself may call this with false internally if this is a config profile switch within a
	currently processing speech sequence.
	@type resetSpeechIfNeeded: bool
	"""
    conf = config.conf["speech"]
    if conf["synth"] != _curSynth.name or conf[
            "outputDevice"] != _audioOutputDevice:
        if resetSpeechIfNeeded:
            # Reset the speech queues as we are now going to be using a new synthesizer with entirely separate state.
            import speech
            speech.cancelSpeech()
        setSynth(conf["synth"])
        return
    _curSynth.loadSettings(onlyChanged=True)


def isDebugForSynthDriver():
    return config.conf["debugLog"]["synthDriver"]


#: Notifies when a synthesizer reaches an index during speech.
#: Handlers are called with these keyword arguments:
#: synth: The L{SynthDriver} which reached the index.
#: index: The number of the index which has just been reached.
synthIndexReached = extensionPoints.Action()
#: Notifies when a synthesizer finishes speaking.
#: Handlers are called with one keyword argument:
#: synth: The L{SynthDriver} which reached the index.
synthDoneSpeaking = extensionPoints.Action()
Beispiel #7
0
### Scrolling
Scrolling is supported by binding a gesture to the braille_scroll_forward and braille scroll_back commands.
For the same reason that Routing is not supported, scrolling via button clicks on the braille viewer window
is not supported.

"""

# global braille viewer driver:
_brailleGui: Optional[BrailleViewerFrame] = None

# Extension points action:
# Triggered every time the Braille Viewer is created / shown or hidden / destroyed.
# Callback definition: Callable(created: bool) -> None
#   created - True for created/shown, False for hidden/destructed.
postBrailleViewerToolToggledAction = extensionPoints.Action()
# Devices with 40 cells are quite common.
DEFAULT_NUM_CELLS = 40


def isBrailleViewerActive() -> bool:
	return bool(_brailleGui)


def update(cells: List[int], rawText: str):
	if _brailleGui:
		_brailleGui.updateBrailleDisplayed(
			cells,
			rawText,
			_getDisplaySize()
		)
Beispiel #8
0
 def setUp(self):
     self.action = extensionPoints.Action()
Beispiel #9
0
import extensionPoints
from config import post_configSave, post_configReset, post_configProfileSwitch
from .unspoken import UnspokenPlayer, libaudioverse, dll_hack

import addonHandler
addonHandler.initTranslation()

THEMES_DIR = os.path.join(os.path.dirname(__file__), "Themes")
INFO_FILE_NAME = "info.json"
SUPPORTED_FILE_TYPES = OrderedDict()
# Translators: The file type to be shown in a dialog used to browse for audio files.
SUPPORTED_FILE_TYPES["ogg"] = _("Ogg audio files")
# Translators: The file type to be shown in a dialog used to browse for audio files.
SUPPORTED_FILE_TYPES["wav"] = _("Wave audio files")
# When the active audio theme is being changed
audiotheme_changed = extensionPoints.Action()

# Configuration spec
audiothemes_config_defaults = {
    "enable_audio_themes": "boolean(default=    True)",
    "active_theme": 'string(default="Default")',
    "audio3d": "boolean(default=True)",
    "use_in_say_all": "boolean(default=True)",
    "speak_roles": "boolean(default=False)",
    "use_synth_volume": "boolean(default=True)",
    "volume": "integer(default=100)",
}


class SpecialProps(IntEnum):
    """Represents sounds defined by this addon."""
Beispiel #10
0
import extensionPoints
import profileUpgrader
from .configSpec import confspec

#: True if NVDA is running as a Windows Store Desktop Bridge application
isAppX=False

#: The active configuration, C{None} if it has not yet been loaded.
#: @type: ConfigObj
conf = None

#: Notifies when the configuration profile is switched.
#: This allows components to apply changes required by the new configuration.
#: For example, braille switches braille displays if necessary.
#: Handlers are called with no arguments.
configProfileSwitched = extensionPoints.Action()

def initialize():
	global conf
	conf = ConfigManager()

def saveOnExit():
	"""Save the configuration if configured to save on exit.
	This should only be called if NVDA is about to exit.
	Errors are ignored.
	"""
	if conf["general"]["saveConfigurationOnExit"]:
		try:
			conf.save()
		except:
			pass
Beispiel #11
0
# Copyright (C) 2020 NV Access Limited
# This file is covered by the GNU General Public License.
# See the file COPYING for more details.
"""
This module is copied to the scratchPad/synthDrivers folder and set as the synthesizer to capture speech
output during system tests.
Note: The name of this module must match the name of the synth driver, and the configured synthesizer
in the `tests/system/nvdaSettingsFiles/*.ini` files.
"""

import synthDriverHandler
import extensionPoints
import speech

# inform those who want to know that there is new speech
post_speech = extensionPoints.Action()


class SpeechSpySynthDriver(synthDriverHandler.SynthDriver):
    """A synth driver configured during system tests to capture speech output
	"""
    name = "SpeechSpySynthDriver"  # Name must match configuration files and module.
    description = "System test speech spy"

    @classmethod
    def check(cls):
        return True

    supportedSettings = []
    supportedNotifications = {
        synthDriverHandler.synthIndexReached,
Beispiel #12
0
# SPL Studio Actions
# An app module and global plugin package for NVDA
# Copyright 2017-2018 Joseph Lee and others, released under GPL.
# Defines various actions to be carried out by various add-on modules, powered by extension points.
# This module provides services for other modules, not the other way around.
# Thus, importing other add-on modules should not be attempted unless granted.

# An action is a notification about something that has happened or about to happen.
# In SPL add-on, an action is prefixed by SPLAction*.

import sys
py3 = sys.version.startswith("3")

# Do not unlock the full power of action extension point until 2018.
import extensionPoints

# 40 (17.12): unconditionally define actions, but not until 2018.
# Studio handle found, app module is fully ready.
SPLActionAppReady = extensionPoints.Action()
# Add-on settings were loaded.
SPLActionSettingsLoaded = extensionPoints.Action()
# Switching broadcast profiles.
SPLActionProfileSwitched = extensionPoints.Action()
# Settings are being saved.
SPLActionSettingsSaved = extensionPoints.Action()
# Studio is terminating.
SPLActionAppTerminating = extensionPoints.Action()
Beispiel #13
0
# -*- coding: UTF-8 -*-
# power status notiffications: This add-on plays a tone when the power status changes.
# Copyright (C) 2019 David CM
# Author: David CM <*****@*****.**>
# Released under GPL 2
#globalPlugins/powerStatusNotiffications.py

import extensionPoints, globalPluginHandler, tones, windowUtils, winKernel, addonHandler

post_windowMessageReceipt = extensionPoints.Action()


class MessageWindow(windowUtils.CustomWindow):
    className = u"PowerStatusNotiffications"
    WM_POWERBROADCAST = 0x218
    PBT_APMPOWERSTATUSCHANGE = 0xA
    UNKNOWN_BATTERY_STATUS = 0xFF
    AC_ONLINE = 0X1
    NO_SYSTEM_BATTERY = 0X80

    def __init__(self, windowName=None):
        super(MessageWindow, self).__init__(windowName)
        self.oldBatteryStatus = None
        self.handlePowerStatusChange()

    def windowProc(self, hwnd, msg, wParam, lParam):
        post_windowMessageReceipt.notify(msg=msg, wParam=wParam, lParam=lParam)
        if msg == self.WM_POWERBROADCAST and wParam == self.PBT_APMPOWERSTATUSCHANGE:
            self.handlePowerStatusChange()

    def handlePowerStatusChange(self):