diff --git a/Opus/Code/Api/ChannelManager.cs b/Opus/Code/Api/ChannelManager.cs
new file mode 100644
index 0000000..1bc9332
--- /dev/null
+++ b/Opus/Code/Api/ChannelManager.cs
@@ -0,0 +1,57 @@
+using Google.Apis.YouTube.v3;
+using Google.Apis.YouTube.v3.Data;
+using Opus.DataStructure;
+using System.Collections.Generic;
+using System.Threading.Tasks;
+using Channel = Opus.DataStructure.Channel;
+
+namespace Opus.Api
+{
+ public class ChannelManager
+ {
+ ///
+ /// Return a complete Channel object from the youtube id of the channel
+ ///
+ ///
+ ///
+ public async static Task GetChannel(string channelID)
+ {
+ ChannelsResource.ListRequest request = YoutubeManager.YoutubeService.Channels.List("snippet");
+ request.Id = channelID;
+
+ ChannelListResponse response = await request.ExecuteAsync();
+
+ if (response.Items.Count > 0)
+ {
+ var result = response.Items[0];
+ return new Channel(result.Snippet.Title, channelID, result.Snippet.Thumbnails.High.Url);
+ }
+ else
+ return null;
+ }
+
+ ///
+ /// Return a list of complete Channel objects from the youtube ids of the channels
+ ///
+ ///
+ ///
+ public async static Task> GetChannels(IEnumerable channelIDs)
+ {
+ ChannelsResource.ListRequest request = YoutubeManager.YoutubeService.Channels.List("snippet");
+ request.Id = string.Join(";", channelIDs);
+
+ ChannelListResponse response = await request.ExecuteAsync();
+
+ if (response.Items.Count > 0)
+ {
+ List channels = new List();
+ foreach (var result in response.Items)
+ channels.Add(new Channel(result.Snippet.Title, result.Id, result.Snippet.Thumbnails.High.Url));
+
+ return channels;
+ }
+ else
+ return null;
+ }
+ }
+}
\ No newline at end of file
diff --git a/Opus/Code/Api/PlaylistManager.cs b/Opus/Code/Api/PlaylistManager.cs
index 55e21b6..2910128 100644
--- a/Opus/Code/Api/PlaylistManager.cs
+++ b/Opus/Code/Api/PlaylistManager.cs
@@ -39,23 +39,30 @@ namespace Opus.Api
///
public static async Task GetPlaylist(string playlistID)
{
- PlaylistsResource.ListRequest request = YoutubeManager.YoutubeService.Playlists.List("snippet");
- request.Id = playlistID;
-
- PlaylistListResponse response = await request.ExecuteAsync();
-
- if (response.Items.Count > 0)
+ try
{
- Playlist result = response.Items[0];
- return new PlaylistItem(result.Snippet.Title, -1, playlistID)
+ PlaylistsResource.ListRequest request = YoutubeManager.YoutubeService.Playlists.List("snippet");
+ request.Id = playlistID;
+
+ PlaylistListResponse response = await request.ExecuteAsync();
+
+ if (response.Items.Count > 0)
{
- HasWritePermission = false,
- ImageURL = result.Snippet.Thumbnails.High.Url,
- Owner = result.Snippet.ChannelTitle
- };
+ return new PlaylistItem(response.Items[0].Snippet.Title, -1, playlistID)
+ {
+ HasWritePermission = false,
+ ImageURL = response.Items[0].Snippet.Thumbnails.Standard.Url,
+ Owner = response.Items[0].Snippet.ChannelTitle
+ };
+ }
+ else
+ return null;
}
- else
+ catch(Exception ex)
+ {
+ Console.WriteLine("&Get playlist catch called, ex: " + ex.Message);
return null;
+ }
}
#region PlayInOrder
diff --git a/Opus/Code/Api/Services/MusicPlayer.cs b/Opus/Code/Api/Services/MusicPlayer.cs
index 454e0b5..f242262 100644
--- a/Opus/Code/Api/Services/MusicPlayer.cs
+++ b/Opus/Code/Api/Services/MusicPlayer.cs
@@ -21,7 +21,7 @@ using Com.Google.Android.Exoplayer2.Trackselection;
using Com.Google.Android.Exoplayer2.Upstream;
using Com.Google.Android.Exoplayer2.Util;
using Newtonsoft.Json;
-using Opus.Code.Api;
+using Opus.Api;
using Opus.DataStructure;
using Opus.Fragments;
using Opus.Others;
@@ -974,7 +974,7 @@ namespace Opus.Api.Services
}
else
{
- SongParser.playPosition = -1;
+ SongParser.playPosition = -2;
currentID = position;
Play(song, StartFromOldPosition ? LastTimer : -1, false);
}
diff --git a/Opus/Code/Api/SongParser.cs b/Opus/Code/Api/SongParser.cs
index 291abf7..9010bef 100644
--- a/Opus/Code/Api/SongParser.cs
+++ b/Opus/Code/Api/SongParser.cs
@@ -12,7 +12,7 @@ using System.Threading.Tasks;
using YoutubeExplode;
using YoutubeExplode.Models;
-namespace Opus.Code.Api
+namespace Opus.Api
{
public class SongParser
{
@@ -20,7 +20,7 @@ namespace Opus.Code.Api
///
/// The reference of the play item. The song parser will start the playback of this queue item as soon as possible.
///
- public static int playPosition = -1;
+ public static int playPosition = -2;
private int queuePosition = -1;
private bool canceled = false;
@@ -154,7 +154,7 @@ namespace Opus.Code.Api
}
MusicPlayer.instance.Play(song, -1, queuePosition == -1);
- playPosition = -1;
+ playPosition = -2;
}
Video video = await client.GetVideoAsync(song.YoutubeID);
@@ -187,7 +187,7 @@ namespace Opus.Code.Api
if(playPosition == queuePosition)
{
- playPosition = -1;
+ playPosition = -2;
Queue.instance.RefreshCurrent();
Player.instance?.Ready();
MainActivity.instance.Timout();
@@ -206,7 +206,7 @@ namespace Opus.Code.Api
if (playPosition == queuePosition)
{
- playPosition = -1;
+ playPosition = -2;
Queue.instance.RefreshCurrent();
Player.instance?.Ready();
}
@@ -223,7 +223,7 @@ namespace Opus.Code.Api
if (playPosition == queuePosition)
{
- playPosition = -1;
+ playPosition = -2;
Queue.instance.RefreshCurrent();
Player.instance?.Ready();
}
@@ -237,7 +237,7 @@ namespace Opus.Code.Api
if (playPosition == queuePosition)
{
- playPosition = -1;
+ playPosition = -2;
Queue.instance.RefreshCurrent();
Player.instance?.Ready();
MainActivity.instance.UnknowError(ErrorCode.SP1, null, Snackbar.LengthLong);
@@ -245,7 +245,7 @@ namespace Opus.Code.Api
}
if (playPosition == queuePosition)
- playPosition = -1;
+ playPosition = -2;
queuePosition = -1;
instances.Remove(this);
return song;
diff --git a/Opus/Code/DataStructure/HomeSection.cs b/Opus/Code/DataStructure/HomeSection.cs
index 1ee3adb..e64e6d2 100644
--- a/Opus/Code/DataStructure/HomeSection.cs
+++ b/Opus/Code/DataStructure/HomeSection.cs
@@ -11,6 +11,7 @@ namespace Opus.DataStructure
public List contentValue;
public List playlistContent;
public List channelContent;
+ public PlaylistItem playlist;
public RecyclerView recycler;
public Section(string sectionTitle, SectionType contentType)
@@ -26,6 +27,14 @@ namespace Opus.DataStructure
this.contentValue = contentValue;
}
+ public Section(string sectionTitle, SectionType contentType, List contentValue, PlaylistItem playlist)
+ {
+ SectionTitle = sectionTitle;
+ this.contentType = contentType;
+ this.contentValue = contentValue;
+ this.playlist = playlist;
+ }
+
public Section(string sectionTitle, SectionType contentType, List playlistContent)
{
SectionTitle = sectionTitle;
diff --git a/Opus/Code/MainActivity.cs b/Opus/Code/MainActivity.cs
index 5681ac3..91a43ae 100644
--- a/Opus/Code/MainActivity.cs
+++ b/Opus/Code/MainActivity.cs
@@ -313,13 +313,12 @@ namespace Opus
{
if(item.ItemId == Android.Resource.Id.Home)
{
- if (PlaylistTracks.instance != null || FolderTracks.instance != null)
+ if (PlaylistTracks.instance != null || FolderTracks.instance != null || ChannelDetails.instance != null)
{
- Console.WriteLine("&PlaylistTrack back");
- for (int i = 0; i < SupportFragmentManager.BackStackEntryCount; i++)
- {
- Console.WriteLine("&Back stack entry " + i + ": " + SupportFragmentManager.GetBackStackEntryAt(i));
- }
+ //for (int i = 0; i < SupportFragmentManager.BackStackEntryCount; i++)
+ //{
+ // Console.WriteLine("&Back stack entry " + i + ": " + SupportFragmentManager.GetBackStackEntryAt(i));
+ //}
SupportFragmentManager.PopBackStack();
}
diff --git a/Opus/Code/UI/Adapter/HomeListAdapter.cs b/Opus/Code/UI/Adapter/HomeListAdapter.cs
index 49734ab..25be72e 100644
--- a/Opus/Code/UI/Adapter/HomeListAdapter.cs
+++ b/Opus/Code/UI/Adapter/HomeListAdapter.cs
@@ -13,59 +13,86 @@ using System.Collections.Generic;
namespace Opus.Adapter
{
- public class HomeListAdapter : RecyclerView.Adapter
+ public class SmallListAdapter : RecyclerView.Adapter
{
public RecyclerView recycler;
- public int listPadding = 0;
- public List channels;
+ public List channels;
public List playlists;
- public List allItems;
private readonly bool UseChannel;
public bool expanded = false;
- public override int ItemCount => UseChannel ? (expanded ? (channels.Count > 3 ? 3 : channels.Count) : channels.Count) :
- expanded ? (playlists.Count > 3 ? 3 : playlists.Count) : playlists.Count;
+ public override int ItemCount
+ {
+ get
+ {
+ if ((UseChannel && channels == null) || (!UseChannel && playlists == null))
+ return 1;
- public HomeListAdapter(List channels, RecyclerView recycler)
+ return UseChannel? (expanded? (channels.Count > 3 ? 3 : channels.Count) : channels.Count) :
+ expanded? (playlists.Count > 3 ? 3 : playlists.Count) : playlists.Count;
+ }
+ }
+
+ public SmallListAdapter(List channels, RecyclerView recycler)
{
this.recycler = recycler;
this.channels = channels;
UseChannel = true;
}
- public HomeListAdapter(List playlists, RecyclerView recycler)
+ public SmallListAdapter(List playlists, RecyclerView recycler)
{
this.recycler = recycler;
this.playlists = playlists;
UseChannel = false;
}
+ public SmallListAdapter(bool UseChannel, RecyclerView recycler)
+ {
+ this.recycler = recycler;
+ this.UseChannel = UseChannel;
+ }
+
public override void OnBindViewHolder(RecyclerView.ViewHolder viewHolder, int position)
{
- SongHolder holder = (SongHolder)viewHolder;
-
- if(UseChannel)
+ if (position == 0 && ((UseChannel && channels == null) || (!UseChannel && playlists == null)))
{
- holder.Title.Text = channels[position].Title;
- Picasso.With(Application.Context).Load(channels[position].Album).Placeholder(Resource.Color.background_material_dark).Transform(new CircleTransformation()).Into(holder.AlbumArt);
- holder.ItemView.SetPadding(4, 1, 4, 1);
+ EmptyHolder holder = (EmptyHolder)viewHolder;
+ holder.text.Text = MainActivity.instance.GetString(Resource.String.long_loading);
+ holder.text.SetHeight(MainActivity.instance.DpToPx(157));
}
else
{
- holder.Title.Text = playlists[position].Name;
- Picasso.With(Application.Context).Load(playlists[position].ImageURL).Placeholder(Resource.Color.background_material_dark).Resize(400, 400).CenterCrop().Into(holder.AlbumArt);
- if(!holder.RightButtons.FindViewById(Resource.Id.play).HasOnClickListeners)
+ SongHolder holder = (SongHolder)viewHolder;
+
+ if (UseChannel)
{
- //Only support local playlists for now.
- holder.RightButtons.FindViewById(Resource.Id.play).Click += (sender, e) => { PlaylistManager.PlayInOrder(playlists[position]); };
- holder.RightButtons.FindViewById(Resource.Id.shuffle).Click += (sender, e) => { PlaylistManager.Shuffle(playlists[position]); };
+ holder.Title.Text = channels[position].Name;
+ Picasso.With(Application.Context).Load(channels[position].ImageURL).Placeholder(Resource.Color.background_material_dark).Transform(new CircleTransformation()).Into(holder.AlbumArt);
+ holder.ItemView.SetPadding(4, 1, 4, 1);
+ }
+ else
+ {
+ holder.Title.Text = playlists[position].Name;
+ Picasso.With(Application.Context).Load(playlists[position].ImageURL).Placeholder(Resource.Color.background_material_dark).Resize(400, 400).CenterCrop().Into(holder.AlbumArt);
+ if (!holder.RightButtons.FindViewById(Resource.Id.play).HasOnClickListeners)
+ {
+ //Only support local playlists for now.
+ holder.RightButtons.FindViewById(Resource.Id.play).Click += (sender, e) => { PlaylistManager.PlayInOrder(playlists[position]); };
+ holder.RightButtons.FindViewById(Resource.Id.shuffle).Click += (sender, e) => { PlaylistManager.Shuffle(playlists[position]); };
+ }
}
}
}
public override RecyclerView.ViewHolder OnCreateViewHolder(ViewGroup parent, int viewType)
{
- if(UseChannel)
+ if ((UseChannel && channels == null) || (!UseChannel && playlists == null))
+ {
+ View itemView = LayoutInflater.From(parent.Context).Inflate(Resource.Layout.EmptyView, parent, false);
+ return new EmptyHolder(itemView);
+ }
+ else if (UseChannel)
{
View itemView = LayoutInflater.From(parent.Context).Inflate(Resource.Layout.HomeChannel, parent, false);
return new SongHolder(itemView, OnClick, OnLongClick);
@@ -80,15 +107,9 @@ namespace Opus.Adapter
void OnClick(int position)
{
if(UseChannel)
- {
- //Open a channel view
- }
+ MainActivity.instance.SupportFragmentManager.BeginTransaction().Replace(Resource.Id.contentView, ChannelDetails.NewInstance(channels[position])).AddToBackStack("Channel Details").Commit();
else
- {
- MainActivity.instance.contentRefresh.Refresh -= Home.instance.OnRefresh;
- Home.instance = null;
MainActivity.instance.SupportFragmentManager.BeginTransaction().Replace(Resource.Id.contentView, PlaylistTracks.NewInstance(playlists[position])).AddToBackStack("Playlist Track").Commit();
- }
}
void OnLongClick(int position) { }
diff --git a/Opus/Code/UI/Adapter/LineAdapter.cs b/Opus/Code/UI/Adapter/LineAdapter.cs
index c981cf1..c1837ba 100644
--- a/Opus/Code/UI/Adapter/LineAdapter.cs
+++ b/Opus/Code/UI/Adapter/LineAdapter.cs
@@ -59,7 +59,7 @@ namespace Opus.Adapter
if (position == 0 && isEmpty)
{
EmptyHolder holder = (EmptyHolder)viewHolder;
- holder.text.Text = "No song currently in queue,\nstart playing song now !";
+ holder.text.Text = UseQueue ? MainActivity.instance.GetString(Resource.String.empty_queue) : MainActivity.instance.GetString(Resource.String.long_loading);
holder.text.SetHeight(MainActivity.instance.DpToPx(157));
return;
}
diff --git a/Opus/Code/UI/Adapter/QueueAdapter.cs b/Opus/Code/UI/Adapter/QueueAdapter.cs
index f790499..c5ddfab 100644
--- a/Opus/Code/UI/Adapter/QueueAdapter.cs
+++ b/Opus/Code/UI/Adapter/QueueAdapter.cs
@@ -7,8 +7,8 @@ using Android.Text;
using Android.Text.Style;
using Android.Views;
using Android.Widget;
+using Opus.Api;
using Opus.Api.Services;
-using Opus.Code.Api;
using Opus.DataStructure;
using Opus.Others;
using Square.Picasso;
diff --git a/Opus/Code/UI/Adapter/SectionAdapter.cs b/Opus/Code/UI/Adapter/SectionAdapter.cs
index 55579c0..86f3118 100644
--- a/Opus/Code/UI/Adapter/SectionAdapter.cs
+++ b/Opus/Code/UI/Adapter/SectionAdapter.cs
@@ -70,10 +70,10 @@ namespace Opus.Adapter
MainActivity.instance.ShowPlayer();
Player.instance.ShowQueue();
};
- if(MusicPlayer.CurrentID() != -1 && MusicPlayer.CurrentID() <= MusicPlayer.queue.Count)
+ if (MusicPlayer.CurrentID() != -1 && MusicPlayer.CurrentID() <= MusicPlayer.queue.Count)
holder.recycler.ScrollToPosition(MusicPlayer.CurrentID());
}
- else if(items[position].SectionTitle == null)
+ else if (items[position].SectionTitle == null)
{
//The playlist is loading
holder.recycler.SetAdapter(new LineAdapter(new List(), holder.recycler));
@@ -85,65 +85,109 @@ namespace Opus.Adapter
holder.more.Click += (sender, e) =>
{
position = holder.AdapterPosition;
- //MainActivity.instance.contentRefresh.Refresh -= Home.instance.OnRefresh;
- //Home.instance = null;
- MainActivity.instance.SupportFragmentManager.BeginTransaction().Replace(Resource.Id.contentView, PlaylistTracks.NewInstance(items[position].contentValue, items[position].SectionTitle)).AddToBackStack(null).Commit();
+ if (items[position].playlist == null)
+ MainActivity.instance.SupportFragmentManager.BeginTransaction().Replace(Resource.Id.contentView, PlaylistTracks.NewInstance(items[position].contentValue, items[position].SectionTitle)).AddToBackStack(null).Commit();
+ else
+ MainActivity.instance.SupportFragmentManager.BeginTransaction().Replace(Resource.Id.contentView, PlaylistTracks.NewInstance(items[position].playlist)).AddToBackStack(null).Commit();
};
}
}
- else if(items[position].contentType == SectionType.ChannelList)
+ else if (items[position].contentType == SectionType.ChannelList)
{
LineSongHolder holder = (LineSongHolder)viewHolder;
items[position].recycler = holder.recycler;
holder.title.Text = items[position].SectionTitle;
holder.recycler.SetLayoutManager(new LinearLayoutManager(MainActivity.instance, LinearLayoutManager.Vertical, false));
- holder.recycler.SetAdapter(new HomeListAdapter(items[position].contentValue.GetRange(0, items[position].contentValue.Count > 4 ? 4 : items[position].contentValue.Count), holder.recycler) { allItems = items[position].contentValue.GetRange(4, items[position].contentValue.Count - 4) });
- ((GradientDrawable)holder.more.Background).SetStroke(5, Android.Content.Res.ColorStateList.ValueOf(Color.Argb(255, 21, 183, 237)));
- holder.more.SetTextColor(Color.Argb(255, 21, 183, 237));
- holder.more.Text = ((HomeListAdapter)holder.recycler.GetAdapter()).channels.Count > 4 ? "View Less" : "View More";
- holder.more.Click += (sender, e) =>
+ if(items[position].channelContent != null)
{
- HomeListAdapter adapter = (HomeListAdapter)holder.recycler.GetAdapter();
- if(adapter.ItemCount == 4)
+ holder.recycler.SetAdapter(new SmallListAdapter(items[position].channelContent.GetRange(0, items[position].channelContent.Count > 4 ? 4 : items[position].channelContent.Count), holder.recycler));
+
+ if (items[position].channelContent.Count > 4)
{
- adapter.channels.AddRange(items[position].contentValue.GetRange(4, items[position].contentValue.Count - 4));
- adapter.NotifyItemRangeInserted(4, items[position].contentValue.Count - 4);
- holder.more.Text = "View Less";
+ holder.more.Visibility = ViewStates.Visible;
+ ((GradientDrawable)holder.more.Background).SetStroke(5, Android.Content.Res.ColorStateList.ValueOf(Color.Argb(255, 21, 183, 237)));
+ holder.more.SetTextColor(Color.Argb(255, 21, 183, 237));
+ holder.more.Text = ((SmallListAdapter)holder.recycler.GetAdapter()).channels.Count > 4 ? MainActivity.instance.GetString(Resource.String.view_less) : MainActivity.instance.GetString(Resource.String.view_more);
+ holder.more.Click += (sender, e) =>
+ {
+ SmallListAdapter adapter = (SmallListAdapter)holder.recycler.GetAdapter();
+ if (adapter.ItemCount == 4)
+ {
+ adapter.channels.AddRange(items[position].channelContent.GetRange(4, items[position].channelContent.Count - 4));
+ adapter.NotifyItemRangeInserted(4, items[position].channelContent.Count - 4);
+ holder.more.Text = MainActivity.instance.GetString(Resource.String.view_less);
+ }
+ else
+ {
+ int count = adapter.channels.Count - 4;
+ adapter.channels.RemoveRange(4, count);
+ adapter.NotifyItemRangeRemoved(4, count);
+ holder.more.Text = MainActivity.instance.GetString(Resource.String.view_more);
+ }
+ };
}
else
- {
- int count = adapter.channels.Count - 4;
- adapter.channels.RemoveRange(4, count);
- adapter.NotifyItemRangeRemoved(4, count);
- holder.more.Text = "View More";
- }
- };
+ holder.more.Visibility = ViewStates.Gone;
+ }
+ else
+ {
+ holder.recycler.SetAdapter(new SmallListAdapter(false, holder.recycler));
+ }
+
}
else if (items[position].contentType == SectionType.PlaylistList)
{
LineSongHolder holder = (LineSongHolder)viewHolder;
+ items[position].recycler = holder.recycler;
holder.title.Text = items[position].SectionTitle;
holder.recycler.SetLayoutManager(new LinearLayoutManager(MainActivity.instance, LinearLayoutManager.Vertical, false));
- holder.recycler.SetAdapter(new HomeListAdapter(items[position].playlistContent.GetRange(0, items[position].playlistContent.Count > 4 ? 4 : items[position].playlistContent.Count), holder.recycler));
- holder.more.Click += (sender, e) => { MainActivity.instance.FindViewById(Resource.Id.bottomView).SelectedItemId = Resource.Id.playlistLayout; };
+ if (items[position].playlistContent != null)
+ {
+ holder.recycler.SetAdapter(new SmallListAdapter(items[position].playlistContent.GetRange(0, items[position].playlistContent.Count > 4 ? 4 : items[position].playlistContent.Count), holder.recycler));
+
+ if (ChannelDetails.instance != null)
+ {
+ if (items[position].playlistContent.Count > 4)
+ {
+ holder.more.Visibility = ViewStates.Visible;
+ ((GradientDrawable)holder.more.Background).SetStroke(5, Android.Content.Res.ColorStateList.ValueOf(Color.Argb(255, 21, 183, 237)));
+ holder.more.SetTextColor(Color.Argb(255, 21, 183, 237));
+ holder.more.Text = ((SmallListAdapter)holder.recycler.GetAdapter()).playlists.Count > 4 ? MainActivity.instance.GetString(Resource.String.view_less) : MainActivity.instance.GetString(Resource.String.view_more);
+ holder.more.Click += (sender, e) =>
+ {
+ SmallListAdapter adapter = (SmallListAdapter)holder.recycler.GetAdapter();
+ if (adapter.ItemCount == 4)
+ {
+ adapter.playlists.AddRange(items[position].playlistContent.GetRange(4, items[position].playlistContent.Count - 4));
+ adapter.NotifyItemRangeInserted(4, items[position].playlistContent.Count - 4);
+ holder.more.Text = MainActivity.instance.GetString(Resource.String.view_less);
+ }
+ else
+ {
+ int count = adapter.playlists.Count - 4;
+ adapter.playlists.RemoveRange(4, count);
+ adapter.NotifyItemRangeRemoved(4, count);
+ holder.more.Text = MainActivity.instance.GetString(Resource.String.view_more);
+ }
+ };
+ }
+ else
+ holder.more.Visibility = ViewStates.Gone;
+ }
+ else
+ {
+ holder.more.Click += (sender, e) => { MainActivity.instance.FindViewById(Resource.Id.bottomView).SelectedItemId = Resource.Id.playlistLayout; };
+ holder.more.Visibility = ViewStates.Visible;
+ }
+ }
+ else
+ {
+ holder.recycler.SetAdapter(new SmallListAdapter(true, holder.recycler));
+ holder.more.Visibility = ViewStates.Gone;
+ }
}
- //else if(items[position].contentType == SectionType.TopicSelector)
- //{
- // LineSongHolder holder = (LineSongHolder)viewHolder;
- // items[position].recycler = holder.recycler;
-
- // holder.title.Text = items[position].SectionTitle;
- // holder.recycler.SetLayoutManager(new LinearLayoutManager(MainActivity.instance, LinearLayoutManager.Vertical, false));
- // holder.recycler.SetAdapter(new HomeListAdapter(items[position].contentValue));
- // holder.more.Click += (sender, e) =>
- // {
- // Intent intent = new Intent(MainActivity.instance, typeof(Preferences));
- // MainActivity.instance.StartActivity(intent);
- // };
-
- //}
}
void OnClick(int position)
@@ -173,7 +217,11 @@ namespace Opus.Adapter
else if (items[position].contentType == SectionType.ChannelList)
return 1;
else if (items[position].contentType == SectionType.PlaylistList)
+ {
+ if (ChannelDetails.instance != null)
+ return 1; //We want to display the playlists with the same view as the channels for this fragment.
return 2;
+ }
else
return 4;
}
diff --git a/Opus/Code/UI/Fragments/ChannelDetails.cs b/Opus/Code/UI/Fragments/ChannelDetails.cs
index d4602a0..96ae6fc 100644
--- a/Opus/Code/UI/Fragments/ChannelDetails.cs
+++ b/Opus/Code/UI/Fragments/ChannelDetails.cs
@@ -1,39 +1,32 @@
-using Android.Content;
-using Android.Database;
-using Android.Net;
-using Android.OS;
+using Android.OS;
using Android.Support.Design.Widget;
using Android.Support.V4.App;
using Android.Views;
using Android.Widget;
-using Java.Lang;
using Opus.Adapter;
using Opus.Api;
using Opus.DataStructure;
using Opus.Others;
using Square.Picasso;
using System.Collections.Generic;
+using System.Linq;
using System.Threading.Tasks;
using YoutubeExplode;
-using static Android.Provider.MediaStore.Audio;
-using CursorLoader = Android.Support.V4.Content.CursorLoader;
using PlaylistItem = Opus.DataStructure.PlaylistItem;
-using PopupMenu = Android.Support.V7.Widget.PopupMenu;
using RecyclerView = Android.Support.V7.Widget.RecyclerView;
using SearchView = Android.Support.V7.Widget.SearchView;
using Toolbar = Android.Support.V7.Widget.Toolbar;
namespace Opus.Fragments
{
- public class ChannelDetails : Fragment, /*PopupMenu.IOnMenuItemClickListener,*/ AppBarLayout.IOnOffsetChangedListener
+ public class ChannelDetails : Fragment, AppBarLayout.IOnOffsetChangedListener
{
public static ChannelDetails instance;
private Channel item;
- private TextView EmptyView;
private RecyclerView ListView;
private SectionAdapter adapter;
- private List sections = new List();
+ private readonly List sections = new List();
public override void OnActivityCreated(Bundle savedInstanceState)
{
@@ -83,7 +76,6 @@ namespace Opus.Fragments
public override void OnDestroyView()
{
- //MainActivity.instance.RemoveFilterListener(Search);
if (!MainActivity.instance.Paused)
{
Activity.FindViewById(Resource.Id.playlistButtons).Visibility = ViewStates.Visible;
@@ -92,8 +84,8 @@ namespace Opus.Fragments
MainActivity.instance.HideSearch();
MainActivity.instance.SupportActionBar.SetHomeButtonEnabled(false);
MainActivity.instance.SupportActionBar.SetDisplayHomeAsUpEnabled(false);
- MainActivity.instance.SupportActionBar.SetDisplayShowTitleEnabled(true);
MainActivity.instance.SupportActionBar.SetDisplayShowTitleEnabled(false);
+ MainActivity.instance.FindViewById(Resource.Id.toolbarLogo).Visibility = ViewStates.Visible;
MainActivity.instance.contentRefresh.Refresh -= OnRefresh;
Activity.FindViewById(Resource.Id.appbar).RemoveOnOffsetChangedListener(this);
@@ -139,18 +131,23 @@ namespace Opus.Fragments
for (int i = 0; i < response.Items.Count; i++)
{
- if (response.Items[i].ContentDetails?.Playlists.Count == 1)
+ if (response.Items[i].ContentDetails?.Playlists?.Count == 1)
{
- System.Console.WriteLine("&Single playlsit");
sections.Add(new Section(null, SectionType.SinglePlaylist));
LoadPlaylist(sections.Count - 1, response.Items[i].ContentDetails.Playlists[0]);
}
- //else if (item.ContentDetails.Playlists.Count > 1)
- // sections.Add(new Section(item.Snippet.Title, SectionType.PlaylistList, new List()));
+ else if (response.Items[i].ContentDetails?.Playlists?.Count > 1)
+ {
+ sections.Add(new Section(response.Items[i].Snippet.Title, SectionType.PlaylistList));
+ LoadMulitplePlaylists(sections.Count - 1, response.Items[i].ContentDetails.Playlists);
+ }
- //else if (item.ContentDetails.Channels.Count > 1)
- // sections.Add(new Section(item.Snippet.Title, SectionType.ChannelList, new List()));
+ else if (response.Items[i].ContentDetails?.Channels?.Count > 1)
+ {
+ sections.Add(new Section(response.Items[i].Snippet.Title, SectionType.ChannelList));
+ LoadChannels(sections.Count - 1, response.Items[i].ContentDetails.Channels);
+ }
}
adapter = new SectionAdapter(sections);
@@ -161,9 +158,28 @@ namespace Opus.Fragments
async void LoadPlaylist(int slot, string playlistID)
{
- System.Console.WriteLine("&Loading playlist: " + playlistID + " slot: " + slot + " sections count " + sections.Count);
var pl = await new YoutubeClient().GetPlaylistAsync(playlistID, 1);
- sections[slot] = new Section(pl.Title, SectionType.SinglePlaylist, Song.FromVideoArray(pl.Videos));
+ sections[slot] = new Section(pl.Title, SectionType.SinglePlaylist, Song.FromVideoArray(pl.Videos), new PlaylistItem(pl.Title, -1, playlistID) { HasWritePermission = false, Owner = item.Name });
+ adapter.NotifyItemChanged(slot);
+ }
+
+ async void LoadMulitplePlaylists(int slot, IList playlistIDs)
+ {
+ List playlists = new List();
+ foreach (string playlistID in playlistIDs)
+ {
+ PlaylistItem playlist = await PlaylistManager.GetPlaylist(playlistID);
+ if(playlist != null)
+ playlists.Add(playlist);
+ }
+ sections[slot] = new Section(sections[slot].SectionTitle, SectionType.PlaylistList, playlists);
+ adapter.NotifyItemChanged(slot);
+ }
+
+ async void LoadChannels(int slot, IList channelIDs)
+ {
+ IEnumerable channels = await ChannelManager.GetChannels(channelIDs);
+ sections[slot] = new Section(sections[slot].SectionTitle, SectionType.ChannelList, channels.ToList());
adapter.NotifyItemChanged(slot);
}
@@ -173,122 +189,10 @@ namespace Opus.Fragments
MainActivity.instance.contentRefresh.Refreshing = false;
}
- //public void Search(object sender, SearchView.QueryTextChangeEventArgs e)
- //{
- // if (e.NewText == "")
- // query = null;
- // else
- // query = e.NewText.ToLower();
-
- // if (item.LocalID != -1)
- // LoaderManager.GetInstance(this).RestartLoader(0, null, this);
- // else
- // {
- // if (query == null)
- // adapter.tracks.SetFilter(x => true);
- // else
- // adapter.tracks.SetFilter(x => x.Title.ToLower().Contains(query) || x.Artist.ToLower().Contains(query));
-
- // adapter.NotifyDataSetChanged();
- // }
- //}
-
- public void More(Song song, int position)
- {
- //BottomSheetDialog bottomSheet = new BottomSheetDialog(MainActivity.instance);
- //View bottomView = LayoutInflater.Inflate(Resource.Layout.BottomSheet, null);
- //bottomView.FindViewById(Resource.Id.bsTitle).Text = song.Title;
- //bottomView.FindViewById(Resource.Id.bsArtist).Text = song.Artist;
- //if (song.AlbumArt == -1 || song.IsYt)
- //{
- // Picasso.With(MainActivity.instance).Load(song.Album).Placeholder(Resource.Drawable.noAlbum).Transform(new RemoveBlackBorder(true)).Into(bottomView.FindViewById(Resource.Id.bsArt));
- //}
- //else
- //{
- // var songCover = Uri.Parse("content://media/external/audio/albumart");
- // var songAlbumArtUri = ContentUris.WithAppendedId(songCover, song.AlbumArt);
-
- // Picasso.With(MainActivity.instance).Load(songAlbumArtUri).Placeholder(Resource.Drawable.noAlbum).Resize(400, 400).CenterCrop().Into(bottomView.FindViewById(Resource.Id.bsArt));
- //}
- //bottomSheet.SetContentView(bottomView);
-
- //List actions = new List
- //{
- // new BottomSheetAction(Resource.Drawable.Play, Resources.GetString(Resource.String.play), (sender, eventArg) =>
- // {
- // if(useHeader)
- // PlaylistManager.PlayInOrder(item, position);
- // else
- // SongManager.Play(song);
- // bottomSheet.Dismiss();
- // }),
- // new BottomSheetAction(Resource.Drawable.PlaylistPlay, Resources.GetString(Resource.String.play_next), (sender, eventArg) =>
- // {
- // SongManager.PlayNext(song);
- // bottomSheet.Dismiss();
- // }),
- // new BottomSheetAction(Resource.Drawable.Queue, Resources.GetString(Resource.String.play_last), (sender, eventArg) =>
- // {
- // SongManager.PlayLast(song);
- // bottomSheet.Dismiss();
- // }),
- // new BottomSheetAction(Resource.Drawable.PlaylistAdd, Resources.GetString(Resource.String.add_to_playlist), (sender, eventArg) =>
- // {
- // PlaylistManager.AddSongToPlaylistDialog(song);
- // bottomSheet.Dismiss();
- // })
- //};
-
- //if (item.HasWritePermission)
- //{
- // actions.Add(new BottomSheetAction(Resource.Drawable.Close, Resources.GetString(Resource.String.remove_track_from_playlist), (sender, eventArg) =>
- // {
- // RemoveFromPlaylist(song, position);
- // bottomSheet.Dismiss();
- // }));
- //}
-
- //if (!song.IsYt)
- //{
- // actions.Add(new BottomSheetAction(Resource.Drawable.Edit, Resources.GetString(Resource.String.edit_metadata), (sender, eventArg) =>
- // {
- // LocalManager.EditMetadata(song);
- // bottomSheet.Dismiss();
- // }));
- //}
- //else
- //{
- // actions.AddRange(new BottomSheetAction[]
- // {
- // new BottomSheetAction(Resource.Drawable.PlayCircle, Resources.GetString(Resource.String.create_mix_from_song), (sender, eventArg) =>
- // {
- // YoutubeManager.CreateMixFromSong(song);
- // bottomSheet.Dismiss();
- // }),
- // new BottomSheetAction(Resource.Drawable.Download, Resources.GetString(Resource.String.download), (sender, eventArg) =>
- // {
- // YoutubeManager.Download(new[] { song });
- // bottomSheet.Dismiss();
- // })
- // });
- //}
-
- //bottomSheet.FindViewById(Resource.Id.bsItems).Adapter = new BottomSheetAdapter(MainActivity.instance, Resource.Layout.BottomSheetText, actions);
- //bottomSheet.Show();
- }
-
-
public override void OnResume()
{
base.OnResume();
instance = this;
-
- //if (!Activity.FindViewById(Resource.Id.headerPlay).HasOnClickListeners)
- // Activity.FindViewById(Resource.Id.headerPlay).Click += (sender, e0) => { PlaylistManager.PlayInOrder(item); };
- //if (!Activity.FindViewById(Resource.Id.headerShuffle).HasOnClickListeners)
- // Activity.FindViewById(Resource.Id.headerShuffle).Click += (sender, e0) => { PlaylistManager.Shuffle(item); };
- //if (!Activity.FindViewById(Resource.Id.headerMore).HasOnClickListeners)
- // Activity.FindViewById(Resource.Id.headerMore).Click += PlaylistMore;
}
public void OnOffsetChanged(AppBarLayout appBarLayout, int verticalOffset)
@@ -307,11 +211,5 @@ namespace Opus.Fragments
MainActivity.instance.SupportActionBar.SetDisplayShowTitleEnabled(true);
}
}
-
- public override void OnDestroy()
- {
- base.OnDestroy();
- MainActivity.instance.FindViewById(Resource.Id.toolbarLogo).Visibility = ViewStates.Visible;
- }
}
}
diff --git a/Opus/Code/UI/Fragments/PlaylistTracks.cs b/Opus/Code/UI/Fragments/PlaylistTracks.cs
index b8e6253..d44f159 100644
--- a/Opus/Code/UI/Fragments/PlaylistTracks.cs
+++ b/Opus/Code/UI/Fragments/PlaylistTracks.cs
@@ -113,7 +113,8 @@ namespace Opus.Fragments
if (item.Count == -1)
Activity.FindViewById(Resource.Id.headerNumber).Text = "NaN" + " " + GetString(Resource.String.songs);
- Picasso.With(Android.App.Application.Context).Load(item.ImageURL).Placeholder(Resource.Drawable.noAlbum).Transform(new RemoveBlackBorder(true)).Into(Activity.FindViewById(Resource.Id.headerArt));
+ if(item.ImageURL != null)
+ Picasso.With(Android.App.Application.Context).Load(item.ImageURL).Placeholder(Resource.Drawable.noAlbum).Transform(new RemoveBlackBorder(true)).Into(Activity.FindViewById(Resource.Id.headerArt));
}
Activity.FindViewById(Resource.Id.collapsingToolbar).RequestLayout();
}
@@ -147,8 +148,8 @@ namespace Opus.Fragments
MainActivity.instance.HideSearch();
MainActivity.instance.SupportActionBar.SetHomeButtonEnabled(false);
MainActivity.instance.SupportActionBar.SetDisplayHomeAsUpEnabled(false);
- MainActivity.instance.SupportActionBar.SetDisplayShowTitleEnabled(true);
MainActivity.instance.SupportActionBar.SetDisplayShowTitleEnabled(false);
+ MainActivity.instance.FindViewById(Resource.Id.toolbarLogo).Visibility = ViewStates.Visible;
MainActivity.instance.contentRefresh.Refresh -= OnRefresh;
Activity.FindViewById(Resource.Id.appbar).RemoveOnOffsetChangedListener(this);
@@ -342,6 +343,9 @@ namespace Opus.Fragments
tracks.Invalidate();
adapter.NotifyDataSetChanged();
+ if(item?.ImageURL == null)
+ Picasso.With(Android.App.Application.Context).Load(tracks[0].Album).Placeholder(Resource.Drawable.noAlbum).Transform(new RemoveBlackBorder(true)).Into(Activity.FindViewById(Resource.Id.headerArt));
+
}
catch (System.Net.Http.HttpRequestException) { }
}
@@ -604,11 +608,5 @@ namespace Opus.Fragments
MainActivity.instance.SupportActionBar.SetDisplayShowTitleEnabled(true);
}
}
-
- public override void OnDestroy()
- {
- base.OnDestroy();
- MainActivity.instance.FindViewById(Resource.Id.toolbarLogo).Visibility = ViewStates.Visible;
- }
}
}
diff --git a/Opus/Code/UI/Fragments/Queue.cs b/Opus/Code/UI/Fragments/Queue.cs
index 25c26ea..a198154 100644
--- a/Opus/Code/UI/Fragments/Queue.cs
+++ b/Opus/Code/UI/Fragments/Queue.cs
@@ -15,7 +15,6 @@ using Opus;
using Opus.Adapter;
using Opus.Api;
using Opus.Api.Services;
-using Opus.Code.Api;
using Opus.DataStructure;
using Opus.Others;
using Opus.Views;
@@ -111,7 +110,8 @@ public class Queue : Fragment, RecyclerView.IOnItemTouchListener, PopupMenu.IOnM
int last = ((LinearLayoutManager)ListView.GetLayoutManager()).FindLastVisibleItemPosition();
for (int i = first; i <= last; i++)
{
- if (ListView.GetChildViewHolder(((LinearLayoutManager)ListView.GetLayoutManager()).FindViewByPosition(i)) is SongHolder holder)
+ View child = ((LinearLayoutManager)ListView.GetLayoutManager()).FindViewByPosition(i);
+ if (child != null && ListView.GetChildViewHolder(child) is SongHolder holder)
{
if (MusicPlayer.CurrentID() == i - 1) //The -1 is because the first displayed item of the queue is a header.
{
diff --git a/Opus/Code/UI/Fragments/YoutubeSearch.cs b/Opus/Code/UI/Fragments/YoutubeSearch.cs
index 747ceaf..2c1c655 100644
--- a/Opus/Code/UI/Fragments/YoutubeSearch.cs
+++ b/Opus/Code/UI/Fragments/YoutubeSearch.cs
@@ -295,6 +295,8 @@ namespace Opus.Fragments
Console.WriteLine("&Exception catched in the youtube search: " + ex.Source + " - " + ex.Message);
EmptyView.Text = GetString(Resource.String.timout);
EmptyView.Visibility = ViewStates.Visible;
+ EmptyView.Visibility = ViewStates.Visible;
+ LoadingView.Visibility = ViewStates.Gone;
}
}
diff --git a/Opus/Opus.csproj b/Opus/Opus.csproj
index c4b4666..979b396 100644
--- a/Opus/Opus.csproj
+++ b/Opus/Opus.csproj
@@ -324,6 +324,7 @@
+
diff --git a/Opus/Resources/Resource.Designer.cs b/Opus/Resources/Resource.Designer.cs
index a2a525c..329e0a9 100644
--- a/Opus/Resources/Resource.Designer.cs
+++ b/Opus/Resources/Resource.Designer.cs
@@ -7183,14 +7183,14 @@ namespace Opus
// aapt resource value: 0x7f0d0072
public const int abc_toolbar_collapse_description = 2131558514;
- // aapt resource value: 0x7f0d0135
- public const int add = 2131558709;
+ // aapt resource value: 0x7f0d0139
+ public const int add = 2131558713;
- // aapt resource value: 0x7f0d00fb
- public const int add_playlist = 2131558651;
+ // aapt resource value: 0x7f0d00fc
+ public const int add_playlist = 2131558652;
- // aapt resource value: 0x7f0d010f
- public const int add_playlist_msg = 2131558671;
+ // aapt resource value: 0x7f0d0110
+ public const int add_playlist_msg = 2131558672;
// aapt resource value: 0x7f0d00df
public const int add_to_library = 2131558623;
@@ -7201,23 +7201,23 @@ namespace Opus
// aapt resource value: 0x7f0d00d9
public const int add_to_queue = 2131558617;
- // aapt resource value: 0x7f0d011c
- public const int album = 2131558684;
+ // aapt resource value: 0x7f0d0120
+ public const int album = 2131558688;
- // aapt resource value: 0x7f0d00e9
- public const int all = 2131558633;
+ // aapt resource value: 0x7f0d00ea
+ public const int all = 2131558634;
// aapt resource value: 0x7f0d0080
public const int appbar_scrolling_view_behavior = 2131558528;
- // aapt resource value: 0x7f0d013f
- public const int appearances = 2131558719;
+ // aapt resource value: 0x7f0d0143
+ public const int appearances = 2131558723;
- // aapt resource value: 0x7f0d0132
- public const int apply = 2131558706;
+ // aapt resource value: 0x7f0d0136
+ public const int apply = 2131558710;
- // aapt resource value: 0x7f0d011b
- public const int artist = 2131558683;
+ // aapt resource value: 0x7f0d011f
+ public const int artist = 2131558687;
// aapt resource value: 0x7f0d00ca
public const int autoplay = 2131558602;
@@ -7225,17 +7225,17 @@ namespace Opus
// aapt resource value: 0x7f0d00cb
public const int autoplay_desc = 2131558603;
- // aapt resource value: 0x7f0d0111
- public const int badplaylisturl = 2131558673;
+ // aapt resource value: 0x7f0d0112
+ public const int badplaylisturl = 2131558674;
- // aapt resource value: 0x7f0d0139
- public const int behavior = 2131558713;
+ // aapt resource value: 0x7f0d013d
+ public const int behavior = 2131558717;
- // aapt resource value: 0x7f0d0159
- public const int beta_available = 2131558745;
+ // aapt resource value: 0x7f0d015d
+ public const int beta_available = 2131558749;
- // aapt resource value: 0x7f0d0144
- public const int black_theme = 2131558724;
+ // aapt resource value: 0x7f0d0148
+ public const int black_theme = 2131558728;
// aapt resource value: 0x7f0d0081
public const int bottom_sheet_behavior = 2131558529;
@@ -7243,17 +7243,17 @@ namespace Opus
// aapt resource value: 0x7f0d00b2
public const int browse = 2131558578;
- // aapt resource value: 0x7f0d0133
- public const int cancel = 2131558707;
+ // aapt resource value: 0x7f0d0137
+ public const int cancel = 2131558711;
- // aapt resource value: 0x7f0d015f
- public const int cancelling = 2131558751;
+ // aapt resource value: 0x7f0d0163
+ public const int cancelling = 2131558755;
- // aapt resource value: 0x7f0d00f1
- public const int cant_delete = 2131558641;
+ // aapt resource value: 0x7f0d00f2
+ public const int cant_delete = 2131558642;
- // aapt resource value: 0x7f0d015c
- public const int cant_play_non_youtube = 2131558748;
+ // aapt resource value: 0x7f0d0160
+ public const int cant_play_non_youtube = 2131558752;
// aapt resource value: 0x7f0d00b7
public const int cast = 2131558583;
@@ -7336,11 +7336,11 @@ namespace Opus
// aapt resource value: 0x7f0d0015
public const int cast_play = 2131558421;
- // aapt resource value: 0x7f0d0130
- public const int cast_queue_push = 2131558704;
+ // aapt resource value: 0x7f0d0134
+ public const int cast_queue_push = 2131558708;
- // aapt resource value: 0x7f0d0131
- public const int cast_queue_pushed = 2131558705;
+ // aapt resource value: 0x7f0d0135
+ public const int cast_queue_pushed = 2131558709;
// aapt resource value: 0x7f0d0016
public const int cast_rewind = 2131558422;
@@ -7390,14 +7390,14 @@ namespace Opus
// aapt resource value: 0x7f0d0025
public const int cast_unmute = 2131558437;
- // aapt resource value: 0x7f0d011e
- public const int change_albumart = 2131558686;
+ // aapt resource value: 0x7f0d0122
+ public const int change_albumart = 2131558690;
- // aapt resource value: 0x7f0d0123
- public const int changes_saved = 2131558691;
+ // aapt resource value: 0x7f0d0127
+ public const int changes_saved = 2131558695;
- // aapt resource value: 0x7f0d00eb
- public const int channels = 2131558635;
+ // aapt resource value: 0x7f0d00ec
+ public const int channels = 2131558636;
// aapt resource value: 0x7f0d0082
public const int character_counter_content_description = 2131558530;
@@ -7405,8 +7405,8 @@ namespace Opus
// aapt resource value: 0x7f0d0083
public const int character_counter_pattern = 2131558531;
- // aapt resource value: 0x7f0d0146
- public const int check_updates = 2131558726;
+ // aapt resource value: 0x7f0d014a
+ public const int check_updates = 2131558730;
// aapt resource value: 0x7f0d002b
public const int common_google_play_services_enable_button = 2131558443;
@@ -7462,14 +7462,14 @@ namespace Opus
// aapt resource value: 0x7f0d003b
public const int common_signin_button_text_long = 2131558459;
- // aapt resource value: 0x7f0d012f
- public const int completed = 2131558703;
+ // aapt resource value: 0x7f0d0133
+ public const int completed = 2131558707;
- // aapt resource value: 0x7f0d0153
- public const int country_blocked = 2131558739;
+ // aapt resource value: 0x7f0d0157
+ public const int country_blocked = 2131558743;
- // aapt resource value: 0x7f0d0117
- public const int create_local = 2131558679;
+ // aapt resource value: 0x7f0d0118
+ public const int create_local = 2131558680;
// aapt resource value: 0x7f0d00cc
public const int create_mix = 2131558604;
@@ -7477,71 +7477,74 @@ namespace Opus
// aapt resource value: 0x7f0d00d0
public const int create_mix_from_song = 2131558608;
- // aapt resource value: 0x7f0d0113
- public const int create_playlist = 2131558675;
+ // aapt resource value: 0x7f0d0114
+ public const int create_playlist = 2131558676;
+
+ // aapt resource value: 0x7f0d011a
+ public const int create_synced = 2131558682;
// aapt resource value: 0x7f0d0119
- public const int create_synced = 2131558681;
+ public const int create_youtube = 2131558681;
- // aapt resource value: 0x7f0d0118
- public const int create_youtube = 2131558680;
-
- // aapt resource value: 0x7f0d0143
- public const int dark_theme = 2131558723;
+ // aapt resource value: 0x7f0d0147
+ public const int dark_theme = 2131558727;
// aapt resource value: 0x7f0d00db
public const int delete = 2131558619;
- // aapt resource value: 0x7f0d010b
- public const int delete_playlist = 2131558667;
+ // aapt resource value: 0x7f0d010c
+ public const int delete_playlist = 2131558668;
- // aapt resource value: 0x7f0d0129
- public const int deleted_file = 2131558697;
+ // aapt resource value: 0x7f0d012d
+ public const int deleted_file = 2131558701;
// aapt resource value: 0x7f0d00d3
public const int download = 2131558611;
- // aapt resource value: 0x7f0d0120
- public const int download_albumart = 2131558688;
+ // aapt resource value: 0x7f0d0124
+ public const int download_albumart = 2131558692;
- // aapt resource value: 0x7f0d013b
- public const int download_directory = 2131558715;
+ // aapt resource value: 0x7f0d013f
+ public const int download_directory = 2131558719;
- // aapt resource value: 0x7f0d0121
- public const int download_meta = 2131558689;
+ // aapt resource value: 0x7f0d0125
+ public const int download_meta = 2131558693;
+
+ // aapt resource value: 0x7f0d00ee
+ public const int download_path_error = 2131558638;
// aapt resource value: 0x7f0d00ed
- public const int download_path_error = 2131558637;
-
- // aapt resource value: 0x7f0d00ec
- public const int download_path_not_set = 2131558636;
-
- // aapt resource value: 0x7f0d0128
- public const int download_queue = 2131558696;
+ public const int download_path_not_set = 2131558637;
// aapt resource value: 0x7f0d012c
- public const int downloader_playlist = 2131558700;
+ public const int download_queue = 2131558700;
- // aapt resource value: 0x7f0d00ef
- public const int downloading = 2131558639;
+ // aapt resource value: 0x7f0d0130
+ public const int downloader_playlist = 2131558704;
- // aapt resource value: 0x7f0d015d
- public const int downloading_notification = 2131558749;
+ // aapt resource value: 0x7f0d00f0
+ public const int downloading = 2131558640;
- // aapt resource value: 0x7f0d012d
- public const int downloading_status = 2131558701;
+ // aapt resource value: 0x7f0d0161
+ public const int downloading_notification = 2131558753;
- // aapt resource value: 0x7f0d015a
- public const int downloading_update = 2131558746;
+ // aapt resource value: 0x7f0d0131
+ public const int downloading_status = 2131558705;
+
+ // aapt resource value: 0x7f0d015e
+ public const int downloading_update = 2131558750;
// aapt resource value: 0x7f0d00d2
public const int edit_metadata = 2131558610;
- // aapt resource value: 0x7f0d0101
- public const int element = 2131558657;
-
// aapt resource value: 0x7f0d0102
- public const int elements = 2131558658;
+ public const int element = 2131558658;
+
+ // aapt resource value: 0x7f0d0103
+ public const int elements = 2131558659;
+
+ // aapt resource value: 0x7f0d00e6
+ public const int empty_queue = 2131558630;
// aapt resource value: 0x7f0d0090
public const int exo_controls_fastforward_description = 2131558544;
@@ -7654,11 +7657,11 @@ namespace Opus
// aapt resource value: 0x7f0d00b6
public const int filter = 2131558582;
- // aapt resource value: 0x7f0d00e7
- public const int folders = 2131558631;
+ // aapt resource value: 0x7f0d00e8
+ public const int folders = 2131558632;
- // aapt resource value: 0x7f0d0127
- public const int format_unsupported = 2131558695;
+ // aapt resource value: 0x7f0d012b
+ public const int format_unsupported = 2131558699;
// aapt resource value: 0x7f0d0086
public const int hide_bottom_view_on_scroll_behavior = 2131558534;
@@ -7672,53 +7675,56 @@ namespace Opus
// aapt resource value: 0x7f0d00c2
public const int hours = 2131558594;
- // aapt resource value: 0x7f0d012a
- public const int initialization = 2131558698;
+ // aapt resource value: 0x7f0d012e
+ public const int initialization = 2131558702;
- // aapt resource value: 0x7f0d0136
- public const int later = 2131558710;
+ // aapt resource value: 0x7f0d013a
+ public const int later = 2131558714;
// aapt resource value: 0x7f0d00d6
public const int list_songs = 2131558614;
- // aapt resource value: 0x7f0d00ea
- public const int lives = 2131558634;
+ // aapt resource value: 0x7f0d00eb
+ public const int lives = 2131558635;
// aapt resource value: 0x7f0d00c7
public const int loading = 2131558599;
- // aapt resource value: 0x7f0d00fe
- public const int local_playlist_empty = 2131558654;
+ // aapt resource value: 0x7f0d00ff
+ public const int local_playlist_empty = 2131558655;
- // aapt resource value: 0x7f0d00f9
- public const int local_playlists = 2131558649;
+ // aapt resource value: 0x7f0d00fa
+ public const int local_playlists = 2131558650;
- // aapt resource value: 0x7f0d0100
- public const int localpl_noperm = 2131558656;
+ // aapt resource value: 0x7f0d0101
+ public const int localpl_noperm = 2131558657;
- // aapt resource value: 0x7f0d014a
- public const int log_in = 2131558730;
+ // aapt resource value: 0x7f0d014e
+ public const int log_in = 2131558734;
- // aapt resource value: 0x7f0d014b
- public const int log_out = 2131558731;
+ // aapt resource value: 0x7f0d014f
+ public const int log_out = 2131558735;
- // aapt resource value: 0x7f0d0149
- public const int logged_in = 2131558729;
+ // aapt resource value: 0x7f0d014d
+ public const int logged_in = 2131558733;
- // aapt resource value: 0x7f0d014c
- public const int login_disabled = 2131558732;
+ // aapt resource value: 0x7f0d0150
+ public const int login_disabled = 2131558736;
- // aapt resource value: 0x7f0d013c
- public const int max_download = 2131558716;
+ // aapt resource value: 0x7f0d011b
+ public const int long_loading = 2131558683;
- // aapt resource value: 0x7f0d013d
- public const int max_download_dialog = 2131558717;
+ // aapt resource value: 0x7f0d0140
+ public const int max_download = 2131558720;
- // aapt resource value: 0x7f0d012b
- public const int metadata = 2131558699;
+ // aapt resource value: 0x7f0d0141
+ public const int max_download_dialog = 2131558721;
- // aapt resource value: 0x7f0d0124
- public const int metdata_error_noid = 2131558692;
+ // aapt resource value: 0x7f0d012f
+ public const int metadata = 2131558703;
+
+ // aapt resource value: 0x7f0d0128
+ public const int metdata_error_noid = 2131558696;
// aapt resource value: 0x7f0d00bf
public const int minute = 2131558591;
@@ -7729,11 +7735,11 @@ namespace Opus
// aapt resource value: 0x7f0d00e3
public const int more = 2131558627;
- // aapt resource value: 0x7f0d0125
- public const int mount_error = 2131558693;
+ // aapt resource value: 0x7f0d0129
+ public const int mount_error = 2131558697;
- // aapt resource value: 0x7f0d0126
- public const int mount_error_action = 2131558694;
+ // aapt resource value: 0x7f0d012a
+ public const int mount_error_action = 2131558698;
// aapt resource value: 0x7f0d0040
public const int mr_button_content_description = 2131558464;
@@ -7810,44 +7816,44 @@ namespace Opus
// aapt resource value: 0x7f0d0087
public const int mtrl_chip_close_icon_content_description = 2131558535;
- // aapt resource value: 0x7f0d0116
- public const int new_playlist = 2131558678;
+ // aapt resource value: 0x7f0d0117
+ public const int new_playlist = 2131558679;
// aapt resource value: 0x7f0d00bc
public const int next_loading = 2131558588;
- // aapt resource value: 0x7f0d0138
- public const int no = 2131558712;
+ // aapt resource value: 0x7f0d013c
+ public const int no = 2131558716;
+
+ // aapt resource value: 0x7f0d00f7
+ public const int no_channel = 2131558647;
// aapt resource value: 0x7f0d00f6
- public const int no_channel = 2131558646;
+ public const int no_lives = 2131558646;
+
+ // aapt resource value: 0x7f0d0152
+ public const int no_permission = 2131558738;
// aapt resource value: 0x7f0d00f5
- public const int no_lives = 2131558645;
-
- // aapt resource value: 0x7f0d014e
- public const int no_permission = 2131558734;
-
- // aapt resource value: 0x7f0d00f4
- public const int no_playlist = 2131558644;
-
- // aapt resource value: 0x7f0d00f2
- public const int no_result = 2131558642;
-
- // aapt resource value: 0x7f0d00e8
- public const int no_song = 2131558632;
-
- // aapt resource value: 0x7f0d014f
- public const int no_song_mix = 2131558735;
+ public const int no_playlist = 2131558645;
// aapt resource value: 0x7f0d00f3
- public const int no_track = 2131558643;
+ public const int no_result = 2131558643;
- // aapt resource value: 0x7f0d0148
- public const int not_log = 2131558728;
+ // aapt resource value: 0x7f0d00e9
+ public const int no_song = 2131558633;
- // aapt resource value: 0x7f0d0154
- public const int not_streamable = 2131558740;
+ // aapt resource value: 0x7f0d0153
+ public const int no_song_mix = 2131558739;
+
+ // aapt resource value: 0x7f0d00f4
+ public const int no_track = 2131558644;
+
+ // aapt resource value: 0x7f0d014c
+ public const int not_log = 2131558732;
+
+ // aapt resource value: 0x7f0d0158
+ public const int not_streamable = 2131558744;
// aapt resource value: 0x7f0d00bb
public const int nothing = 2131558587;
@@ -7855,14 +7861,14 @@ namespace Opus
// aapt resource value: 0x7f0d00be
public const int off = 2131558590;
- // aapt resource value: 0x7f0d0134
- public const int ok = 2131558708;
+ // aapt resource value: 0x7f0d0138
+ public const int ok = 2131558712;
// aapt resource value: 0x7f0d00c4
public const int open_youtube = 2131558596;
- // aapt resource value: 0x7f0d0145
- public const int others = 2131558725;
+ // aapt resource value: 0x7f0d0149
+ public const int others = 2131558729;
// aapt resource value: 0x7f0d0088
public const int password_toggle_content_description = 2131558536;
@@ -7882,8 +7888,8 @@ namespace Opus
// aapt resource value: 0x7f0d00c6
public const int paused = 2131558598;
- // aapt resource value: 0x7f0d011f
- public const int pick_album_local = 2131558687;
+ // aapt resource value: 0x7f0d0123
+ public const int pick_album_local = 2131558691;
// aapt resource value: 0x7f0d00cd
public const int play = 2131558605;
@@ -7900,29 +7906,29 @@ namespace Opus
// aapt resource value: 0x7f0d00c5
public const int playing = 2131558597;
- // aapt resource value: 0x7f0d010a
- public const int playlist_add_song_not_found = 2131558666;
-
- // aapt resource value: 0x7f0d0107
- public const int playlist_already_saved = 2131558663;
-
- // aapt resource value: 0x7f0d0103
- public const int playlist_empty = 2131558659;
-
- // aapt resource value: 0x7f0d0110
- public const int playlist_fork = 2131558672;
-
- // aapt resource value: 0x7f0d0109
- public const int playlist_not_found = 2131558665;
-
- // aapt resource value: 0x7f0d0106
- public const int playlist_saved = 2131558662;
+ // aapt resource value: 0x7f0d010b
+ public const int playlist_add_song_not_found = 2131558667;
// aapt resource value: 0x7f0d0108
- public const int playlist_unsaved = 2131558664;
+ public const int playlist_already_saved = 2131558664;
- // aapt resource value: 0x7f0d0112
- public const int playlist_uptodate = 2131558674;
+ // aapt resource value: 0x7f0d0104
+ public const int playlist_empty = 2131558660;
+
+ // aapt resource value: 0x7f0d0111
+ public const int playlist_fork = 2131558673;
+
+ // aapt resource value: 0x7f0d010a
+ public const int playlist_not_found = 2131558666;
+
+ // aapt resource value: 0x7f0d0107
+ public const int playlist_saved = 2131558663;
+
+ // aapt resource value: 0x7f0d0109
+ public const int playlist_unsaved = 2131558665;
+
+ // aapt resource value: 0x7f0d0113
+ public const int playlist_uptodate = 2131558675;
// aapt resource value: 0x7f0d00b3
public const int playlists = 2131558579;
@@ -7933,23 +7939,23 @@ namespace Opus
// aapt resource value: 0x7f0d00d8
public const int random_play = 2131558616;
- // aapt resource value: 0x7f0d00f8
- public const int remove = 2131558648;
+ // aapt resource value: 0x7f0d00f9
+ public const int remove = 2131558649;
- // aapt resource value: 0x7f0d0104
- public const int remove_from_playlist = 2131558660;
+ // aapt resource value: 0x7f0d0105
+ public const int remove_from_playlist = 2131558661;
// aapt resource value: 0x7f0d00d4
public const int remove_from_queue = 2131558612;
- // aapt resource value: 0x7f0d00f7
- public const int remove_search = 2131558647;
+ // aapt resource value: 0x7f0d00f8
+ public const int remove_search = 2131558648;
// aapt resource value: 0x7f0d00d5
public const int remove_track_from_playlist = 2131558613;
- // aapt resource value: 0x7f0d0105
- public const int removed_from_playlist = 2131558661;
+ // aapt resource value: 0x7f0d0106
+ public const int removed_from_playlist = 2131558662;
// aapt resource value: 0x7f0d00c8
public const int removed_from_queue = 2131558600;
@@ -7957,8 +7963,8 @@ namespace Opus
// aapt resource value: 0x7f0d00da
public const int rename = 2131558618;
- // aapt resource value: 0x7f0d010c
- public const int rename_playlist = 2131558668;
+ // aapt resource value: 0x7f0d010d
+ public const int rename_playlist = 2131558669;
// aapt resource value: 0x7f0d00b4
public const int repeat = 2131558580;
@@ -7966,17 +7972,17 @@ namespace Opus
// aapt resource value: 0x7f0d00c9
public const int save_as_playlist = 2131558601;
- // aapt resource value: 0x7f0d0115
- public const int save_folder_playlist = 2131558677;
+ // aapt resource value: 0x7f0d0116
+ public const int save_folder_playlist = 2131558678;
- // aapt resource value: 0x7f0d0114
- public const int save_playlist = 2131558676;
+ // aapt resource value: 0x7f0d0115
+ public const int save_playlist = 2131558677;
// aapt resource value: 0x7f0d0073
public const int search_menu_title = 2131558515;
- // aapt resource value: 0x7f0d00ee
- public const int set_path = 2131558638;
+ // aapt resource value: 0x7f0d00ef
+ public const int set_path = 2131558639;
// aapt resource value: 0x7f0d00b8
public const int settings = 2131558584;
@@ -7993,8 +7999,8 @@ namespace Opus
// aapt resource value: 0x7f0d00bd
public const int sleep_timer = 2131558589;
- // aapt resource value: 0x7f0d00e6
- public const int songs = 2131558630;
+ // aapt resource value: 0x7f0d00e7
+ public const int songs = 2131558631;
// aapt resource value: 0x7f0d008d
public const int status_bar_notification_info_overflow = 2131558541;
@@ -8002,8 +8008,8 @@ namespace Opus
// aapt resource value: 0x7f0d00de
public const int stop_sync = 2131558622;
- // aapt resource value: 0x7f0d010d
- public const int stop_syncing = 2131558669;
+ // aapt resource value: 0x7f0d010e
+ public const int stop_syncing = 2131558670;
// aapt resource value: 0x7f0d003d
public const int summary_collapsed_preference_list = 2131558461;
@@ -8014,65 +8020,65 @@ namespace Opus
// aapt resource value: 0x7f0d00dd
public const int sync_now = 2131558621;
- // aapt resource value: 0x7f0d013e
- public const int sync_remove = 2131558718;
+ // aapt resource value: 0x7f0d0142
+ public const int sync_remove = 2131558722;
- // aapt resource value: 0x7f0d00f0
- public const int syncing = 2131558640;
+ // aapt resource value: 0x7f0d00f1
+ public const int syncing = 2131558641;
- // aapt resource value: 0x7f0d015e
- public const int tap_details = 2131558750;
+ // aapt resource value: 0x7f0d0162
+ public const int tap_details = 2131558754;
- // aapt resource value: 0x7f0d0140
- public const int theme = 2131558720;
+ // aapt resource value: 0x7f0d0144
+ public const int theme = 2131558724;
- // aapt resource value: 0x7f0d0141
- public const int theme_dialog = 2131558721;
+ // aapt resource value: 0x7f0d0145
+ public const int theme_dialog = 2131558725;
// aapt resource value: 0x7f0d00c3
public const int timer = 2131558595;
+ // aapt resource value: 0x7f0d0155
+ public const int timout = 2131558741;
+
+ // aapt resource value: 0x7f0d011e
+ public const int title = 2131558686;
+
// aapt resource value: 0x7f0d0151
- public const int timout = 2131558737;
+ public const int undo = 2131558737;
- // aapt resource value: 0x7f0d011a
- public const int title = 2131558682;
-
- // aapt resource value: 0x7f0d014d
- public const int undo = 2131558733;
-
- // aapt resource value: 0x7f0d0122
- public const int undo_change = 2131558690;
+ // aapt resource value: 0x7f0d0126
+ public const int undo_change = 2131558694;
// aapt resource value: 0x7f0d00e0
public const int unfork = 2131558624;
- // aapt resource value: 0x7f0d010e
- public const int unfork_playlist = 2131558670;
+ // aapt resource value: 0x7f0d010f
+ public const int unfork_playlist = 2131558671;
- // aapt resource value: 0x7f0d0152
- public const int unknow = 2131558738;
+ // aapt resource value: 0x7f0d0156
+ public const int unknow = 2131558742;
// aapt resource value: 0x7f0d00ba
public const int up_next = 2131558586;
- // aapt resource value: 0x7f0d0158
- public const int up_to_date = 2131558744;
+ // aapt resource value: 0x7f0d015c
+ public const int up_to_date = 2131558748;
- // aapt resource value: 0x7f0d012e
- public const int up_to_date_status = 2131558702;
+ // aapt resource value: 0x7f0d0132
+ public const int up_to_date_status = 2131558706;
- // aapt resource value: 0x7f0d0156
- public const int update = 2131558742;
-
- // aapt resource value: 0x7f0d0157
- public const int update_message = 2131558743;
-
- // aapt resource value: 0x7f0d0155
- public const int update_no_internet = 2131558741;
+ // aapt resource value: 0x7f0d015a
+ public const int update = 2131558746;
// aapt resource value: 0x7f0d015b
- public const int updating = 2131558747;
+ public const int update_message = 2131558747;
+
+ // aapt resource value: 0x7f0d0159
+ public const int update_no_internet = 2131558745;
+
+ // aapt resource value: 0x7f0d015f
+ public const int updating = 2131558751;
// aapt resource value: 0x7f0d003e
public const int v7_preference_off = 2131558462;
@@ -8080,38 +8086,44 @@ namespace Opus
// aapt resource value: 0x7f0d003f
public const int v7_preference_on = 2131558463;
- // aapt resource value: 0x7f0d0147
- public const int version = 2131558727;
+ // aapt resource value: 0x7f0d014b
+ public const int version = 2131558731;
- // aapt resource value: 0x7f0d013a
- public const int volume = 2131558714;
+ // aapt resource value: 0x7f0d011d
+ public const int view_less = 2131558685;
- // aapt resource value: 0x7f0d0142
- public const int white_theme = 2131558722;
+ // aapt resource value: 0x7f0d011c
+ public const int view_more = 2131558684;
- // aapt resource value: 0x7f0d0137
- public const int yes = 2131558711;
+ // aapt resource value: 0x7f0d013e
+ public const int volume = 2131558718;
- // aapt resource value: 0x7f0d0150
- public const int youtube_endpoint = 2131558736;
+ // aapt resource value: 0x7f0d0146
+ public const int white_theme = 2131558726;
- // aapt resource value: 0x7f0d00fc
- public const int youtube_loading_error = 2131558652;
+ // aapt resource value: 0x7f0d013b
+ public const int yes = 2131558715;
+
+ // aapt resource value: 0x7f0d0154
+ public const int youtube_endpoint = 2131558740;
// aapt resource value: 0x7f0d00fd
- public const int youtube_not_logged = 2131558653;
+ public const int youtube_loading_error = 2131558653;
- // aapt resource value: 0x7f0d00ff
- public const int youtube_playlist_empty = 2131558655;
+ // aapt resource value: 0x7f0d00fe
+ public const int youtube_not_logged = 2131558654;
- // aapt resource value: 0x7f0d00fa
- public const int youtube_playlists = 2131558650;
+ // aapt resource value: 0x7f0d0100
+ public const int youtube_playlist_empty = 2131558656;
+
+ // aapt resource value: 0x7f0d00fb
+ public const int youtube_playlists = 2131558651;
// aapt resource value: 0x7f0d00b5
public const int youtube_search = 2131558581;
- // aapt resource value: 0x7f0d011d
- public const int youtubeid = 2131558685;
+ // aapt resource value: 0x7f0d0121
+ public const int youtubeid = 2131558689;
// aapt resource value: 0x7f0d00b0
public const int yt_api_key = 2131558576;
diff --git a/Opus/Resources/layout/HomeChannels.xml b/Opus/Resources/layout/HomeChannels.xml
index a4dcbd1..d20024d 100644
--- a/Opus/Resources/layout/HomeChannels.xml
+++ b/Opus/Resources/layout/HomeChannels.xml
@@ -21,6 +21,7 @@
PLUS
Liste de lecture
Mis en avant
+ Aucune musique dans la liste de lecture,\ncommencez maintenant.
Titres
@@ -129,6 +130,11 @@
Playlist youtube
Playlist synchronisée (disponible localement et sur youtube)
+
+ Chargement en cours, veuillez patientez...
+ Voir plus
+ Voir moins
+
Titre
Artiste
diff --git a/Opus/Resources/values/strings.xml b/Opus/Resources/values/strings.xml
index 6ae0cb0..5888e1d 100644
--- a/Opus/Resources/values/strings.xml
+++ b/Opus/Resources/values/strings.xml
@@ -67,6 +67,7 @@
MORE
Queue
Featured
+ No song currently in queue,\nstart playing song now!
Songs
@@ -128,6 +129,11 @@
Local playlist
Youtube playlist
Synced playlist (both local and youtube)
+
+
+ Loading, please wait...
+ View more
+ View less
Title