Skip to content

Commit 722f23e

Browse files
committed
fix(voice): send speaking packet on reconnect (#862)
`AudioPlayer` would previously not update the [`SPEAKING`](https://discord.com/developers/docs/topics/voice-connections#speaking) state to a non-zero value after reconnecting (which happens when moving between channels, for instance). This results in the bot continuing to send audio packets, which aren't processed by Discord as the speaking state would still be `0`.
1 parent fb1168c commit 722f23e

File tree

3 files changed

+12
-6
lines changed

3 files changed

+12
-6
lines changed

changelog/845.bugfix.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Fix :class:`VoiceClient` not continuing to play audio when moving between channels.

disnake/gateway.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1067,7 +1067,7 @@ def average_latency(self) -> float:
10671067
async def load_secret_key(self, data: VoiceSessionDescriptionPayload) -> None:
10681068
_log.info("received secret key for voice connection")
10691069
self.secret_key = self._connection.secret_key = data["secret_key"]
1070-
await self.speak()
1070+
# need to send this at least once to set the ssrc
10711071
await self.speak(False)
10721072

10731073
async def poll_event(self) -> None:

disnake/player.py

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -690,12 +690,10 @@ def __init__(self, source: AudioSource, client: VoiceClient, *, after=None) -> N
690690
raise TypeError('Expected a callable for the "after" parameter.')
691691

692692
def _do_run(self) -> None:
693-
self.loops = 0
694-
self._start = time.perf_counter()
693+
self._reset_state(speak=True)
695694

696695
# getattr lookup speed ups
697696
play_audio = self.client.send_audio_packet
698-
self._speak(True)
699697

700698
while not self._end.is_set():
701699
# are we paused?
@@ -709,8 +707,7 @@ def _do_run(self) -> None:
709707
# wait until we are connected
710708
self._connected.wait()
711709
# reset our internal data
712-
self.loops = 0
713-
self._start = time.perf_counter()
710+
self._reset_state(speak=self._resumed.is_set())
714711

715712
self.loops += 1
716713
data = self.source.read()
@@ -724,6 +721,14 @@ def _do_run(self) -> None:
724721
delay = max(0, self.DELAY + (next_time - time.perf_counter()))
725722
time.sleep(delay)
726723

724+
# this is called right after (re)connecting;
725+
# reset the timings and set the speaking state accordingly
726+
def _reset_state(self, *, speak: bool) -> None:
727+
self.loops = 0
728+
self._start = time.perf_counter()
729+
if speak:
730+
self._speak(True)
731+
727732
def run(self) -> None:
728733
try:
729734
self._do_run()

0 commit comments

Comments
 (0)