From 63d2a42c5e1a664dab838b427a672d9959f179e4 Mon Sep 17 00:00:00 2001 From: NovusTheory Date: Wed, 9 May 2018 11:15:17 -0500 Subject: [PATCH] ConnectAsync(bool external) API implemented This allows developers to handle the AudioClient externally (for example with Lavalink) --- .../Entities/Channels/IAudioChannel.cs | 5 +- .../Entities/Channels/RestGroupChannel.cs | 1 + .../Entities/Channels/RestVoiceChannel.cs | 3 +- .../Entities/Channels/SocketGroupChannel.cs | 1 + .../Entities/Channels/SocketVoiceChannel.cs | 9 +++- .../Entities/Guilds/SocketGuild.cs | 50 +++++++++++-------- 6 files changed, 44 insertions(+), 25 deletions(-) diff --git a/src/Discord.Net.Core/Entities/Channels/IAudioChannel.cs b/src/Discord.Net.Core/Entities/Channels/IAudioChannel.cs index afb81d92f..68f222020 100644 --- a/src/Discord.Net.Core/Entities/Channels/IAudioChannel.cs +++ b/src/Discord.Net.Core/Entities/Channels/IAudioChannel.cs @@ -1,4 +1,4 @@ -using Discord.Audio; +using Discord.Audio; using System; using System.Threading.Tasks; @@ -8,5 +8,8 @@ namespace Discord { /// Connects to this audio channel. Task ConnectAsync(Action configAction = null); + + /// Connects to this audio channel but can specify if client is handled externally. + Task ConnectAsync(bool external, Action configAction = null); } } diff --git a/src/Discord.Net.Rest/Entities/Channels/RestGroupChannel.cs b/src/Discord.Net.Rest/Entities/Channels/RestGroupChannel.cs index a1868573e..863b2ca58 100644 --- a/src/Discord.Net.Rest/Entities/Channels/RestGroupChannel.cs +++ b/src/Discord.Net.Rest/Entities/Channels/RestGroupChannel.cs @@ -144,6 +144,7 @@ namespace Discord.Rest //IAudioChannel Task IAudioChannel.ConnectAsync(Action configAction) { throw new NotSupportedException(); } + Task IAudioChannel.ConnectAsync(bool external, Action configAction) { throw new NotSupportedException(); } //IChannel Task IChannel.GetUserAsync(ulong id, CacheMode mode, RequestOptions options) diff --git a/src/Discord.Net.Rest/Entities/Channels/RestVoiceChannel.cs b/src/Discord.Net.Rest/Entities/Channels/RestVoiceChannel.cs index 300ebd08d..26d62c02e 100644 --- a/src/Discord.Net.Rest/Entities/Channels/RestVoiceChannel.cs +++ b/src/Discord.Net.Rest/Entities/Channels/RestVoiceChannel.cs @@ -1,4 +1,4 @@ -using Discord.Audio; +using Discord.Audio; using System; using System.Collections.Generic; using System.Diagnostics; @@ -42,6 +42,7 @@ namespace Discord.Rest //IAudioChannel Task IAudioChannel.ConnectAsync(Action configAction) { throw new NotSupportedException(); } + Task IAudioChannel.ConnectAsync(bool external, Action configAction) { throw new NotSupportedException(); } //IGuildChannel Task IGuildChannel.GetUserAsync(ulong id, CacheMode mode, RequestOptions options) diff --git a/src/Discord.Net.WebSocket/Entities/Channels/SocketGroupChannel.cs b/src/Discord.Net.WebSocket/Entities/Channels/SocketGroupChannel.cs index d46c5fc59..671d2ea67 100644 --- a/src/Discord.Net.WebSocket/Entities/Channels/SocketGroupChannel.cs +++ b/src/Discord.Net.WebSocket/Entities/Channels/SocketGroupChannel.cs @@ -207,6 +207,7 @@ namespace Discord.WebSocket //IAudioChannel Task IAudioChannel.ConnectAsync(Action configAction) { throw new NotSupportedException(); } + Task IAudioChannel.ConnectAsync(bool external, Action configAction) { throw new NotSupportedException(); } //IChannel Task IChannel.GetUserAsync(ulong id, CacheMode mode, RequestOptions options) diff --git a/src/Discord.Net.WebSocket/Entities/Channels/SocketVoiceChannel.cs b/src/Discord.Net.WebSocket/Entities/Channels/SocketVoiceChannel.cs index e8a669845..2227c3155 100644 --- a/src/Discord.Net.WebSocket/Entities/Channels/SocketVoiceChannel.cs +++ b/src/Discord.Net.WebSocket/Entities/Channels/SocketVoiceChannel.cs @@ -1,4 +1,4 @@ -using Discord.Audio; +using Discord.Audio; using Discord.Rest; using System; using System.Collections.Generic; @@ -42,7 +42,12 @@ namespace Discord.WebSocket public async Task ConnectAsync(Action configAction = null) { - return await Guild.ConnectAudioAsync(Id, false, false, configAction).ConfigureAwait(false); + return await Guild.ConnectAudioAsync(Id, false, false, configAction, false).ConfigureAwait(false); + } + + public async Task ConnectAsync(bool external, Action configAction = null) + { + return await Guild.ConnectAudioAsync(Id, false, false, configAction, external).ConfigureAwait(false); } public override SocketGuildUser GetUser(ulong id) diff --git a/src/Discord.Net.WebSocket/Entities/Guilds/SocketGuild.cs b/src/Discord.Net.WebSocket/Entities/Guilds/SocketGuild.cs index 3dbd1160c..b92f6c58b 100644 --- a/src/Discord.Net.WebSocket/Entities/Guilds/SocketGuild.cs +++ b/src/Discord.Net.WebSocket/Entities/Guilds/SocketGuild.cs @@ -504,7 +504,7 @@ namespace Discord.WebSocket { return _audioClient?.GetInputStream(userId); } - internal async Task ConnectAudioAsync(ulong channelId, bool selfDeaf, bool selfMute, Action configAction) + internal async Task ConnectAudioAsync(ulong channelId, bool selfDeaf, bool selfMute, Action configAction, bool external) { selfDeaf = false; selfMute = false; @@ -518,29 +518,37 @@ namespace Discord.WebSocket promise = new TaskCompletionSource(); _audioConnectPromise = promise; - if (_audioClient == null) + if (!external) { - var audioClient = new AudioClient(this, Discord.GetAudioId(), channelId); - audioClient.Disconnected += async ex => + if (_audioClient == null) { - if (!promise.Task.IsCompleted) + var audioClient = new AudioClient(this, Discord.GetAudioId(), channelId); + audioClient.Disconnected += async ex => { - try { audioClient.Dispose(); } catch { } - _audioClient = null; - if (ex != null) - await promise.TrySetExceptionAsync(ex); - else - await promise.TrySetCanceledAsync(); - return; - } - }; - audioClient.Connected += () => - { - var _ = promise.TrySetResultAsync(_audioClient); - return Task.Delay(0); - }; - configAction?.Invoke(audioClient); - _audioClient = audioClient; + if (!promise.Task.IsCompleted) + { + try + { audioClient.Dispose(); } + catch { } + _audioClient = null; + if (ex != null) + await promise.TrySetExceptionAsync(ex); + else + await promise.TrySetCanceledAsync(); + return; + } + }; + audioClient.Connected += () => + { + var _ = promise.TrySetResultAsync(_audioClient); + return Task.Delay(0); + }; + configAction?.Invoke(audioClient); + _audioClient = audioClient; + } + } else + { + var _ = promise.TrySetResultAsync(null); } await Discord.ApiClient.SendVoiceStateUpdateAsync(Id, channelId, selfDeaf, selfMute).ConfigureAwait(false);