示例#1
0
        public async Task DrawAsync(EduardoContext context, string emojiOrUrl, int size)
        {
            string url;

            if (Emote.TryParse(emojiOrUrl, out Emote emote))
            {
                url = emote.Url;
            }
            else if (Uri.TryCreate(emojiOrUrl, UriKind.Absolute, out Uri result))
            {
                url = result.AbsoluteUri;
            }
            else
            {
                await context.Channel.SendMessageAsync("Please enter a valid emote!");

                return;
            }

            string     previousName = context.Client.CurrentUser.Username;
            IGuildUser user         = await((IGuild)context.Guild).GetUserAsync(context.Client.CurrentUser.Id);
            await user.ModifyAsync(usr => usr.Nickname = "----");

            List <string> blocks = await GetBlocksAsync(url, size);

            foreach (string block in blocks)
            {
                await context.Channel.SendMessageAsync(block);
            }

            await user.ModifyAsync(usr => usr.Nickname = previousName);
        }
示例#2
0
        private async Task OnMessageReceviedAsync(SocketMessage sm)
        {
            if (!(sm is SocketUserMessage msg))
            {
                return;
            }

            EduardoContext context = new EduardoContext(_client, msg, serviceProvider);

            int argPos = 0;

            if (msg.HasStringPrefix(Constants.CMD_PREFIX, ref argPos) || msg.HasMentionPrefix(_client.CurrentUser, ref argPos))
            {
                IResult result = await _commandService.ExecuteAsync(context, argPos, serviceProvider);

                if (!result.IsSuccess && result.Error != CommandError.UnknownCommand)
                {
                    if (result.Error == CommandError.BadArgCount)
                    {
                        await context.Channel.SendMessageAsync(Format.Bold($"Incorrect command usage. Use `{Constants.CMD_PREFIX}help <command>` to show usage"));
                    }
                    else
                    {
                        Console.WriteLine(result.ErrorReason);
                        await context.Channel.SendMessageAsync("Something went wrong while executing that command...");
                    }
                }
            }
        }
示例#3
0
        public async Task StartQueue(EduardoContext context)
        {
            queueCts = new CancellationTokenSource();
            List <SongInfo> guildQueue = GetGuildQueue(context.Guild.Id);

            if (guildQueue.Count == 0)
            {
                await context.Channel.SendMessageAsync($"There are no songs in the queue! Use `{Constants.CMD_PREFIX}queue add <song>` to add items to the queue");

                return;
            }

            await JoinAudio(context);

            if (_connectedChannels.TryGetValue(context.Guild.Id, out IAudioClient client))
            {
                using AudioOutStream stream = client.CreatePCMStream(AudioApplication.Music, bufferMillis: 1);

                while (guildQueue.Count > 0 && !queueCts.IsCancellationRequested)
                {
                    await SendAudioAsync(context, guildQueue.First(), stream);
                }
            }

            await LeaveAudio(context.Guild);
        }
示例#4
0
        private async Task JoinAudio(EduardoContext context)
        {
            // Get connected voice channel of requesting user
            IVoiceChannel target = (context.User as IVoiceState)?.VoiceChannel;

            // Don't join audio if not correct guild.
            if (target?.Guild.Id != context.Guild.Id)
            {
                return;
            }

            // Leave current audio channel on guild (if any)
            if (_connectedChannels.ContainsKey(context.Guild.Id))
            {
                await LeaveAudio(context.Guild);
            }

            // Connect to new audio channel
            IAudioClient audioClient = await target.ConnectAsync();

            // Register connection in connected channels
            if (_connectedChannels.TryAdd(context.Guild.Id, audioClient))
            {
                await Logger.Log($"Connected to voice channel on {context.Guild.Name}", LogSeverity.Info);
            }
            else
            {
                await Logger.Log($"Failed to join voice channel on {context.Guild.Name}", LogSeverity.Error);
            }
        }
示例#5
0
        private async Task SendAudioAsync(EduardoContext context, SongInfo song, AudioOutStream discordStream)
        {
            audioCts = new CancellationTokenSource();

            await ShowCurrentSong(context);

            await Logger.Log($"Starting playback of {song.Name} in {context.Guild.Name}", LogSeverity.Debug);

            SongBuffer songBuffer = null;

            try
            {
                songBuffer = new SongBuffer(song.StreamUrl);
                songBuffer.StartBuffering(audioCts.Token);

                RestUserMessage message = await context.Channel.SendMessageAsync("Video is buffering, please wait a moment...");

                await songBuffer.PrebufferingCompleted.Task;

                await message.DeleteAsync();

                //await Task.WhenAny(Task.Delay(10000), songBuffer.PrebufferingCompleted.Task);

                if (audioCts.IsCancellationRequested)
                {
                    return;
                }

                int bytesSent = 0;

                while (true)
                {
                    byte[] buffer = songBuffer.Read(FrameBytes).ToArray();

                    if (buffer.Length == 0)
                    {
                        break;
                    }

                    AdjustVolume(buffer, volume);

                    await discordStream.WriteAsync(buffer, 0, buffer.Length, audioCts.Token);

                    bytesSent += buffer.Length;

                    song.CurrentTime = TimeSpan.FromSeconds(bytesSent / (float)FrameBytes / (1000 / Milliseconds));

                    await(pauseTaskSource?.Task ?? Task.CompletedTask);
                }
            }
            catch (Exception ex) when(!(ex is OperationCanceledException cancelledException) || cancelledException.CancellationToken.IsCancellationRequested)
            {
            }
            finally
            {
                await discordStream.FlushAsync();

                songBuffer?.Dispose();
            }
        }
示例#6
0
        public async Task GetAlbumAsync(EduardoContext context, string searchAlbum)
        {
            SearchItem searchItem = await GetAsync(() => _spotify.SearchItemsAsync(searchAlbum, SearchType.Album));

            if (searchItem.Albums.Total == 0)
            {
                await context.Channel.SendMessageAsync($"No albums found from search term \"{searchAlbum}\"");
            }

            List <Embed> embeds = new List <Embed>();

            foreach (SimpleAlbum album in searchItem.Albums.Items)
            {
                embeds.Add(new EmbedBuilder()
                           .WithTitle(album.Name)
                           .WithColor(Color.DarkGreen)
                           .WithUrl(album.ExternalUrls["spotify"])
                           .WithImageUrl(album.Images.Count > 0 ? album.Images[0].Url : "")
                           .AddField("Album Type", album.AlbumType)
                           .AddField("Released", album.ReleaseDate)
                           .Build());
            }

            await context.SendMessageOrPaginatedAsync(embeds);
        }
示例#7
0
        public async Task DisplayUserInfo(EduardoContext context, IGuildUser user = null)
        {
            SocketGuildUser guildUser = user != null?user.AsSocketGuildUser() : context.User.AsSocketGuildUser();

            string userInfo = $"Created: {guildUser.CreatedAt:dddd MMM d}{DateTime.Now.Day.GetDaySuffix()} {guildUser.CreatedAt:yyyy} at {guildUser.CreatedAt:h:m tt}\n" +
                              $"Status: {guildUser.Status}\n" +
                              $"Game: {guildUser.Activity?.Name ?? "N/A"}\n";

            string memberInfo = $"Joined: {guildUser.JoinedAt:dddd MMM d}{DateTime.Now.Day.GetDaySuffix()} {guildUser.JoinedAt:yyyy} at {guildUser.JoinedAt:h:m tt}\n" +
                                $"Nickname: {guildUser.Nickname ?? "N/A"}\n";

            string roleInfo = string.Join(", ", guildUser.Roles.Where(x => !x.IsEveryone));

            EmbedBuilder builder = new EmbedBuilder()
                                   .WithColor(Color.Orange)
                                   .WithAuthor($"Summary for {guildUser.Username}#{guildUser.Discriminator} ({guildUser.Id})",
                                               guildUser.GetAvatarUrl())
                                   .WithThumbnailUrl(guildUser.GetAvatarUrl())
                                   .AddField("User Info", userInfo)
                                   .AddField("Member Info", memberInfo)
                                   .AddConditionalField("Roles", roleInfo, !string.IsNullOrWhiteSpace(roleInfo))
                                   .WithFooter($"Eduardo | {string.Format("{0:dddd MMM d}{1} {0:yyyy} at {0:h:m tt}", DateTime.Now, DateTime.Now.Day.GetDaySuffix())}",
                                               context.User.AsSocketGuildUser().GetAvatarUrl());

            await context.Channel.SendMessageAsync(embed : builder.Build());
        }
示例#8
0
        public async Task GetSongAsync(EduardoContext context, string searchSong)
        {
            SearchItem searchItem = await GetAsync(() => _spotify.SearchItemsAsync(searchSong, SearchType.Track));

            if (searchItem.Tracks.Total == 0)
            {
                await context.Channel.SendMessageAsync($"No songs found from search term \"{searchSong}\"");
            }

            List <Embed> embeds = new List <Embed>();

            foreach (FullTrack track in searchItem.Tracks.Items)
            {
                embeds.Add(new EmbedBuilder()
                           .WithTitle(track.Name)
                           .WithColor(Color.DarkGreen)
                           .WithUrl(track.ExternUrls["spotify"])
                           .WithImageUrl(track.Album.Images.Count > 0 ? track.Album.Images[0].Url : "")
                           .AddField("Duration", TimeSpan.FromMilliseconds(track.DurationMs).ToString(@"mm\:ss"))
                           .AddField("Album", $"{track.Album.Name} - {track.Album.AlbumType}")
                           .AddField("Released", track.Album.ReleaseDate)
                           .AddField("Explcit", track.Explicit ? "Yes": "No")
                           .Build());
            }

            await context.SendMessageOrPaginatedAsync(embeds);
        }
        public static async Task SendMessageOrPaginatedAsync(this EduardoContext context, List <Embed> embeds)
        {
            PaginatedMessage paginatedMsg = PaginatedMessage.Default;

            paginatedMsg.Embeds = embeds;
            await SendMessageOrPaginatedAsync(context, paginatedMsg);
        }
示例#10
0
        public async Task ViewPlaylistAsync(EduardoContext context, string playlistName)
        {
            if (string.IsNullOrWhiteSpace(playlistName))
            {
                return;
            }

            Models.Playlist playlist = await _playlistRepository.GetPlaylistAsync((long)context.User.Id, playlistName);

            if (playlist == null)
            {
                await context.Channel.SendMessageAsync($"No playlist found with name \"{playlistName}\"");

                return;
            }

            EmbedBuilder playlistBuilder = new EmbedBuilder()
                                           .WithColor(Color.DarkRed)
                                           .WithTitle(playlist.Name)
                                           .WithCurrentTimestamp();

            if (playlist.Songs.Count > 0)
            {
                playlistBuilder = playlistBuilder
                                  .WithFieldsForList(playlist.Songs, x => x.Name, x => x.Url);
            }
            else
            {
                playlistBuilder = playlistBuilder
                                  .WithDescription($"This playlist doesn't contain any songs. Use ```{Constants.CMD_PREFIX}playlist add <playlist name> <song or url>``` to add a song");
            }

            await context.Channel.SendMessageAsync(embed : playlistBuilder.Build());
        }
示例#11
0
        public async Task DisplayEightBall(EduardoContext context, string question = null)
        {
            await context.Channel.TriggerTypingAsync();

            string answer = _eightBallData.Words[_prng.Next(0, _eightBallData.Words.Count)];
            await context.Channel.SendMessageAsync($"{question} -- {answer}");
        }
示例#12
0
 public void AddCommands(EduardoContext context, ModuleInfo module, ref EmbedBuilder builder)
 {
     foreach (CommandInfo command in module.Commands)
     {
         command.CheckPreconditionsAsync(context, context.Provider).GetAwaiter().GetResult();
         AddCommand(command, ref builder);
     }
 }
示例#13
0
        public async Task GetMatches(EduardoContext context, string username, PubgPlatform platform)
        {
            PubgPlayer player = await GetPlayerFromApiAsync(username, platform);

            if (player == null)
            {
                await context.Channel.SendMessageAsync($"No player found with username \"{username}\"");

                return;
            }

            List <Embed> embeds = new List <Embed>();

            foreach (string matchId in player.MatchIds.Take(_pubgData.MaxMatches))
            {
                PubgMatch match = await GetMatchFromApiAsync(matchId, platform);

                TimeSpan        matchDuration = TimeSpan.FromSeconds(match.Duration);
                PubgRoster      roster        = match.Rosters.FirstOrDefault(r => r.Participants.Any(p => p.Stats.PlayerId == player.Id));
                PubgParticipant participant   = match.Rosters.SelectMany(r => r.Participants).FirstOrDefault(p => p.Stats.PlayerId == player.Id);
                TimeSpan        timeSurvived  = TimeSpan.FromSeconds(participant?.Stats.TimeSurvived ?? 0);

                embeds.Add(new EmbedBuilder()
                           .WithTitle(match.GameMode.ToString())
                           .WithColor(Color.Orange)
                           .AddField("Started", DateTime.Parse(match.CreatedAt), true)
                           .AddField("Duration", $"{matchDuration.Minutes:D2}m {matchDuration.Seconds:D2}s", true)
                           .AddField("Player Count", match.Rosters.Count(), true)
                           .AddField("Placement", roster != null
                        ? $"#{roster.Stats.Rank}"
                        : "Unknown", true)
                           .AddConditionalField("Death Reason", participant?.Stats.DeathType.ToString() ?? "Unknown",
                                                participant != null && participant.Stats.DeathType == PubgParticipantDeathType.Alive, true)
                           .AddField("Kills", participant?.Stats.Kills.ToString() ?? "Unknown", true)
                           .AddField("Damage Dealt", participant != null
                        ? Math.Round(participant.Stats.DamageDealt, 2).ToString(CultureInfo.InvariantCulture)
                        : "Unknown", true)
                           .AddField("Headshot %", participant != null
                        ? participant.Stats.Kills > 0
                            ? (participant.Stats.HeadshotKills / participant.Stats.Kills * 100).ToString()
                            : "0%"
                        : "Unknown", true)
                           .AddField("Time Survived", participant != null
                        ? $"{timeSurvived.Minutes:D2}m {timeSurvived.Seconds:D2}s"
                        : "Unknown", true)
                           .AddField("Distance Travelled", participant != null
                        ? Math.Round(participant.Stats.RideDistance + participant.Stats.WalkDistance, 2).ToString(CultureInfo.InvariantCulture)
                        : "Unknown", true)
                           .AddField("DBNOs", participant?.Stats.DBNOs.ToString() ?? "Unknown", true)
                           .AddField("Heals Used", participant?.Stats.Heals.ToString() ?? "Unknown", true)
                           .AddField("Boosts Used", participant?.Stats.Boosts.ToString() ?? "Unknown", true)
                           .WithFooter($"Match Data for {participant?.Stats.Name ?? "Unknown"} for match {matchId}",
                                       "https://steemit-production-imageproxy-thumbnail.s3.amazonaws.com/U5dt5ZoFC4oMbrTPSSvVHVfyGSakHWV_1680x8400")
                           .Build());
            }

            await context.SendMessageOrPaginatedAsync(embeds);
        }
示例#14
0
        public async Task ShowMoney(EduardoContext context, IGuildUser user)
        {
            (string username, long userId) = user == null ?
                                             (context.User.Username, (long)context.User.Id) :
                                             (user.Username, (long)user.Id);

            int money = await _moneyRepository.GetMoneyAsync(userId, (long)context.Guild.Id);

            await context.Channel.SendMessageAsync($"{Format.Bold(username)} has ${money}");
        }
示例#15
0
        public async Task Skip(EduardoContext context)
        {
            if (GetGuildQueue(context.Guild.Id).Any())
            {
                IUserMessage skipMessage = await context.Channel.SendMessageAsync("Skipping song...");

                audioCts?.Cancel();
                await skipMessage.DeleteAsync();
            }
        }
示例#16
0
        public async Task SetVolume(EduardoContext context, int newVolume)
        {
            if (newVolume < 0 || newVolume > 100)
            {
                await context.Channel.SendMessageAsync("Volume must be between 0 and 100");

                return;
            }

            volume = (float)newVolume / 100;
        }
 public static async Task SendMessageOrPaginatedAsync(this EduardoContext context, PaginatedMessage paginatedMsg)
 {
     if (paginatedMsg.Embeds.Count == 1)
     {
         await context.Channel.SendMessageAsync(embed : paginatedMsg.Embeds[0]);
     }
     else
     {
         await context.SendPaginatedMessageAsync(paginatedMsg);
     }
 }
示例#18
0
 public async Task GetAvatar(EduardoContext context, IUser targetUser = null)
 {
     if (targetUser == null)
     {
         await context.Channel.SendMessageAsync(context.User.GetAvatarUrl());
     }
     else
     {
         await context.Channel.SendMessageAsync(targetUser.GetAvatarUrl());
     }
 }
示例#19
0
        public async Task ShowCurrentSong(EduardoContext context)
        {
            List <SongInfo> guildQueue = GetGuildQueue(context.Guild.Id);

            if (guildQueue.Any() && !(audioCts.IsCancellationRequested || queueCts.IsCancellationRequested))
            {
                await context.Channel.SendMessageAsync("Currently playing:", false, BuildSongEmbed(guildQueue.First()));
            }
            else
            {
                await context.Channel.SendMessageAsync("There is no song playing");
            }
        }
示例#20
0
        public async Task Unshorten(EduardoContext context, string url)
        {
            if (!url.Contains("goo.gl"))
            {
                await context.Channel.SendMessageAsync($"**{context.User.Username}, This Url is not shortened**");

                return;
            }

            string unshortened = await ShortenHelper.UnshortenUrlAsync(_credentials.GoogleShortenerApiKey, url);

            await context.Channel.SendMessageAsync($"**{context.User.Mention}, your unshortened url is: \"{unshortened}\"**");
        }
示例#21
0
        public async Task KickUser(EduardoContext context, IGuildUser kickUser, string reason)
        {
            try
            {
                await kickUser.SendMessageAsync($"You were kicked from {Format.Bold(context.Guild.Name)} with reason: {Format.Bold(reason)}");
            } catch (HttpException ex) when(ex.DiscordCode == 50007)
            {
                // ignored
            }

            await kickUser.KickAsync(reason);

            await context.Channel.SendMessageAsync($"{Format.Bold(context.User.Mention)} has kicked {kickUser.Mention}: \"{Format.Bold(reason)}\"");
        }
示例#22
0
        public async Task BanUser(EduardoContext context, IGuildUser banUser, string reason)
        {
            try
            {
                await banUser.SendMessageAsync($"You were banned from {Format.Bold(context.Guild.Name)} with reason: {Format.Bold(reason)}");
            } catch (HttpException ex) when(ex.DiscordCode == 50007)  // https://discordapp.com/developers/docs/topics/opcodes-and-status-codes
            {
                // ignored
            }

            await context.Guild.AddBanAsync(banUser, 0, reason);

            await context.Channel.SendMessageAsync($"{Format.Bold(context.User.Mention)} has banned {banUser.Mention}: \"{Format.Bold(reason)}\"");
        }
示例#23
0
        public async Task AddSongToQueue(EduardoContext context, string input)
        {
            SongInfo requestedSong = await GetVideoInfo(context, input);

            if (requestedSong != null)
            {
                GetGuildQueue(context.Guild.Id).Add(requestedSong);
                await context.Channel.SendMessageAsync($"Added {Format.Bold(requestedSong.Name)} to the queue");
            }
            else
            {
                await context.Channel.SendMessageAsync($"Could not find video like \"{input}\"");
            }
        }
示例#24
0
        public async Task CreatePlaylistAsync(EduardoContext context, string playlistName)
        {
            if (string.IsNullOrWhiteSpace(playlistName))
            {
                return;
            }

            CreatePlaylistResult result = await _playlistRepository.CreatePlaylistAsync((long)context.User.Id, playlistName);

            await context.Channel.SendMessageAsync(result switch
            {
                CreatePlaylistResult.PlaylistExists => "You have already created a playlist with this name",
                CreatePlaylistResult.MaxPlaylistsReached => "You have reached the maximum number of playlists (5)",
                _ => $"Playlist \"{playlistName}\" created successfully!"
            });
示例#25
0
        public async Task ShortenYouTube(EduardoContext context, string url)
        {
            string        videoId          = string.Empty;
            List <string> alreadyShortened = new List <string>
            {
                "youtu.be", "www.youtu.be"
            };

            if (alreadyShortened.Any(url.Contains) && !url.Contains("&feature=youtu.be"))
            {
                await context.Channel.SendMessageAsync($"**{context.User.Username}, This url is already shortened!**");

                return;
            }

            List <string> validAuthorities = new List <string>
            {
                "youtube.com", "www.youtube.com"
            };

            if (validAuthorities.Any(url.Contains))
            {
                Regex regexExtractId = new Regex(Constants.YOUTUBE_LINK_REGEX, RegexOptions.Compiled);
                Uri   uri            = new Uri(url);
                try
                {
                    string authority = new UriBuilder(uri).Uri.Authority.ToLower();
                    if (validAuthorities.Contains(authority))
                    {
                        Match regRes = regexExtractId.Match(uri.ToString());
                        if (regRes.Success)
                        {
                            videoId = regRes.Groups[1].Value;
                        }
                    }

                    await context.Channel.SendMessageAsync($"**{context.User.Mention}, your shortened url is: \"http://youtu.be/{videoId}\"**");
                }
                catch
                {
                    await context.Channel.SendMessageAsync("**Failed to parse url.**");
                }
            }
            else
            {
                await context.Channel.SendMessageAsync($"**{context.User.Username}, This is not a valid YouTube url.");
            }
        }
示例#26
0
        public async Task CleanMessages(EduardoContext context, int count)
        {
            if (count <= 0)
            {
                return;
            }

            IEnumerable <IMessage> messagesToDelete = await context.Channel.GetMessagesAsync(count + 1).FlattenAsync();

            await((ITextChannel)context.Channel).DeleteMessagesAsync(messagesToDelete);
            string          plural          = count > 1 ? "s" : "";
            RestUserMessage finishedMessage = await context.Channel.SendMessageAsync($"Successfully cleared {count} message{plural} :ok_hand:");

            await Task.Delay(3000);

            await finishedMessage.DeleteAsync();
        }
示例#27
0
        public async Task PostDankMeme(EduardoContext context)
        {
            Subreddit subreddit = await _reddit.GetSubredditAsync("dankmemes");

            Listing <Post> postListing = subreddit.GetPosts(Subreddit.Sort.Hot, 100);
            List <Post>    posts       = new List <Post>(100);

            await postListing.ForEachAsync(post =>
            {
                posts.Add(post);
            });

            Post randomPost = posts[_rng.Next(0, posts.Count)];

            using Stream stream = await NetworkHelper.GetStreamAsync(randomPost.Url.AbsoluteUri);

            await context.Channel.SendFileAsync(stream, $"{randomPost.Title}.png");
        }
示例#28
0
        public async Task PlaySong(EduardoContext context, string input)
        {
            SongInfo song = await GetVideoInfo(context, input);

            if (song != null)
            {
                audioCts?.Cancel();
                queueCts?.Cancel();

                GetGuildQueue(context.Guild.Id).Insert(0, song);

                await StartQueue(context);
            }
            else
            {
                await context.Channel.SendMessageAsync($"Could not find video like \"{input}\"");
            }
        }
示例#29
0
        public async Task GetPlaylist(EduardoContext context, string searchPlaylist)
        {
            SearchItem searchItem = await GetAsync(() => _spotify.SearchItemsAsync(searchPlaylist, SearchType.Playlist));

            if (searchItem.Playlists.Total == 0)
            {
                await context.Channel.SendMessageAsync($"No playlists found from search term \"{searchPlaylist}\"");
            }

            List <Embed> embeds = new List <Embed>();

            foreach (SimplePlaylist playlist in searchItem.Playlists.Items)
            {
                embeds.Add(new EmbedBuilder()
                           .Build());
            }

            await context.SendMessageOrPaginatedAsync(embeds);
        }
示例#30
0
        public async Task ViewQueue(EduardoContext context)
        {
            List <SongInfo> guildQueue = GetGuildQueue(context.Guild.Id);

            if (guildQueue.Any())
            {
                string queueInfo = "Queue:";
                for (int queueIndex = 0; queueIndex < guildQueue.Count; queueIndex++)
                {
                    queueInfo += $"\n{queueIndex + 1}. {guildQueue[queueIndex].Name}";
                }

                await context.Channel.SendMessageAsync(queueInfo);
            }
            else
            {
                await context.Channel.SendMessageAsync($"There are no songs in the queue! Use {Format.Bold($"`{Constants.CMD_PREFIX}queue add <song>`")} to add a song to the queue");
            }
        }