Sound should now stop when speech stops. This means no more interrupting speech just to have the link sounds on a page continue to play.
This commit is contained in:
@@ -128,6 +128,10 @@ class Player:
|
||||
def stop(self, _element: Any = None) -> None:
|
||||
"""Stops current sound playback."""
|
||||
|
||||
with self._workerLock:
|
||||
if self._workerProcess is None or self._workerProcess.poll() is not None:
|
||||
return
|
||||
|
||||
self._sendWorkerCommand({"action": "stop"}, waitForResponse=False)
|
||||
|
||||
def shutdown(self) -> None:
|
||||
|
||||
@@ -694,6 +694,8 @@ def stop() -> None:
|
||||
_speechserver.stop() # type: ignore
|
||||
if _echoSpeechserver and _echoSpeechserver != _speechserver:
|
||||
_echoSpeechserver.stop() # type: ignore
|
||||
player = sound.getPlayer()
|
||||
player.stop()
|
||||
|
||||
def shutdown() -> None:
|
||||
debug.printMessage(debug.LEVEL_INFO, 'SPEECH: Shutting down', True)
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
import sys
|
||||
import unittest
|
||||
from pathlib import Path
|
||||
from unittest import mock
|
||||
|
||||
sys.path.insert(0, str(Path(__file__).resolve().parents[1] / "src"))
|
||||
|
||||
from cthulhu import speech
|
||||
|
||||
|
||||
class PresentationInterruptSoundRegressionTests(unittest.TestCase):
|
||||
def test_speech_stop_also_stops_sound_playback(self):
|
||||
speechServer = mock.Mock()
|
||||
echoServer = mock.Mock()
|
||||
soundPlayer = mock.Mock()
|
||||
|
||||
with (
|
||||
mock.patch.object(speech, "_speechserver", speechServer),
|
||||
mock.patch.object(speech, "_echoSpeechserver", echoServer),
|
||||
mock.patch.object(speech.sound, "getPlayer", return_value=soundPlayer),
|
||||
):
|
||||
speech.stop()
|
||||
|
||||
speechServer.stop.assert_called_once_with()
|
||||
echoServer.stop.assert_called_once_with()
|
||||
soundPlayer.stop.assert_called_once_with()
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
unittest.main()
|
||||
@@ -38,8 +38,11 @@ from cthulhu import sound_sink
|
||||
|
||||
|
||||
class _FakeProcess:
|
||||
def __init__(self, returnCode=None):
|
||||
self.returnCode = returnCode
|
||||
|
||||
def poll(self):
|
||||
return None
|
||||
return self.returnCode
|
||||
|
||||
|
||||
class SoundSinkTests(unittest.TestCase):
|
||||
@@ -107,6 +110,23 @@ class PlayerRecoveryTests(unittest.TestCase):
|
||||
self.assertEqual(stopReasons, ["lost audio sink"])
|
||||
self.assertEqual(startedSinks, [settings.SOUND_SINK_AUTO])
|
||||
|
||||
def test_stop_does_not_start_worker_when_worker_is_not_running(self):
|
||||
player = sound.Player()
|
||||
|
||||
with mock.patch.object(player, "_sendWorkerCommand") as sendCommand:
|
||||
player.stop()
|
||||
|
||||
sendCommand.assert_not_called()
|
||||
|
||||
def test_stop_sends_command_to_running_worker(self):
|
||||
player = sound.Player()
|
||||
player._workerProcess = _FakeProcess()
|
||||
|
||||
with mock.patch.object(player, "_sendWorkerCommand") as sendCommand:
|
||||
player.stop()
|
||||
|
||||
sendCommand.assert_called_once_with({"action": "stop"}, waitForResponse=False)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
unittest.main()
|
||||
|
||||
Reference in New Issue
Block a user