localization complete, or nearly complete if I missed something

This commit is contained in:
Kwoth 2017-02-25 02:04:32 +01:00
parent 466ec12de0
commit 22f961a093
6 changed files with 761 additions and 98 deletions

View File

@ -65,7 +65,6 @@ namespace NadekoBot.Modules.Games
} }
private readonly ITextChannel _channel; private readonly ITextChannel _channel;
private readonly Logger _log;
private readonly IGuildUser[] _users; private readonly IGuildUser[] _users;
private readonly int?[,] _state; private readonly int?[,] _state;
private Phase _phase; private Phase _phase;
@ -90,8 +89,7 @@ namespace NadekoBot.Modules.Games
{ null, null, null }, { null, null, null },
{ null, null, null }, { null, null, null },
}; };
_log = LogManager.GetCurrentClassLogger();
_phase = Phase.Starting; _phase = Phase.Starting;
_moveLock = new SemaphoreSlim(1, 1); _moveLock = new SemaphoreSlim(1, 1);
} }

View File

@ -40,7 +40,7 @@ namespace NadekoBot.Modules.Music.Classes
//pwetty //pwetty
public string PrettyProvider => public string PrettyProvider =>
$"{(SongInfo.Provider ?? "No Provider")}"; $"{(SongInfo.Provider ?? "???")}";
public string PrettyFullTime => PrettyCurrentTime + " / " + PrettyTotalTime; public string PrettyFullTime => PrettyCurrentTime + " / " + PrettyTotalTime;

View File

@ -20,7 +20,7 @@ namespace NadekoBot.Modules.Music
{ {
[NadekoModule("Music", "!!")] [NadekoModule("Music", "!!")]
[DontAutoLoad] [DontAutoLoad]
public partial class Music : NadekoTopLevelModule public class Music : NadekoTopLevelModule
{ {
public static ConcurrentDictionary<ulong, MusicPlayer> MusicPlayers { get; } = new ConcurrentDictionary<ulong, MusicPlayer>(); public static ConcurrentDictionary<ulong, MusicPlayer> MusicPlayers { get; } = new ConcurrentDictionary<ulong, MusicPlayer>();
@ -155,7 +155,14 @@ namespace NadekoBot.Modules.Music
return; return;
var val = musicPlayer.FairPlay = !musicPlayer.FairPlay; var val = musicPlayer.FairPlay = !musicPlayer.FairPlay;
await channel.SendConfirmAsync("Fair play " + (val ? "enabled" : "disabled") + ".").ConfigureAwait(false); if (val)
{
await ReplyConfirmLocalized("fp_enabled").ConfigureAwait(false);
}
else
{
await ReplyConfirmLocalized("fp_disabled").ConfigureAwait(false);
}
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -184,34 +191,31 @@ namespace NadekoBot.Modules.Music
[RequireContext(ContextType.Guild)] [RequireContext(ContextType.Guild)]
public async Task ListQueue(int page = 1) public async Task ListQueue(int page = 1)
{ {
Song currentSong;
MusicPlayer musicPlayer; MusicPlayer musicPlayer;
if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer)) if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer) ||
(currentSong = musicPlayer?.CurrentSong) == null)
{ {
await Context.Channel.SendErrorAsync("🎵 No active music player.").ConfigureAwait(false); await ReplyErrorLocalized("no_music_player").ConfigureAwait(false);
return; return;
} }
if (page <= 0) if (page <= 0)
return; return;
var currentSong = musicPlayer.CurrentSong;
if (currentSong == null)
{
await Context.Channel.SendErrorAsync("🎵 No active music player.").ConfigureAwait(false);
return;
}
try { await musicPlayer.UpdateSongDurationsAsync().ConfigureAwait(false); } catch { } try { await musicPlayer.UpdateSongDurationsAsync().ConfigureAwait(false); } catch { }
const int itemsPerPage = 10; const int itemsPerPage = 10;
var total = musicPlayer.TotalPlaytime; var total = musicPlayer.TotalPlaytime;
var totalStr = total == TimeSpan.MaxValue ? "∞" : $"{(int)total.TotalHours}h {total.Minutes}m {total.Seconds}s"; var totalStr = total == TimeSpan.MaxValue ? "∞" : GetText("time_format",
(int) total.TotalHours,
total.Minutes,
total.Seconds);
var maxPlaytime = musicPlayer.MaxPlaytimeSeconds; var maxPlaytime = musicPlayer.MaxPlaytimeSeconds;
var lastPage = musicPlayer.Playlist.Count / itemsPerPage; var lastPage = musicPlayer.Playlist.Count / itemsPerPage;
Func<int, EmbedBuilder> printAction = (curPage) => Func<int, EmbedBuilder> printAction = curPage =>
{ {
int startAt = itemsPerPage * (curPage - 1); var startAt = itemsPerPage * (curPage - 1);
var number = 0 + startAt; var number = 0 + startAt;
var desc = string.Join("\n", musicPlayer.Playlist var desc = string.Join("\n", musicPlayer.Playlist
.Skip(startAt) .Skip(startAt)
@ -221,19 +225,22 @@ namespace NadekoBot.Modules.Music
desc = $"`🔊` {currentSong.PrettyFullName}\n\n" + desc; desc = $"`🔊` {currentSong.PrettyFullName}\n\n" + desc;
if (musicPlayer.RepeatSong) if (musicPlayer.RepeatSong)
desc = "🔂 Repeating Current Song\n\n" + desc; desc = "🔂 " + GetText("repeating_cur_song") +"\n\n" + desc;
else if (musicPlayer.RepeatPlaylist) else if (musicPlayer.RepeatPlaylist)
desc = "🔁 Repeating Playlist\n\n" + desc; desc = "🔁 " + GetText("repeating_playlist")+"\n\n" + desc;
var embed = new EmbedBuilder() var embed = new EmbedBuilder()
.WithAuthor(eab => eab.WithName($"Player Queue - Page {curPage}/{lastPage + 1}") .WithAuthor(eab => eab.WithName(GetText("player_queue", curPage, lastPage + 1))
.WithMusicIcon()) .WithMusicIcon())
.WithDescription(desc) .WithDescription(desc)
.WithFooter(ef => ef.WithText($"{musicPlayer.PrettyVolume} | {musicPlayer.Playlist.Count} " + .WithFooter(ef => ef.WithText($"{musicPlayer.PrettyVolume} | {musicPlayer.Playlist.Count} " +
$"{("tracks".SnPl(musicPlayer.Playlist.Count))} | {totalStr} | " + $"{("tracks".SnPl(musicPlayer.Playlist.Count))} | {totalStr} | " +
(musicPlayer.FairPlay ? "✔fairplay" : "✖fairplay") + $" | " + (maxPlaytime == 0 ? "unlimited" : $"{maxPlaytime}s limit"))) (musicPlayer.FairPlay
? "✔️" + GetText("fairplay")
: "✖️" + GetText("fairplay")) + " | " +
(maxPlaytime == 0 ? "unlimited" : GetText("play_limit", maxPlaytime))))
.WithOkColor(); .WithOkColor();
return embed; return embed;
@ -254,7 +261,7 @@ namespace NadekoBot.Modules.Music
try { await musicPlayer.UpdateSongDurationsAsync().ConfigureAwait(false); } catch { } try { await musicPlayer.UpdateSongDurationsAsync().ConfigureAwait(false); } catch { }
var embed = new EmbedBuilder().WithOkColor() var embed = new EmbedBuilder().WithOkColor()
.WithAuthor(eab => eab.WithName("Now Playing").WithMusicIcon()) .WithAuthor(eab => eab.WithName(GetText("now_playing")).WithMusicIcon())
.WithDescription(currentSong.PrettyName) .WithDescription(currentSong.PrettyName)
.WithThumbnailUrl(currentSong.Thumbnail) .WithThumbnailUrl(currentSong.Thumbnail)
.WithFooter(ef => ef.WithText(musicPlayer.PrettyVolume + " | " + currentSong.PrettyFullTime + $" | {currentSong.PrettyProvider} | {currentSong.QueuerName}")); .WithFooter(ef => ef.WithText(musicPlayer.PrettyVolume + " | " + currentSong.PrettyFullTime + $" | {currentSong.PrettyProvider} | {currentSong.QueuerName}"));
@ -271,21 +278,22 @@ namespace NadekoBot.Modules.Music
return; return;
if (((IGuildUser)Context.User).VoiceChannel != musicPlayer.PlaybackVoiceChannel) if (((IGuildUser)Context.User).VoiceChannel != musicPlayer.PlaybackVoiceChannel)
return; return;
if (val < 0) if (val < 0 || val > 100)
{
await ReplyErrorLocalized("volume_input_invalid").ConfigureAwait(false);
return; return;
}
var volume = musicPlayer.SetVolume(val); var volume = musicPlayer.SetVolume(val);
await Context.Channel.SendConfirmAsync($"🎵 Volume set to {volume}%").ConfigureAwait(false); await ReplyConfirmLocalized("volume_set", volume).ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
[RequireContext(ContextType.Guild)] [RequireContext(ContextType.Guild)]
public async Task Defvol([Remainder] int val) public async Task Defvol([Remainder] int val)
{ {
if (val < 0 || val > 100) if (val < 0 || val > 100)
{ {
await Context.Channel.SendErrorAsync("Volume number invalid. Must be between 0 and 100").ConfigureAwait(false); await ReplyErrorLocalized("volume_input_invalid").ConfigureAwait(false);
return; return;
} }
using (var uow = DbHandler.UnitOfWork()) using (var uow = DbHandler.UnitOfWork())
@ -293,7 +301,7 @@ namespace NadekoBot.Modules.Music
uow.GuildConfigs.For(Context.Guild.Id, set => set).DefaultMusicVolume = val / 100.0f; uow.GuildConfigs.For(Context.Guild.Id, set => set).DefaultMusicVolume = val / 100.0f;
uow.Complete(); uow.Complete();
} }
await Context.Channel.SendConfirmAsync($"🎵 Default volume set to {val}%").ConfigureAwait(false); await ReplyConfirmLocalized("defvol_set").ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -307,13 +315,10 @@ namespace NadekoBot.Modules.Music
if (((IGuildUser)Context.User).VoiceChannel != musicPlayer.PlaybackVoiceChannel) if (((IGuildUser)Context.User).VoiceChannel != musicPlayer.PlaybackVoiceChannel)
return; return;
if (musicPlayer.Playlist.Count < 2) if (musicPlayer.Playlist.Count < 2)
{
await Context.Channel.SendErrorAsync("💢 Not enough songs in order to perform the shuffle.").ConfigureAwait(false);
return; return;
}
musicPlayer.Shuffle(); musicPlayer.Shuffle();
await Context.Channel.SendConfirmAsync("🎵 Songs shuffled.").ConfigureAwait(false); await ReplyConfirmLocalized("songs_shuffled").ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -326,29 +331,31 @@ namespace NadekoBot.Modules.Music
return; return;
if (((IGuildUser)Context.User).VoiceChannel?.Guild != Context.Guild) if (((IGuildUser)Context.User).VoiceChannel?.Guild != Context.Guild)
{ {
await Context.Channel.SendErrorAsync($"💢 You need to be in a **voice channel** on this server.").ConfigureAwait(false); await ReplyErrorLocalized("must_be_in_voice").ConfigureAwait(false);
return; return;
} }
var plId = (await NadekoBot.Google.GetPlaylistIdsByKeywordsAsync(arg).ConfigureAwait(false)).FirstOrDefault(); var plId = (await NadekoBot.Google.GetPlaylistIdsByKeywordsAsync(arg).ConfigureAwait(false)).FirstOrDefault();
if (plId == null) if (plId == null)
{ {
await Context.Channel.SendErrorAsync("No search results for that query."); await ReplyErrorLocalized("no_search_results").ConfigureAwait(false);
return; return;
} }
var ids = await NadekoBot.Google.GetPlaylistTracksAsync(plId, 500).ConfigureAwait(false); var ids = await NadekoBot.Google.GetPlaylistTracksAsync(plId, 500).ConfigureAwait(false);
if (!ids.Any()) if (!ids.Any())
{ {
await Context.Channel.SendErrorAsync($"🎵 Failed to find any songs.").ConfigureAwait(false); await ReplyErrorLocalized("no_search_results").ConfigureAwait(false);
return; return;
} }
var count = ids.Count(); var count = ids.Count();
var msg = await Context.Channel.SendMessageAsync($"🎵 Attempting to queue **{count}** songs".SnPl(count) + "...").ConfigureAwait(false); var msg = await Context.Channel.SendMessageAsync(GetText("attempting_to_queue",
Format.Bold(count.ToString())))
.ConfigureAwait(false);
var cancelSource = new CancellationTokenSource(); var cancelSource = new CancellationTokenSource();
var gusr = (IGuildUser)Context.User; var gusr = (IGuildUser)Context.User;
//todo use grouping
while (ids.Any() && !cancelSource.IsCancellationRequested) while (ids.Any() && !cancelSource.IsCancellationRequested)
{ {
var tasks = Task.WhenAll(ids.Take(5).Select(async id => var tasks = Task.WhenAll(ids.Take(5).Select(async id =>
@ -367,7 +374,7 @@ namespace NadekoBot.Modules.Music
ids = ids.Skip(5); ids = ids.Skip(5);
} }
await msg.ModifyAsync(m => m.Content = "✅ Playlist queue complete.").ConfigureAwait(false); await msg.ModifyAsync(m => m.Content = GetText("playlist_queue_complete")).ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -393,7 +400,7 @@ namespace NadekoBot.Modules.Music
{ {
try try
{ {
mp.AddSong(new Song(new Classes.SongInfo mp.AddSong(new Song(new SongInfo
{ {
Title = svideo.FullName, Title = svideo.FullName,
Provider = "SoundCloud", Provider = "SoundCloud",
@ -435,20 +442,20 @@ namespace NadekoBot.Modules.Music
// ignored // ignored
} }
} }
await Context.Channel.SendConfirmAsync("🎵 Directory queue complete.").ConfigureAwait(false); await ReplyConfirmLocalized("dir_queue_complete").ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
[RequireContext(ContextType.Guild)] [RequireContext(ContextType.Guild)]
public async Task Radio(string radio_link) public async Task Radio(string radioLink)
{ {
if (((IGuildUser)Context.User).VoiceChannel?.Guild != Context.Guild) if (((IGuildUser)Context.User).VoiceChannel?.Guild != Context.Guild)
{ {
await Context.Channel.SendErrorAsync("💢 You need to be in a voice channel on this server.\n If you are already in a voice (ITextChannel)Context.Channel, try rejoining it.").ConfigureAwait(false); await ReplyErrorLocalized("must_be_in_voice").ConfigureAwait(false);
return; return;
} }
await QueueSong(((IGuildUser)Context.User), (ITextChannel)Context.Channel, ((IGuildUser)Context.User).VoiceChannel, radio_link, musicType: MusicType.Radio).ConfigureAwait(false); await QueueSong(((IGuildUser)Context.User), (ITextChannel)Context.Channel, ((IGuildUser)Context.User).VoiceChannel, radioLink, musicType: MusicType.Radio).ConfigureAwait(false);
if ((await Context.Guild.GetCurrentUserAsync()).GetPermissions((IGuildChannel)Context.Channel).ManageMessages) if ((await Context.Guild.GetCurrentUserAsync()).GetPermissions((IGuildChannel)Context.Channel).ManageMessages)
{ {
Context.Message.DeleteAfter(10); Context.Message.DeleteAfter(10);
@ -505,8 +512,7 @@ namespace NadekoBot.Modules.Music
MusicPlayer musicPlayer; MusicPlayer musicPlayer;
if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer)) return; if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer)) return;
musicPlayer.ClearQueue(); musicPlayer.ClearQueue();
await Context.Channel.SendConfirmAsync($"🎵 Queue cleared!").ConfigureAwait(false); await ReplyConfirmLocalized("queue_cleared").ConfigureAwait(false);
return;
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -532,7 +538,7 @@ namespace NadekoBot.Modules.Music
!int.TryParse(fromtoArr[1], out n2) || n1 < 1 || n2 < 1 || n1 == n2 || !int.TryParse(fromtoArr[1], out n2) || n1 < 1 || n2 < 1 || n1 == n2 ||
n1 > playlist.Count || n2 > playlist.Count) n1 > playlist.Count || n2 > playlist.Count)
{ {
await Context.Channel.SendErrorAsync("Invalid input.").ConfigureAwait(false); await ReplyConfirmLocalized("invalid_input").ConfigureAwait(false);
return; return;
} }
@ -544,9 +550,9 @@ namespace NadekoBot.Modules.Music
var embed = new EmbedBuilder() var embed = new EmbedBuilder()
.WithTitle($"{s.SongInfo.Title.TrimTo(70)}") .WithTitle($"{s.SongInfo.Title.TrimTo(70)}")
.WithUrl(s.SongUrl) .WithUrl(s.SongUrl)
.WithAuthor(eab => eab.WithName("Song Moved").WithIconUrl("https://cdn.discordapp.com/attachments/155726317222887425/258605269972549642/music1.png")) .WithAuthor(eab => eab.WithName(GetText("song_moved")).WithIconUrl("https://cdn.discordapp.com/attachments/155726317222887425/258605269972549642/music1.png"))
.AddField(fb => fb.WithName("**From Position**").WithValue($"#{n1}").WithIsInline(true)) .AddField(fb => fb.WithName(GetText("from_position")).WithValue($"#{n1}").WithIsInline(true))
.AddField(fb => fb.WithName("**To Position**").WithValue($"#{n2}").WithIsInline(true)) .AddField(fb => fb.WithName(GetText("to_position")).WithValue($"#{n2}").WithIsInline(true))
.WithColor(NadekoBot.OkColor); .WithColor(NadekoBot.OkColor);
await Context.Channel.EmbedAsync(embed).ConfigureAwait(false); await Context.Channel.EmbedAsync(embed).ConfigureAwait(false);
@ -564,7 +570,11 @@ namespace NadekoBot.Modules.Music
return; return;
musicPlayer.MaxQueueSize = size; musicPlayer.MaxQueueSize = size;
await Context.Channel.SendConfirmAsync($"🎵 Max queue set to {(size == 0 ? ("unlimited") : size + " tracks")}.");
if(size == 0)
await ReplyConfirmLocalized("max_queue_unlimited").ConfigureAwait(false);
else
await ReplyConfirmLocalized("max_queue_x", size).ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -580,9 +590,9 @@ namespace NadekoBot.Modules.Music
return; return;
musicPlayer.MaxPlaytimeSeconds = seconds; musicPlayer.MaxPlaytimeSeconds = seconds;
if (seconds == 0) if (seconds == 0)
await channel.SendConfirmAsync($"🎵 Max playtime has no limit now."); await ReplyConfirmLocalized("max_playtime_none").ConfigureAwait(false);
else else
await channel.SendConfirmAsync($"🎵 Max playtime set to {seconds} seconds."); await ReplyConfirmLocalized("max_playtime_set").ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -601,11 +611,11 @@ namespace NadekoBot.Modules.Music
if (currentValue) if (currentValue)
await Context.Channel.EmbedAsync(new EmbedBuilder() await Context.Channel.EmbedAsync(new EmbedBuilder()
.WithOkColor() .WithOkColor()
.WithAuthor(eab => eab.WithMusicIcon().WithName("🔂 Repeating track")) .WithAuthor(eab => eab.WithMusicIcon().WithName("🔂 " + GetText("repeating_track")))
.WithDescription(currentSong.PrettyName) .WithDescription(currentSong.PrettyName)
.WithFooter(ef => ef.WithText(currentSong.PrettyInfo))).ConfigureAwait(false); .WithFooter(ef => ef.WithText(currentSong.PrettyInfo))).ConfigureAwait(false);
else else
await Context.Channel.SendConfirmAsync($"🔂 Current track repeat stopped.") await Context.Channel.SendConfirmAsync("🔂 " + GetText("repeating_track_stopped"))
.ConfigureAwait(false); .ConfigureAwait(false);
} }
@ -618,7 +628,10 @@ namespace NadekoBot.Modules.Music
if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer)) if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer))
return; return;
var currentValue = musicPlayer.ToggleRepeatPlaylist(); var currentValue = musicPlayer.ToggleRepeatPlaylist();
await Context.Channel.SendConfirmAsync($"🔁 Repeat playlist {(currentValue ? "**enabled**." : "**disabled**.")}").ConfigureAwait(false); if(currentValue)
await ReplyConfirmLocalized("rpl_enabled").ConfigureAwait(false);
else
await ReplyConfirmLocalized("rpl_disabled").ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -655,7 +668,10 @@ namespace NadekoBot.Modules.Music
await uow.CompleteAsync().ConfigureAwait(false); await uow.CompleteAsync().ConfigureAwait(false);
} }
await Context.Channel.SendConfirmAsync(($"🎵 Saved playlist as **{name}**, ID: {playlist.Id}.")).ConfigureAwait(false); await Context.Channel.EmbedAsync(new EmbedBuilder().WithOkColor()
.WithTitle(GetText("playlist_saved"))
.AddField(efb => efb.WithName(GetText("name")).WithValue(name))
.AddField(efb => efb.WithName(GetText("id")).WithValue(playlist.Id.ToString())));
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -670,11 +686,11 @@ namespace NadekoBot.Modules.Music
if (mpl == null) if (mpl == null)
{ {
await Context.Channel.SendErrorAsync("Can't find playlist with that ID.").ConfigureAwait(false); await ReplyErrorLocalized("playlist_id_not_found").ConfigureAwait(false);
return; return;
} }
IUserMessage msg = null; IUserMessage msg = null;
try { msg = await Context.Channel.SendMessageAsync($"🎶 Attempting to load **{mpl.Songs.Count}** songs...").ConfigureAwait(false); } catch (Exception ex) { _log.Warn(ex); } try { msg = await ReplyConfirmLocalized("attempting_to_queue", Format.Bold(mpl.Songs.Count.ToString())).ConfigureAwait(false); } catch (Exception ex) { _log.Warn(ex); }
foreach (var item in mpl.Songs) foreach (var item in mpl.Songs)
{ {
var usr = (IGuildUser)Context.User; var usr = (IGuildUser)Context.User;
@ -686,15 +702,13 @@ namespace NadekoBot.Modules.Music
catch { break; } catch { break; }
} }
if (msg != null) if (msg != null)
await msg.ModifyAsync(m => m.Content = $"✅ Done loading playlist **{mpl.Name}**.").ConfigureAwait(false); await msg.ModifyAsync(m => m.Content = GetText("playlist_queue_complete")).ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
[RequireContext(ContextType.Guild)] [RequireContext(ContextType.Guild)]
public async Task Playlists([Remainder] int num = 1) public async Task Playlists([Remainder] int num = 1)
{ {
if (num <= 0) if (num <= 0)
return; return;
@ -706,8 +720,9 @@ namespace NadekoBot.Modules.Music
} }
var embed = new EmbedBuilder() var embed = new EmbedBuilder()
.WithAuthor(eab => eab.WithName($"Page {num} of Saved Playlists").WithMusicIcon()) .WithAuthor(eab => eab.WithName(GetText("playlists_page", num)).WithMusicIcon())
.WithDescription(string.Join("\n", playlists.Select(r => $"`#{r.Id}` - **{r.Name}** by *{r.Author}* ({r.Songs.Count} songs)"))) .WithDescription(string.Join("\n", playlists.Select(r =>
GetText("playlists", "#" + r.Id, r.Name, r.Author, r.Songs.Count))))
.WithOkColor(); .WithOkColor();
await Context.Channel.EmbedAsync(embed).ConfigureAwait(false); await Context.Channel.EmbedAsync(embed).ConfigureAwait(false);
@ -717,13 +732,12 @@ namespace NadekoBot.Modules.Music
[RequireContext(ContextType.Guild)] [RequireContext(ContextType.Guild)]
public async Task DeletePlaylist([Remainder] int id) public async Task DeletePlaylist([Remainder] int id)
{ {
bool success = false; var success = false;
MusicPlaylist pl = null;
try try
{ {
using (var uow = DbHandler.UnitOfWork()) using (var uow = DbHandler.UnitOfWork())
{ {
pl = uow.MusicPlaylists.Get(id); var pl = uow.MusicPlaylists.Get(id);
if (pl != null) if (pl != null)
{ {
@ -733,15 +747,13 @@ namespace NadekoBot.Modules.Music
await uow.CompleteAsync().ConfigureAwait(false); await uow.CompleteAsync().ConfigureAwait(false);
success = true; success = true;
} }
else
success = false;
} }
} }
if (!success) if (!success)
await Context.Channel.SendErrorAsync("Failed to delete that playlist. It either doesn't exist, or you are not its author.").ConfigureAwait(false); await ReplyErrorLocalized("playlist_delete_fail").ConfigureAwait(false);
else else
await Context.Channel.SendConfirmAsync("🗑 Playlist successfully **deleted**.").ConfigureAwait(false); await ReplyConfirmLocalized("playlist_deleted").ConfigureAwait(false);
} }
catch (Exception ex) catch (Exception ex)
{ {
@ -781,7 +793,7 @@ namespace NadekoBot.Modules.Music
if (seconds.Length == 1) if (seconds.Length == 1)
seconds = "0" + seconds; seconds = "0" + seconds;
await Context.Channel.SendConfirmAsync($"Skipped to `{minutes}:{seconds}`").ConfigureAwait(false); await ReplyConfirmLocalized("skipped_to", minutes, seconds).ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -793,9 +805,9 @@ namespace NadekoBot.Modules.Music
return; return;
if (!musicPlayer.ToggleAutoplay()) if (!musicPlayer.ToggleAutoplay())
await Context.Channel.SendConfirmAsync("❌ Autoplay disabled.").ConfigureAwait(false); await ReplyConfirmLocalized("autoplay_disabled").ConfigureAwait(false);
else else
await Context.Channel.SendConfirmAsync("✅ Autoplay enabled.").ConfigureAwait(false); await ReplyConfirmLocalized("autoplay_enabled").ConfigureAwait(false);
} }
[NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
@ -806,29 +818,29 @@ namespace NadekoBot.Modules.Music
MusicPlayer musicPlayer; MusicPlayer musicPlayer;
if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer)) if (!MusicPlayers.TryGetValue(Context.Guild.Id, out musicPlayer))
{ {
await Context.Channel.SendErrorAsync("Music must be playing before you set an ouput channel.").ConfigureAwait(false); await ReplyErrorLocalized("player_none").ConfigureAwait(false);
return; return;
} }
musicPlayer.OutputTextChannel = (ITextChannel)Context.Channel; musicPlayer.OutputTextChannel = (ITextChannel)Context.Channel;
await Context.Channel.SendConfirmAsync("I will now output playing, finished, paused and removed songs in this channel.").ConfigureAwait(false); await ReplyConfirmLocalized("set_music_channel").ConfigureAwait(false);
} }
public static async Task QueueSong(IGuildUser queuer, ITextChannel textCh, IVoiceChannel voiceCh, string query, bool silent = false, MusicType musicType = MusicType.Normal) public async Task QueueSong(IGuildUser queuer, ITextChannel textCh, IVoiceChannel voiceCh, string query, bool silent = false, MusicType musicType = MusicType.Normal)
{ {
if (voiceCh == null || voiceCh.Guild != textCh.Guild) if (voiceCh == null || voiceCh.Guild != textCh.Guild)
{ {
if (!silent) if (!silent)
await textCh.SendErrorAsync($"💢 You need to be in a voice channel on this server.").ConfigureAwait(false); await textCh.SendErrorAsync(GetText("must_be_in_voice")).ConfigureAwait(false);
throw new ArgumentNullException(nameof(voiceCh)); throw new ArgumentNullException(nameof(voiceCh));
} }
if (string.IsNullOrWhiteSpace(query) || query.Length < 3) if (string.IsNullOrWhiteSpace(query) || query.Length < 3)
throw new ArgumentException("💢 Invalid query for queue song.", nameof(query)); throw new ArgumentException("Invalid song query.", nameof(query));
var musicPlayer = MusicPlayers.GetOrAdd(textCh.Guild.Id, server => var musicPlayer = MusicPlayers.GetOrAdd(textCh.Guild.Id, server =>
{ {
float vol = 1;// SpecificConfigurations.Default.Of(server.Id).DefaultMusicVolume; float vol;// SpecificConfigurations.Default.Of(server.Id).DefaultMusicVolume;
using (var uow = DbHandler.UnitOfWork()) using (var uow = DbHandler.UnitOfWork())
{ {
vol = uow.GuildConfigs.For(textCh.Guild.Id, set => set).DefaultMusicVolume; vol = uow.GuildConfigs.For(textCh.Guild.Id, set => set).DefaultMusicVolume;
@ -845,7 +857,7 @@ namespace NadekoBot.Modules.Music
try try
{ {
lastFinishedMessage = await mp.OutputTextChannel.EmbedAsync(new EmbedBuilder().WithOkColor() lastFinishedMessage = await mp.OutputTextChannel.EmbedAsync(new EmbedBuilder().WithOkColor()
.WithAuthor(eab => eab.WithName("Finished Song").WithMusicIcon()) .WithAuthor(eab => eab.WithName(GetText("finished_song")).WithMusicIcon())
.WithDescription(song.PrettyName) .WithDescription(song.PrettyName)
.WithFooter(ef => ef.WithText(song.PrettyInfo))) .WithFooter(ef => ef.WithText(song.PrettyInfo)))
.ConfigureAwait(false); .ConfigureAwait(false);
@ -866,7 +878,10 @@ namespace NadekoBot.Modules.Music
true).ConfigureAwait(false); true).ConfigureAwait(false);
} }
} }
catch { } catch
{
// ignored
}
}; };
mp.OnStarted += async (player, song) => mp.OnStarted += async (player, song) =>
@ -876,7 +891,7 @@ namespace NadekoBot.Modules.Music
{ {
// ignored // ignored
} }
var sender = player as MusicPlayer; var sender = player;
if (sender == null) if (sender == null)
return; return;
try try
@ -884,12 +899,15 @@ namespace NadekoBot.Modules.Music
playingMessage?.DeleteAfter(0); playingMessage?.DeleteAfter(0);
playingMessage = await mp.OutputTextChannel.EmbedAsync(new EmbedBuilder().WithOkColor() playingMessage = await mp.OutputTextChannel.EmbedAsync(new EmbedBuilder().WithOkColor()
.WithAuthor(eab => eab.WithName("Playing Song").WithMusicIcon()) .WithAuthor(eab => eab.WithName(GetText("playing_song")).WithMusicIcon())
.WithDescription(song.PrettyName) .WithDescription(song.PrettyName)
.WithFooter(ef => ef.WithText(song.PrettyInfo))) .WithFooter(ef => ef.WithText(song.PrettyInfo)))
.ConfigureAwait(false); .ConfigureAwait(false);
} }
catch { } catch
{
// ignored
}
}; };
mp.OnPauseChanged += async (paused) => mp.OnPauseChanged += async (paused) =>
{ {
@ -897,13 +915,16 @@ namespace NadekoBot.Modules.Music
{ {
IUserMessage msg; IUserMessage msg;
if (paused) if (paused)
msg = await mp.OutputTextChannel.SendConfirmAsync("🎵 Music playback **paused**.").ConfigureAwait(false); msg = await mp.OutputTextChannel.SendConfirmAsync(GetText("music_paused")).ConfigureAwait(false);
else else
msg = await mp.OutputTextChannel.SendConfirmAsync("🎵 Music playback **resumed**.").ConfigureAwait(false); msg = await mp.OutputTextChannel.SendConfirmAsync(GetText("music_resumed")).ConfigureAwait(false);
msg?.DeleteAfter(10); msg?.DeleteAfter(10);
} }
catch { } catch
{
// ignored
}
}; };
mp.SongRemoved += async (song, index) => mp.SongRemoved += async (song, index) =>
@ -911,7 +932,7 @@ namespace NadekoBot.Modules.Music
try try
{ {
var embed = new EmbedBuilder() var embed = new EmbedBuilder()
.WithAuthor(eab => eab.WithName("Removed song #" + (index + 1)).WithMusicIcon()) .WithAuthor(eab => eab.WithName(GetText("removed_song") + " #" + (index + 1)).WithMusicIcon())
.WithDescription(song.PrettyName) .WithDescription(song.PrettyName)
.WithFooter(ef => ef.WithText(song.PrettyInfo)) .WithFooter(ef => ef.WithText(song.PrettyInfo))
.WithErrorColor(); .WithErrorColor();
@ -939,7 +960,14 @@ namespace NadekoBot.Modules.Music
} }
catch (PlaylistFullException) catch (PlaylistFullException)
{ {
try { await textCh.SendConfirmAsync($"🎵 Queue is full at **{musicPlayer.MaxQueueSize}/{musicPlayer.MaxQueueSize}**."); } catch { } try
{
await textCh.SendConfirmAsync(GetText("queue_full", musicPlayer.MaxQueueSize));
}
catch
{
// ignored
}
throw; throw;
} }
if (!silent) if (!silent)
@ -948,8 +976,8 @@ namespace NadekoBot.Modules.Music
{ {
//var queuedMessage = await textCh.SendConfirmAsync($"🎵 Queued **{resolvedSong.SongInfo.Title}** at `#{musicPlayer.Playlist.Count + 1}`").ConfigureAwait(false); //var queuedMessage = await textCh.SendConfirmAsync($"🎵 Queued **{resolvedSong.SongInfo.Title}** at `#{musicPlayer.Playlist.Count + 1}`").ConfigureAwait(false);
var queuedMessage = await textCh.EmbedAsync(new EmbedBuilder().WithOkColor() var queuedMessage = await textCh.EmbedAsync(new EmbedBuilder().WithOkColor()
.WithAuthor(eab => eab.WithName("Queued Song #" + (musicPlayer.Playlist.Count + 1)).WithMusicIcon()) .WithAuthor(eab => eab.WithName(GetText("queued_song") + " #" + (musicPlayer.Playlist.Count + 1)).WithMusicIcon())
.WithDescription($"{resolvedSong.PrettyName}\nQueue ") .WithDescription($"{resolvedSong.PrettyName}\n{GetText("queue")} ")
.WithThumbnailUrl(resolvedSong.Thumbnail) .WithThumbnailUrl(resolvedSong.Thumbnail)
.WithFooter(ef => ef.WithText(resolvedSong.PrettyProvider))) .WithFooter(ef => ef.WithText(resolvedSong.PrettyProvider)))
.ConfigureAwait(false); .ConfigureAwait(false);

View File

@ -3388,6 +3388,483 @@ namespace NadekoBot.Resources {
} }
} }
/// <summary>
/// Looks up a localized string similar to Attempting to queue {0} songs....
/// </summary>
public static string music_attempting_to_queue {
get {
return ResourceManager.GetString("music_attempting_to_queue", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Autoplay disabled..
/// </summary>
public static string music_autoplay_disabled {
get {
return ResourceManager.GetString("music_autoplay_disabled", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Autoplay enabled..
/// </summary>
public static string music_autoplay_enabled {
get {
return ResourceManager.GetString("music_autoplay_enabled", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Default volume set to {0}%.
/// </summary>
public static string music_defvol_set {
get {
return ResourceManager.GetString("music_defvol_set", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Directory queue complete..
/// </summary>
public static string music_dir_queue_complete {
get {
return ResourceManager.GetString("music_dir_queue_complete", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Finished Song.
/// </summary>
public static string music_finished_song {
get {
return ResourceManager.GetString("music_finished_song", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Fair play disabled..
/// </summary>
public static string music_fp_disabled {
get {
return ResourceManager.GetString("music_fp_disabled", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Fair play enabled..
/// </summary>
public static string music_fp_enabled {
get {
return ResourceManager.GetString("music_fp_enabled", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to From position.
/// </summary>
public static string music_from_position {
get {
return ResourceManager.GetString("music_from_position", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Id.
/// </summary>
public static string music_id {
get {
return ResourceManager.GetString("music_id", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Invalid input..
/// </summary>
public static string music_invalid_input {
get {
return ResourceManager.GetString("music_invalid_input", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Max playtime has no limit now..
/// </summary>
public static string music_max_playtime_none {
get {
return ResourceManager.GetString("music_max_playtime_none", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Max playtime set to {0} second(s)..
/// </summary>
public static string music_max_playtime_set {
get {
return ResourceManager.GetString("music_max_playtime_set", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Max music queue size set to unlimited..
/// </summary>
public static string music_max_queue_unlimited {
get {
return ResourceManager.GetString("music_max_queue_unlimited", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Max music queue size set to {0} track(s)..
/// </summary>
public static string music_max_queue_x {
get {
return ResourceManager.GetString("music_max_queue_x", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to You need to be in the voice channel on this server..
/// </summary>
public static string music_must_be_in_voice {
get {
return ResourceManager.GetString("music_must_be_in_voice", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Name.
/// </summary>
public static string music_name {
get {
return ResourceManager.GetString("music_name", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to No active music player..
/// </summary>
public static string music_no_player {
get {
return ResourceManager.GetString("music_no_player", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to No search results..
/// </summary>
public static string music_no_search_results {
get {
return ResourceManager.GetString("music_no_search_results", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Now Playing.
/// </summary>
public static string music_now_playing {
get {
return ResourceManager.GetString("music_now_playing", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Music playback paused..
/// </summary>
public static string music_paused {
get {
return ResourceManager.GetString("music_paused", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to {0}s limit.
/// </summary>
public static string music_play_limit {
get {
return ResourceManager.GetString("music_play_limit", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to No music player active..
/// </summary>
public static string music_player_none {
get {
return ResourceManager.GetString("music_player_none", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Player Queue - Page {0}/{1}.
/// </summary>
public static string music_player_queue {
get {
return ResourceManager.GetString("music_player_queue", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Playing Song.
/// </summary>
public static string music_playing_song {
get {
return ResourceManager.GetString("music_playing_song", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Failed to delete that playlist. It either doesn&apos;t exist, or you are not its author..
/// </summary>
public static string music_playlist_delete_fail {
get {
return ResourceManager.GetString("music_playlist_delete_fail", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Playlist deleted..
/// </summary>
public static string music_playlist_deleted {
get {
return ResourceManager.GetString("music_playlist_deleted", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Playlist with that ID doesn&apos;t exist..
/// </summary>
public static string music_playlist_id_not_found {
get {
return ResourceManager.GetString("music_playlist_id_not_found", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Playlist queue complete..
/// </summary>
public static string music_playlist_queue_complete {
get {
return ResourceManager.GetString("music_playlist_queue_complete", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Playlist Saved.
/// </summary>
public static string music_playlist_saved {
get {
return ResourceManager.GetString("music_playlist_saved", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to `#{0}` - **{1}** by *{2}* ({3} songs).
/// </summary>
public static string music_playlists {
get {
return ResourceManager.GetString("music_playlists", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Page {0} of Saved Playlists.
/// </summary>
public static string music_playlists_page {
get {
return ResourceManager.GetString("music_playlists_page", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Queue.
/// </summary>
public static string music_queue {
get {
return ResourceManager.GetString("music_queue", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Music queue cleared..
/// </summary>
public static string music_queue_cleared {
get {
return ResourceManager.GetString("music_queue_cleared", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Queue is full at {0}/{0}..
/// </summary>
public static string music_queue_full {
get {
return ResourceManager.GetString("music_queue_full", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Queued Song.
/// </summary>
public static string music_queued_song {
get {
return ResourceManager.GetString("music_queued_song", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Removed song.
/// </summary>
public static string music_removed_song {
get {
return ResourceManager.GetString("music_removed_song", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Repeating Current Song.
/// </summary>
public static string music_repeating_cur_song {
get {
return ResourceManager.GetString("music_repeating_cur_song", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Repeating Playlist.
/// </summary>
public static string music_repeating_playlist {
get {
return ResourceManager.GetString("music_repeating_playlist", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Repeating Track.
/// </summary>
public static string music_repeating_track {
get {
return ResourceManager.GetString("music_repeating_track", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Current track repeat stopped..
/// </summary>
public static string music_repeating_track_stopped {
get {
return ResourceManager.GetString("music_repeating_track_stopped", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Music playback resumed..
/// </summary>
public static string music_resumed {
get {
return ResourceManager.GetString("music_resumed", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Repeat playlist disabled..
/// </summary>
public static string music_rpl_disabled {
get {
return ResourceManager.GetString("music_rpl_disabled", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Repeat playlist enabled..
/// </summary>
public static string music_rpl_enabled {
get {
return ResourceManager.GetString("music_rpl_enabled", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to I will now output playing, finished, paused and removed songs in this channel..
/// </summary>
public static string music_set_music_channel {
get {
return ResourceManager.GetString("music_set_music_channel", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Skipped to `{0}:{1}`.
/// </summary>
public static string music_skipped_to {
get {
return ResourceManager.GetString("music_skipped_to", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Song Moved.
/// </summary>
public static string music_song_moved {
get {
return ResourceManager.GetString("music_song_moved", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Songs shuffled..
/// </summary>
public static string music_songs_shuffled {
get {
return ResourceManager.GetString("music_songs_shuffled", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to {0}h {1}m {2}s.
/// </summary>
public static string music_time_format {
get {
return ResourceManager.GetString("music_time_format", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to To position.
/// </summary>
public static string music_to_position {
get {
return ResourceManager.GetString("music_to_position", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to unlimited.
/// </summary>
public static string music_unlimited {
get {
return ResourceManager.GetString("music_unlimited", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Volume must be between 0 and 100.
/// </summary>
public static string music_volume_input_invalid {
get {
return ResourceManager.GetString("music_volume_input_invalid", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Volume set to {0}%.
/// </summary>
public static string music_volume_set {
get {
return ResourceManager.GetString("music_volume_set", resourceCulture);
}
}
/// <summary> /// <summary>
/// Looks up a localized string similar to Autohentai started. Reposting every {0}s with one of the following tags: /// Looks up a localized string similar to Autohentai started. Reposting every {0}s with one of the following tags:
///{1}. ///{1}.

View File

@ -1332,6 +1332,166 @@ Don't forget to leave your discord name or id in the message.
<data name="games_vs" xml:space="preserve"> <data name="games_vs" xml:space="preserve">
<value>{0} vs {1}</value> <value>{0} vs {1}</value>
</data> </data>
<data name="music_attempting_to_queue" xml:space="preserve">
<value>Attempting to queue {0} songs...</value>
</data>
<data name="music_autoplay_disabled" xml:space="preserve">
<value>Autoplay disabled.</value>
</data>
<data name="music_autoplay_enabled" xml:space="preserve">
<value>Autoplay enabled.</value>
</data>
<data name="music_defvol_set" xml:space="preserve">
<value>Default volume set to {0}%</value>
</data>
<data name="music_dir_queue_complete" xml:space="preserve">
<value>Directory queue complete.</value>
</data>
<data name="music_finished_song" xml:space="preserve">
<value>Finished Song</value>
</data>
<data name="music_fp_disabled" xml:space="preserve">
<value>Fair play disabled.</value>
</data>
<data name="music_fp_enabled" xml:space="preserve">
<value>Fair play enabled.</value>
</data>
<data name="music_from_position" xml:space="preserve">
<value>From position</value>
</data>
<data name="music_id" xml:space="preserve">
<value>Id</value>
</data>
<data name="music_invalid_input" xml:space="preserve">
<value>Invalid input.</value>
</data>
<data name="music_max_playtime_none" xml:space="preserve">
<value>Max playtime has no limit now.</value>
</data>
<data name="music_max_playtime_set" xml:space="preserve">
<value>Max playtime set to {0} second(s).</value>
</data>
<data name="music_max_queue_unlimited" xml:space="preserve">
<value>Max music queue size set to unlimited.</value>
</data>
<data name="music_max_queue_x" xml:space="preserve">
<value>Max music queue size set to {0} track(s).</value>
</data>
<data name="music_must_be_in_voice" xml:space="preserve">
<value>You need to be in the voice channel on this server.</value>
</data>
<data name="music_name" xml:space="preserve">
<value>Name</value>
</data>
<data name="music_now_playing" xml:space="preserve">
<value>Now Playing</value>
</data>
<data name="music_no_player" xml:space="preserve">
<value>No active music player.</value>
</data>
<data name="music_no_search_results" xml:space="preserve">
<value>No search results.</value>
</data>
<data name="music_paused" xml:space="preserve">
<value>Music playback paused.</value>
</data>
<data name="music_player_none" xml:space="preserve">
<value>No music player active.</value>
</data>
<data name="music_player_queue" xml:space="preserve">
<value>Player Queue - Page {0}/{1}</value>
</data>
<data name="music_playing_song" xml:space="preserve">
<value>Playing Song</value>
</data>
<data name="music_playlists" xml:space="preserve">
<value>`#{0}` - **{1}** by *{2}* ({3} songs)</value>
</data>
<data name="music_playlists_page" xml:space="preserve">
<value>Page {0} of Saved Playlists</value>
</data>
<data name="music_playlist_deleted" xml:space="preserve">
<value>Playlist deleted.</value>
</data>
<data name="music_playlist_delete_fail" xml:space="preserve">
<value>Failed to delete that playlist. It either doesn't exist, or you are not its author.</value>
</data>
<data name="music_playlist_id_not_found" xml:space="preserve">
<value>Playlist with that ID doesn't exist.</value>
</data>
<data name="music_playlist_queue_complete" xml:space="preserve">
<value>Playlist queue complete.</value>
</data>
<data name="music_playlist_saved" xml:space="preserve">
<value>Playlist Saved</value>
</data>
<data name="music_play_limit" xml:space="preserve">
<value>{0}s limit</value>
</data>
<data name="music_queue" xml:space="preserve">
<value>Queue</value>
</data>
<data name="music_queued_song" xml:space="preserve">
<value>Queued Song</value>
</data>
<data name="music_queue_cleared" xml:space="preserve">
<value>Music queue cleared.</value>
</data>
<data name="music_queue_full" xml:space="preserve">
<value>Queue is full at {0}/{0}.</value>
</data>
<data name="music_removed_song" xml:space="preserve">
<value>Removed song</value>
<comment>context: "removed song #5"</comment>
</data>
<data name="music_repeating_cur_song" xml:space="preserve">
<value>Repeating Current Song</value>
</data>
<data name="music_repeating_playlist" xml:space="preserve">
<value>Repeating Playlist</value>
</data>
<data name="music_repeating_track" xml:space="preserve">
<value>Repeating Track</value>
</data>
<data name="music_repeating_track_stopped" xml:space="preserve">
<value>Current track repeat stopped.</value>
</data>
<data name="music_resumed" xml:space="preserve">
<value>Music playback resumed.</value>
</data>
<data name="music_rpl_disabled" xml:space="preserve">
<value>Repeat playlist disabled.</value>
</data>
<data name="music_rpl_enabled" xml:space="preserve">
<value>Repeat playlist enabled.</value>
</data>
<data name="music_set_music_channel" xml:space="preserve">
<value>I will now output playing, finished, paused and removed songs in this channel.</value>
</data>
<data name="music_skipped_to" xml:space="preserve">
<value>Skipped to `{0}:{1}`</value>
</data>
<data name="music_songs_shuffled" xml:space="preserve">
<value>Songs shuffled.</value>
</data>
<data name="music_song_moved" xml:space="preserve">
<value>Song Moved</value>
</data>
<data name="music_time_format" xml:space="preserve">
<value>{0}h {1}m {2}s</value>
</data>
<data name="music_to_position" xml:space="preserve">
<value>To position</value>
</data>
<data name="music_unlimited" xml:space="preserve">
<value>unlimited</value>
</data>
<data name="music_volume_input_invalid" xml:space="preserve">
<value>Volume must be between 0 and 100</value>
</data>
<data name="music_volume_set" xml:space="preserve">
<value>Volume set to {0}%</value>
</data>
<data name="permissions_acm_disable" xml:space="preserve"> <data name="permissions_acm_disable" xml:space="preserve">
<value>Disabled usage of ALL MODULES on {0} channel.</value> <value>Disabled usage of ALL MODULES on {0} channel.</value>
</data> </data>

View File

@ -14,9 +14,9 @@ namespace NadekoBot.Services.Impl
public class StatsService : IStatsService public class StatsService : IStatsService
{ {
private readonly DiscordShardedClient _client; private readonly DiscordShardedClient _client;
private DateTime _started; private readonly DateTime _started;
public const string BotVersion = "1.1.8-alpha"; public const string BotVersion = "1.2-beta";
public string Author => "Kwoth#2560"; public string Author => "Kwoth#2560";
public string Library => "Discord.Net"; public string Library => "Discord.Net";