mirror of
https://github.com/MCV-Software/TWBlue.git
synced 2025-08-26 01:49:22 +00:00
Putting all the code from the current master branch of TWBlue
This commit is contained in:
88
src/accessible_output2/outputs/sapi5.py
Normal file
88
src/accessible_output2/outputs/sapi5.py
Normal file
@@ -0,0 +1,88 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
import config
|
||||
from collections import OrderedDict
|
||||
from libloader.com import load_com
|
||||
from base import Output, OutputError
|
||||
import pywintypes
|
||||
import logging
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
class SAPI5(Output):
|
||||
has_volume = True
|
||||
has_rate = True
|
||||
has_pitch = True
|
||||
min_pitch = -10
|
||||
max_pitch = 10
|
||||
min_rate = -10
|
||||
max_rate = 10
|
||||
min_volume = 0
|
||||
max_volume = 100
|
||||
name = "sapi5"
|
||||
priority = 101
|
||||
|
||||
def __init__(self):
|
||||
if config.main["general"]["voice_enabled"] == False: raise OutputError
|
||||
try:
|
||||
self.object = load_com("SAPI.SPVoice")
|
||||
self._voices = self._available_voices()
|
||||
except pywintypes.com_error:
|
||||
raise OutputError
|
||||
self._pitch = 0
|
||||
|
||||
def _available_voices(self):
|
||||
_voices = OrderedDict()
|
||||
for v in self.object.GetVoices():
|
||||
_voices[v.GetDescription()] = v
|
||||
return _voices
|
||||
|
||||
def list_voices(self):
|
||||
return self.available_voices.keys()
|
||||
|
||||
def get_voice(self):
|
||||
return self.object.Voice.GetDescription()
|
||||
|
||||
def set_voice(self, value):
|
||||
log.debug("Setting SAPI5 voice to \"%s\"" % value)
|
||||
self.object.Voice = self.available_voices[value]
|
||||
# For some reason SAPI5 does not reset audio after changing the voice
|
||||
# By setting the audio device after changing voices seems to fix this
|
||||
# This was noted from information at:
|
||||
# http://lists.nvaccess.org/pipermail/nvda-dev/2011-November/022464.html
|
||||
self.object.AudioOutput = self.object.AudioOutput
|
||||
|
||||
def get_pitch(self):
|
||||
return self._pitch
|
||||
|
||||
def set_pitch(self, value):
|
||||
log.debug("Setting pitch to %d" % value)
|
||||
self._pitch = value
|
||||
|
||||
def get_rate(self):
|
||||
return self.object.Rate
|
||||
|
||||
def set_rate(self, value):
|
||||
log.debug("Setting rate to %d" % value)
|
||||
self.object.Rate = value
|
||||
|
||||
def get_volume(self):
|
||||
return self.object.Volume
|
||||
|
||||
def set_volume(self, value):
|
||||
self.object.Volume = value
|
||||
|
||||
def speak(self, text, interrupt=False):
|
||||
if interrupt:
|
||||
self.silence()
|
||||
# We need to do the pitch in XML here
|
||||
textOutput = "<pitch absmiddle=\"%d\">%s</pitch>" % (round(self._pitch), text.replace("<", "<"))
|
||||
self.object.Speak(textOutput, 1|8)
|
||||
|
||||
def silence(self):
|
||||
self.object.Speak("", 3)
|
||||
|
||||
def is_active(self):
|
||||
if self.object:
|
||||
return True
|
||||
return False
|
||||
|
||||
output_class = SAPI5
|
Reference in New Issue
Block a user