Code refactor

This commit is contained in:
Hemanth S 2020-05-09 14:48:29 +05:30
parent 6e7d945fb1
commit 2d3ad54ab5
54 changed files with 436 additions and 142 deletions

View file

@ -24,8 +24,8 @@ android {
vectorDrawables.useSupportLibrary = true
applicationId "code.name.monkey.retromusic"
versionCode 423
versionName '3.5.120'
versionCode 424
versionName '3.5.200'
multiDexEnabled true

View file

@ -88,7 +88,6 @@ class AlbumDetailsActivity : AbsSlidingMusicPanelActivity(), AlbumDetailsView, C
slide.excludeTarget(R.id.status_bar, true)
slide.excludeTarget(android.R.id.statusBarBackground, true)
slide.excludeTarget(android.R.id.navigationBarBackground, true)
window.enterTransition = slide
}
@ -348,7 +347,8 @@ class AlbumDetailsActivity : AbsSlidingMusicPanelActivity(), AlbumDetailsView, C
R.id.action_sort_order_title -> sortOrder = AlbumSongSortOrder.SONG_A_Z
R.id.action_sort_order_title_desc -> sortOrder = AlbumSongSortOrder.SONG_Z_A
R.id.action_sort_order_track_list -> sortOrder = AlbumSongSortOrder.SONG_TRACK_LIST
R.id.action_sort_order_artist_song_duration -> sortOrder = AlbumSongSortOrder.SONG_DURATION
R.id.action_sort_order_artist_song_duration ->
sortOrder = AlbumSongSortOrder.SONG_DURATION
}
if (sortOrder != null) {
item.isChecked = true
@ -364,8 +364,7 @@ class AlbumDetailsActivity : AbsSlidingMusicPanelActivity(), AlbumDetailsView, C
AlbumSongSortOrder.SONG_Z_A -> sortOrder.findItem(R.id.action_sort_order_title_desc)
.isChecked = true
AlbumSongSortOrder.SONG_TRACK_LIST -> sortOrder.findItem(R.id.action_sort_order_track_list)
.isChecked =
true
.isChecked = true
AlbumSongSortOrder.SONG_DURATION -> sortOrder.findItem(R.id.action_sort_order_artist_song_duration)
.isChecked = true
}
@ -373,7 +372,29 @@ class AlbumDetailsActivity : AbsSlidingMusicPanelActivity(), AlbumDetailsView, C
private fun setSaveSortOrder(sortOrder: String?) {
PreferenceUtil.getInstance(this).albumDetailSongSortOrder = sortOrder
reload()
when (sortOrder) {
AlbumSongSortOrder.SONG_TRACK_LIST -> album.songs?.sortWith(Comparator { o1, o2 ->
o1.trackNumber.compareTo(
o2.trackNumber
)
})
AlbumSongSortOrder.SONG_A_Z -> album.songs?.sortWith(Comparator { o1, o2 ->
o1.title.compareTo(
o2.title
)
})
AlbumSongSortOrder.SONG_Z_A -> album.songs?.sortWith(Comparator { o1, o2 ->
o2.title.compareTo(
o1.title
)
})
AlbumSongSortOrder.SONG_DURATION -> album.songs?.sortWith(Comparator { o1, o2 ->
o1.duration.compareTo(
o2.duration
)
})
}
album.songs?.let { simpleSongAdapter.swapDataSet(it) }
}
override fun onMediaStoreChanged() {

View file

@ -185,7 +185,7 @@ class PlaylistDetailActivity : AbsSlidingMusicPanelActivity(), CabHolder, Playli
}
private fun setToolbarTitle(title: String) {
supportActionBar!!.title = title
supportActionBar?.title = title
}
private fun checkForPadding() {

View file

@ -113,16 +113,16 @@ class HomeAdapter(
inner class ArtistViewHolder(view: View) : AbsHomeViewItem(view) {
fun bindView(list: ArrayList<Artist>, titleRes: Int) {
if (list.isNotEmpty()) {
recyclerView.apply {
show()
layoutManager =
LinearLayoutManager(activity, LinearLayoutManager.HORIZONTAL, false)
val manager = LinearLayoutManager(activity, LinearLayoutManager.HORIZONTAL, false)
val artistAdapter = ArtistAdapter(
activity,
list,
PreferenceUtil.getInstance(activity).getHomeGridStyle(activity),
null
)
recyclerView.apply {
show()
layoutManager = manager
adapter = artistAdapter
}
title.text = activity.getString(titleRes)

View file

@ -77,6 +77,7 @@ class AlbumFullWidthAdapter(
if (holder.image == null) {
return
}
AlbumGlideRequest.Builder.from(Glide.with(activity), album.safeGetFirstSong())
.checkIgnoreMediaStore(activity)
.generatePalette(activity)

View file

@ -41,6 +41,8 @@ public class MediaEntryViewHolder extends AbstractDraggableSwipeableItemViewHold
@Nullable
public ImageView image;
@Nullable
public ImageView artistImage;
@Nullable
public ImageView playerImage;
@ -87,6 +89,7 @@ public class MediaEntryViewHolder extends AbstractDraggableSwipeableItemViewHold
text = itemView.findViewById(R.id.text);
image = itemView.findViewById(R.id.image);
artistImage = itemView.findViewById(R.id.artistImage);
playerImage = itemView.findViewById(R.id.player_image);
time = itemView.findViewById(R.id.time);

View file

@ -196,8 +196,8 @@ class AdaptiveFragment : AbsPlayerFragment(), MusicProgressViewUpdateHelper.Call
}
override fun onColorChanged(color: MediaNotificationProcessor) {
playbackControlsFragment.setDark(color.backgroundColor)
lastColor = color.backgroundColor
playbackControlsFragment.setDark(color.primaryTextColor)
lastColor = color.primaryTextColor
callbacks?.onPaletteColorChanged()
ToolbarContentTintHelper.colorizeToolbar(
playerToolbar,

View file

@ -45,10 +45,9 @@ class CardFragment : AbsPlayerFragment() {
}
override fun onColorChanged(color: MediaNotificationProcessor) {
playbackControlsFragment.setDark(color.backgroundColor)
lastColor = color.backgroundColor
callbacks!!.onPaletteColorChanged()
playbackControlsFragment.setDark(color.primaryTextColor)
lastColor = color.primaryTextColor
callbacks?.onPaletteColorChanged()
ToolbarContentTintHelper.colorizeToolbar(playerToolbar, Color.WHITE, activity)
}

View file

@ -129,7 +129,7 @@ class CirclePlayerFragment : AbsPlayerFragment(), Callback, OnAudioVolumeChanged
if (audioVolumeObserver == null) {
audioVolumeObserver = AudioVolumeObserver(requireActivity())
}
audioVolumeObserver!!.register(AudioManager.STREAM_MUSIC, this)
audioVolumeObserver?.register(AudioManager.STREAM_MUSIC, this)
val audioManager = audioManager
if (audioManager != null) {
@ -163,6 +163,7 @@ class CirclePlayerFragment : AbsPlayerFragment(), Callback, OnAudioVolumeChanged
get() = Color.BLACK
override fun onColorChanged(color: MediaNotificationProcessor) {
}
override fun onFavoriteToggled() {

View file

@ -7,7 +7,6 @@ import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.LinearLayout
import androidx.appcompat.app.AppCompatActivity
import androidx.appcompat.widget.Toolbar
import androidx.core.view.ViewCompat
@ -66,7 +65,6 @@ class ClassicPlayerFragment : AbsPlayerFragment(), View.OnLayoutChangeListener,
playerQueueSheet.contentPaddingRight,
playerQueueSheet.contentPaddingBottom
)
val corner = (1 - slideOffset) * DensityUtil.dip2px(requireContext(), 16f)
shapeDrawable.interpolation = 1 - slideOffset
}
@ -120,6 +118,11 @@ class ClassicPlayerFragment : AbsPlayerFragment(), View.OnLayoutChangeListener,
0
).build()
)
ToolbarContentTintHelper.colorizeToolbar(
playerToolbar,
Color.WHITE,
requireActivity()
)
}
private fun hideVolumeIfAvailable() {
@ -270,6 +273,12 @@ class ClassicPlayerFragment : AbsPlayerFragment(), View.OnLayoutChangeListener,
updateRepeatState()
updateShuffleState()
updatePrevNextColor()
ToolbarContentTintHelper.colorizeToolbar(
playerToolbar,
Color.WHITE,
requireActivity()
)
}
override fun toggleFavorite(song: Song) {

View file

@ -44,8 +44,8 @@ class FitFragment : AbsPlayerFragment() {
}
override fun onColorChanged(color: MediaNotificationProcessor) {
playbackControlsFragment.setDark(color.backgroundColor)
lastColor = color.backgroundColor
playbackControlsFragment.setDark(color.primaryTextColor)
lastColor = color.primaryTextColor
callbacks?.onPaletteColorChanged()
ToolbarContentTintHelper.colorizeToolbar(
playerToolbar,

View file

@ -29,13 +29,13 @@ class FlatPlayerFragment : AbsPlayerFragment() {
}
private var valueAnimator: ValueAnimator? = null
private lateinit var flatPlaybackControlsFragment: FlatPlaybackControlsFragment
private lateinit var controlsFragment: FlatPlaybackControlsFragment
private var lastColor: Int = 0
override val paletteColor: Int
get() = lastColor
private fun setUpSubFragments() {
flatPlaybackControlsFragment =
controlsFragment =
childFragmentManager.findFragmentById(R.id.playbackControlsFragment) as FlatPlaybackControlsFragment
val playerAlbumCoverFragment =
childFragmentManager.findFragmentById(R.id.playerAlbumCoverFragment) as PlayerAlbumCoverFragment
@ -55,11 +55,11 @@ class FlatPlayerFragment : AbsPlayerFragment() {
private fun colorize(i: Int) {
if (valueAnimator != null) {
valueAnimator!!.cancel()
valueAnimator?.cancel()
}
valueAnimator = ValueAnimator.ofObject(ArgbEvaluator(), android.R.color.transparent, i)
valueAnimator!!.addUpdateListener { animation ->
valueAnimator?.addUpdateListener { animation ->
val drawable = DrawableGradient(
GradientDrawable.Orientation.TOP_BOTTOM,
intArrayOf(animation.animatedValue as Int, android.R.color.transparent), 0
@ -67,7 +67,7 @@ class FlatPlayerFragment : AbsPlayerFragment() {
colorGradientBackground?.background = drawable
}
valueAnimator!!.setDuration(ViewUtil.RETRO_MUSIC_ANIM_TIME.toLong()).start()
valueAnimator?.setDuration(ViewUtil.RETRO_MUSIC_ANIM_TIME.toLong())?.start()
}
override fun onCreateView(
@ -84,11 +84,11 @@ class FlatPlayerFragment : AbsPlayerFragment() {
}
override fun onShow() {
flatPlaybackControlsFragment.show()
controlsFragment.show()
}
override fun onHide() {
flatPlaybackControlsFragment.hide()
controlsFragment.hide()
onBackPressed()
}
@ -106,7 +106,7 @@ class FlatPlayerFragment : AbsPlayerFragment() {
override fun onColorChanged(color: MediaNotificationProcessor) {
lastColor = color.backgroundColor
flatPlaybackControlsFragment.setDark(color.backgroundColor)
controlsFragment.setDark(color.primaryTextColor)
callbacks?.onPaletteColorChanged()
val isLight = ColorUtil.isColorLight(color.backgroundColor)
val iconColor = if (PreferenceUtil.getInstance(requireContext()).adaptiveColor)

View file

@ -125,7 +125,7 @@ class FullPlayerFragment : AbsPlayerFragment(), MusicProgressViewUpdateHelper.Ca
private var lastColor: Int = 0
override val paletteColor: Int
get() = lastColor
private lateinit var fullPlaybackControlsFragment: FullPlaybackControlsFragment
private lateinit var controlsFragment: FullPlaybackControlsFragment
private fun setUpPlayerToolbar() {
playerToolbar.apply {
@ -174,7 +174,7 @@ class FullPlayerFragment : AbsPlayerFragment(), MusicProgressViewUpdateHelper.Ca
}
private fun setUpSubFragments() {
fullPlaybackControlsFragment =
controlsFragment =
childFragmentManager.findFragmentById(R.id.playbackControlsFragment) as FullPlaybackControlsFragment
val playerAlbumCoverFragment =
@ -199,14 +199,14 @@ class FullPlayerFragment : AbsPlayerFragment(), MusicProgressViewUpdateHelper.Ca
override fun onColorChanged(color: MediaNotificationProcessor) {
lastColor = color.backgroundColor
fullPlaybackControlsFragment.setDark(color.backgroundColor)
controlsFragment.setDark(color.primaryTextColor)
callbacks?.onPaletteColorChanged()
ToolbarContentTintHelper.colorizeToolbar(playerToolbar, Color.WHITE, activity)
}
override fun onFavoriteToggled() {
toggleFavorite(MusicPlayerRemote.currentSong)
fullPlaybackControlsFragment.onFavoriteToggled()
controlsFragment.onFavoriteToggled()
}
override fun toggleFavorite(song: Song) {

View file

@ -28,7 +28,7 @@ class PlayerFragment : AbsPlayerFragment() {
override val paletteColor: Int
get() = lastColor
private lateinit var playbackControlsFragment: PlayerPlaybackControlsFragment
private lateinit var controlsFragment: PlayerPlaybackControlsFragment
private var valueAnimator: ValueAnimator? = null
@ -58,11 +58,11 @@ class PlayerFragment : AbsPlayerFragment() {
}
override fun onShow() {
playbackControlsFragment.show()
controlsFragment.show()
}
override fun onHide() {
playbackControlsFragment.hide()
controlsFragment.hide()
onBackPressed()
}
@ -75,7 +75,7 @@ class PlayerFragment : AbsPlayerFragment() {
}
override fun onColorChanged(color: MediaNotificationProcessor) {
playbackControlsFragment.setDark(color.backgroundColor)
controlsFragment.setDark(color.primaryTextColor)
lastColor = color.backgroundColor
callbacks?.onPaletteColorChanged()
@ -118,7 +118,7 @@ class PlayerFragment : AbsPlayerFragment() {
private fun setUpSubFragments() {
playbackControlsFragment =
controlsFragment =
childFragmentManager.findFragmentById(R.id.playbackControlsFragment) as PlayerPlaybackControlsFragment
val playerAlbumCoverFragment =
childFragmentManager.findFragmentById(R.id.playerAlbumCoverFragment) as PlayerAlbumCoverFragment

View file

@ -40,7 +40,7 @@ import kotlinx.android.synthetic.main.fragment_peak_player.*
class PeakPlayerFragment : AbsPlayerFragment() {
private lateinit var playbackControlsFragment: PeakPlayerControlFragment
private lateinit var controlsFragment: PeakPlayerControlFragment
private var lastColor: Int = 0
override fun onCreateView(
@ -62,7 +62,7 @@ class PeakPlayerFragment : AbsPlayerFragment() {
}
private fun setUpSubFragments() {
playbackControlsFragment =
controlsFragment =
childFragmentManager.findFragmentById(R.id.playbackControlsFragment) as PeakPlayerControlFragment
}
@ -101,8 +101,8 @@ class PeakPlayerFragment : AbsPlayerFragment() {
get() = lastColor
override fun onColorChanged(color: MediaNotificationProcessor) {
playbackControlsFragment.setDark(color.backgroundColor)
lastColor = color.backgroundColor
controlsFragment.setDark(color.primaryTextColor)
lastColor = color.primaryTextColor
callbacks?.onPaletteColorChanged()
}
@ -127,7 +127,7 @@ class PeakPlayerFragment : AbsPlayerFragment() {
.build()
.into(object : RetroMusicColoredTarget(playerImage) {
override fun onColorReady(colors: MediaNotificationProcessor) {
playbackControlsFragment.setDark(colors.backgroundColor)
controlsFragment.setDark(colors.primaryTextColor)
}
})
}

View file

@ -95,8 +95,8 @@ class PlainPlayerFragment : AbsPlayerFragment() {
}
override fun onColorChanged(color: MediaNotificationProcessor) {
plainPlaybackControlsFragment.setDark(color.backgroundColor)
lastColor = color.backgroundColor
plainPlaybackControlsFragment.setDark(color.primaryTextColor)
lastColor = color.primaryTextColor
callbacks!!.onPaletteColorChanged()
ToolbarContentTintHelper.colorizeToolbar(
playerToolbar,

View file

@ -29,7 +29,7 @@ class SimplePlayerFragment : AbsPlayerFragment() {
override val paletteColor: Int
get() = lastColor
private lateinit var simplePlaybackControlsFragment: SimplePlaybackControlsFragment
private lateinit var controlsFragment: SimplePlaybackControlsFragment
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?,
@ -49,16 +49,16 @@ class SimplePlayerFragment : AbsPlayerFragment() {
val playerAlbumCoverFragment =
childFragmentManager.findFragmentById(R.id.playerAlbumCoverFragment) as PlayerAlbumCoverFragment
playerAlbumCoverFragment.setCallbacks(this)
simplePlaybackControlsFragment =
controlsFragment =
childFragmentManager.findFragmentById(R.id.playbackControlsFragment) as SimplePlaybackControlsFragment
}
override fun onShow() {
simplePlaybackControlsFragment.show()
controlsFragment.show()
}
override fun onHide() {
simplePlaybackControlsFragment.hide()
controlsFragment.hide()
}
override fun onBackPressed(): Boolean {
@ -72,7 +72,7 @@ class SimplePlayerFragment : AbsPlayerFragment() {
override fun onColorChanged(color: MediaNotificationProcessor) {
lastColor = color.backgroundColor
callbacks?.onPaletteColorChanged()
simplePlaybackControlsFragment.setDark(color.backgroundColor)
controlsFragment.setDark(color.primaryTextColor)
ToolbarContentTintHelper.colorizeToolbar(
playerToolbar,
ATHUtil.resolveColor(requireContext(), R.attr.colorControlNormal),

View file

@ -75,7 +75,7 @@ class TinyPlayerFragment : AbsPlayerFragment(), MusicProgressViewUpdateHelper.Ca
override fun onColorChanged(color: MediaNotificationProcessor) {
val colorFinal = if (PreferenceUtil.getInstance(requireContext()).adaptiveColor) {
color.backgroundColor
color.primaryTextColor
} else {
ThemeStore.accentColor(requireContext())
}

View file

@ -16,13 +16,13 @@ package code.name.monkey.retromusic.loaders
import android.content.Context
import android.provider.MediaStore.Audio.AudioColumns
import code.name.monkey.retromusic.App
import code.name.monkey.retromusic.helper.SortOrder
import code.name.monkey.retromusic.model.Album
import code.name.monkey.retromusic.model.Song
import code.name.monkey.retromusic.util.PreferenceUtil
import java.util.*
import kotlin.collections.ArrayList
import kotlin.collections.isNotEmpty
import kotlin.collections.sortWith
/**
@ -108,12 +108,32 @@ object AlbumLoader {
}
private fun sortSongsByTrackNumber(album: Album) {
album.songs?.sortWith(Comparator { o1, o2 -> o1.trackNumber.compareTo(o2.trackNumber) })
when (PreferenceUtil.getInstance(App.getContext()).albumDetailSongSortOrder) {
SortOrder.AlbumSongSortOrder.SONG_TRACK_LIST -> album.songs?.sortWith(Comparator { o1, o2 ->
o1.trackNumber.compareTo(
o2.trackNumber
)
})
SortOrder.AlbumSongSortOrder.SONG_A_Z -> album.songs?.sortWith(Comparator { o1, o2 ->
o1.title.compareTo(
o2.title
)
})
SortOrder.AlbumSongSortOrder.SONG_Z_A -> album.songs?.sortWith(Comparator { o1, o2 ->
o2.title.compareTo(
o1.title
)
})
SortOrder.AlbumSongSortOrder.SONG_DURATION -> album.songs?.sortWith(Comparator { o1, o2 ->
o1.duration.compareTo(
o2.duration
)
})
}
}
private fun getSongLoaderSortOrder(context: Context): String {
return PreferenceUtil.getInstance(context).albumSortOrder + ", " + PreferenceUtil.getInstance(
context
).albumSongSortOrder
return PreferenceUtil.getInstance(context).albumSortOrder + ", " +
PreferenceUtil.getInstance(context).albumSongSortOrder
}
}

View file

@ -31,7 +31,6 @@ import java.util.*
object SongLoader {
fun getAllSongs(
context: Context
): ArrayList<Song> {
@ -128,9 +127,8 @@ object SongLoader {
return context.contentResolver.query(
MediaStore.Audio.Media.EXTERNAL_CONTENT_URI,
baseProjection,
selectionFinal + " AND " + MediaStore.Audio.Media.DURATION + ">= " + (PreferenceUtil.getInstance(
context
).filterLength * 1000),
selectionFinal + " AND " + MediaStore.Audio.Media.DURATION + ">= " +
(PreferenceUtil.getInstance(context).filterLength * 1000),
selectionValuesFinal,
sortOrder
)

View file

@ -42,7 +42,241 @@ import static android.provider.MediaStore.Audio.Playlists.EXTERNAL_CONTENT_URI;
public class PlaylistsUtil {
public static void addToPlaylist(@NonNull Context context,
public static int createPlaylist(@NonNull final Context context, @Nullable final String name) {
int id = -1;
if (name != null && name.length() > 0) {
try {
Cursor cursor = context.getContentResolver().query(EXTERNAL_CONTENT_URI,
new String[]{MediaStore.Audio.Playlists._ID},
MediaStore.Audio.PlaylistsColumns.NAME + "=?", new String[]{name},
null);
if (cursor == null || cursor.getCount() < 1) {
final ContentValues values = new ContentValues(1);
values.put(MediaStore.Audio.PlaylistsColumns.NAME, name);
final Uri uri = context.getContentResolver().insert(
EXTERNAL_CONTENT_URI,
values);
if (uri != null) {
// Necessary because somehow the MediaStoreObserver is not notified when adding a playlist
context.getContentResolver().notifyChange(Uri.parse("content://media"), null);
Toast.makeText(context, context.getResources().getString(
R.string.created_playlist_x, name), Toast.LENGTH_SHORT).show();
id = Integer.parseInt(uri.getLastPathSegment());
}
} else {
// Playlist exists
if (cursor.moveToFirst()) {
id = cursor.getInt(cursor.getColumnIndex(MediaStore.Audio.Playlists._ID));
}
}
if (cursor != null) {
cursor.close();
}
} catch (SecurityException e) {
e.printStackTrace();
Toast.makeText(context, "Don't have permission for adding to playlist", Toast.LENGTH_SHORT).show();
}
}
if (id == -1) {
Toast.makeText(context, context.getResources().getString(
R.string.could_not_create_playlist), Toast.LENGTH_SHORT).show();
}
return id;
}
public static void deletePlaylists(@NonNull final Context context, @NonNull final ArrayList<Playlist> playlists) {
final StringBuilder selection = new StringBuilder();
selection.append(MediaStore.Audio.Playlists._ID + " IN (");
for (int i = 0; i < playlists.size(); i++) {
selection.append(playlists.get(i).id);
if (i < playlists.size() - 1) {
selection.append(",");
}
}
selection.append(")");
try {
context.getContentResolver().delete(EXTERNAL_CONTENT_URI, selection.toString(), null);
context.getContentResolver().notifyChange(Uri.parse("content://media"), null);
} catch (SecurityException ignored) {
}
}
public static void addToPlaylist(@NonNull final Context context, final Song song, final int playlistId, final boolean showToastOnFinish) {
List<Song> helperList = new ArrayList<>();
helperList.add(song);
addToPlaylist(context, helperList, playlistId, showToastOnFinish);
}
public static void addToPlaylist(@NonNull final Context context, @NonNull final List<Song> songs, final int playlistId, final boolean showToastOnFinish) {
final int size = songs.size();
final ContentResolver resolver = context.getContentResolver();
final String[] projection = new String[]{
"max(" + MediaStore.Audio.Playlists.Members.PLAY_ORDER + ")",
};
final Uri uri = MediaStore.Audio.Playlists.Members.getContentUri("external", playlistId);
Cursor cursor = null;
int base = 0;
try {
try {
cursor = resolver.query(uri, projection, null, null, null);
if (cursor != null && cursor.moveToFirst()) {
base = cursor.getInt(0) + 1;
}
} finally {
if (cursor != null) {
cursor.close();
}
}
int numInserted = 0;
for (int offSet = 0; offSet < size; offSet += 1000)
numInserted += resolver.bulkInsert(uri, makeInsertItems(songs, offSet, 1000, base));
if (showToastOnFinish) {
Toast.makeText(context, context.getResources().getString(
R.string.inserted_x_songs_into_playlist_x, numInserted, getNameForPlaylist(context, playlistId)), Toast.LENGTH_SHORT).show();
}
} catch (SecurityException ignored) {
ignored.printStackTrace();
Toast.makeText(context, "Don't have permission for adding to playlist", Toast.LENGTH_SHORT).show();
}
}
@NonNull
public static ContentValues[] makeInsertItems(@NonNull final List<Song> songs, final int offset, int len, final int base) {
if (offset + len > songs.size()) {
len = songs.size() - offset;
}
ContentValues[] contentValues = new ContentValues[len];
for (int i = 0; i < len; i++) {
contentValues[i] = new ContentValues();
contentValues[i].put(MediaStore.Audio.Playlists.Members.PLAY_ORDER, base + offset + i);
contentValues[i].put(MediaStore.Audio.Playlists.Members.AUDIO_ID, songs.get(offset + i).getId());
}
return contentValues;
}
public static String getNameForPlaylist(@NonNull final Context context, final long id) {
try {
Cursor cursor = context.getContentResolver().query(EXTERNAL_CONTENT_URI,
new String[]{MediaStore.Audio.PlaylistsColumns.NAME},
BaseColumns._ID + "=?",
new String[]{String.valueOf(id)},
null);
if (cursor != null) {
try {
if (cursor.moveToFirst()) {
return cursor.getString(0);
}
} finally {
cursor.close();
}
}
} catch (SecurityException ignored) {
}
return "";
}
public static void removeFromPlaylist(@NonNull final Context context, @NonNull final Song song, int playlistId) {
Uri uri = MediaStore.Audio.Playlists.Members.getContentUri(
"external", playlistId);
String selection = MediaStore.Audio.Playlists.Members.AUDIO_ID + " =?";
String[] selectionArgs = new String[]{String.valueOf(song.getId())};
try {
context.getContentResolver().delete(uri, selection, selectionArgs);
} catch (SecurityException ignored) {
}
}
public static void removeFromPlaylist(@NonNull final Context context, @NonNull final List<PlaylistSong> songs) {
final int playlistId = songs.get(0).getPlaylistId();
Uri uri = MediaStore.Audio.Playlists.Members.getContentUri(
"external", playlistId);
String selectionArgs[] = new String[songs.size()];
for (int i = 0; i < selectionArgs.length; i++) {
selectionArgs[i] = String.valueOf(songs.get(i).getIdInPlayList());
}
String selection = MediaStore.Audio.Playlists.Members._ID + " in (";
//noinspection unused
for (String selectionArg : selectionArgs) selection += "?, ";
selection = selection.substring(0, selection.length() - 2) + ")";
try {
context.getContentResolver().delete(uri, selection, selectionArgs);
} catch (SecurityException ignored) {
}
}
public static boolean doPlaylistContains(@NonNull final Context context, final long playlistId, final int songId) {
if (playlistId != -1) {
try {
Cursor c = context.getContentResolver().query(
MediaStore.Audio.Playlists.Members.getContentUri("external", playlistId),
new String[]{MediaStore.Audio.Playlists.Members.AUDIO_ID}, MediaStore.Audio.Playlists.Members.AUDIO_ID + "=?", new String[]{String.valueOf(songId)}, null);
int count = 0;
if (c != null) {
count = c.getCount();
c.close();
}
return count > 0;
} catch (SecurityException ignored) {
}
}
return false;
}
public static boolean moveItem(@NonNull final Context context, int playlistId, int from, int to) {
return MediaStore.Audio.Playlists.Members.moveItem(context.getContentResolver(),
playlistId, from, to);
}
public static void renamePlaylist(@NonNull final Context context, final long id, final String newName) {
ContentValues contentValues = new ContentValues();
contentValues.put(MediaStore.Audio.PlaylistsColumns.NAME, newName);
try {
context.getContentResolver().update(EXTERNAL_CONTENT_URI,
contentValues,
MediaStore.Audio.Playlists._ID + "=?",
new String[]{String.valueOf(id)});
context.getContentResolver().notifyChange(Uri.parse("content://media"), null);
} catch (SecurityException ignored) {
}
}
public static File savePlaylist(Context context, Playlist playlist) throws IOException {
return M3UWriter.write(context, new File(Environment.getExternalStorageDirectory(), "Playlists"), playlist);
}
public static boolean doesPlaylistExist(@NonNull final Context context, final int playlistId) {
return playlistId != -1 && doesPlaylistExist(context,
MediaStore.Audio.Playlists._ID + "=?",
new String[]{String.valueOf(playlistId)});
}
public static boolean doesPlaylistExist(@NonNull final Context context, final String name) {
return doesPlaylistExist(context,
MediaStore.Audio.PlaylistsColumns.NAME + "=?",
new String[]{name});
}
private static boolean doesPlaylistExist(@NonNull Context context, @NonNull final String selection, @NonNull final String[] values) {
Cursor cursor = context.getContentResolver().query(EXTERNAL_CONTENT_URI,
new String[]{}, selection, values, null);
boolean exists = false;
if (cursor != null) {
exists = cursor.getCount() != 0;
cursor.close();
}
return exists;
}
/*public static void addToPlaylist(@NonNull Context context,
@NonNull List<Song> songs,
int playlistId,
boolean showToastOnFinish) {
@ -273,5 +507,5 @@ public class PlaylistsUtil {
cursor.close();
}
return exists;
}
}*/
}

View file

@ -37,7 +37,7 @@ class RetroShapeableImageView @JvmOverloads constructor(
typedArray.recycle()
}
fun updateCornerSize(cornerSize: Float) {
private fun updateCornerSize(cornerSize: Float) {
shapeAppearanceModel = ShapeAppearanceModel.Builder()
.setAllCorners(CornerFamily.ROUNDED, cornerSize)
.build()

Binary file not shown.

Before

Width:  |  Height:  |  Size: 141 KiB

After

Width:  |  Height:  |  Size: 125 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 110 KiB

After

Width:  |  Height:  |  Size: 111 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 75 KiB

After

Width:  |  Height:  |  Size: 76 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 126 KiB

After

Width:  |  Height:  |  Size: 109 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 90 KiB

After

Width:  |  Height:  |  Size: 88 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 84 KiB

After

Width:  |  Height:  |  Size: 121 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 102 KiB

After

Width:  |  Height:  |  Size: 104 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 138 KiB

After

Width:  |  Height:  |  Size: 132 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 109 KiB

After

Width:  |  Height:  |  Size: 109 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 49 KiB

After

Width:  |  Height:  |  Size: 75 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 103 KiB

After

Width:  |  Height:  |  Size: 106 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 109 KiB

After

Width:  |  Height:  |  Size: 110 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 40 KiB

After

Width:  |  Height:  |  Size: 40 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 107 KiB

After

Width:  |  Height:  |  Size: 107 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1,015 KiB

After

Width:  |  Height:  |  Size: 107 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 111 KiB

After

Width:  |  Height:  |  Size: 14 KiB

View file

@ -0,0 +1,5 @@
<vector android:height="24dp" android:tint="#FFFFFF"
android:viewportHeight="24.0" android:viewportWidth="24.0"
android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
<path android:fillColor="#FF000000" android:pathData="M12,2C6.48,2 2,6.48 2,12s4.48,10 10,10 10,-4.48 10,-10S17.52,2 12,2zM10,17l-5,-5 1.41,-1.41L10,14.17l7.59,-7.59L19,8l-9,9z"/>
</vector>

View file

@ -3,8 +3,8 @@
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:background="@color/md_black_1000"
android:layout_height="match_parent"
android:background="@color/md_black_1000"
android:orientation="vertical">
<View
@ -72,7 +72,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
app:srcCompat="@drawable/ic_invert_colors_white_24dp"
app:srcCompat="@drawable/ic_check_circle_white_24dp"
app:tint="@color/md_white_1000" />
<com.google.android.material.textview.MaterialTextView
@ -94,7 +94,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
app:srcCompat="@drawable/ic_theme_palette_white_24dp"
app:srcCompat="@drawable/ic_check_circle_white_24dp"
app:tint="@color/md_white_1000" />
<com.google.android.material.textview.MaterialTextView
@ -116,7 +116,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
app:srcCompat="@drawable/ic_view_carousel_black_24dp"
app:srcCompat="@drawable/ic_check_circle_white_24dp"
app:tint="@color/md_white_1000" />
<com.google.android.material.textview.MaterialTextView
@ -139,7 +139,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
app:srcCompat="@drawable/ic_rounded_corner"
app:srcCompat="@drawable/ic_check_circle_white_24dp"
app:tint="@color/md_white_1000" />
<com.google.android.material.textview.MaterialTextView
@ -161,7 +161,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
app:srcCompat="@drawable/ic_favorite_white_24dp"
app:srcCompat="@drawable/ic_check_circle_white_24dp"
app:tint="@color/md_white_1000" />
<com.google.android.material.textview.MaterialTextView
@ -180,8 +180,7 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:paddingHorizontal="16dp"
android:paddingBottom="16dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
@ -191,7 +190,8 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:padding="24dp"
android:paddingHorizontal="16dp"
android:paddingVertical="24dp"
android:text="@string/try_retro_music_premium"
android:textAppearance="@style/TextViewHeadline5"
android:textColor="@color/md_white_1000" />

View file

@ -8,10 +8,11 @@
<com.google.android.material.card.MaterialCardView
android:layout_width="match_parent"
android:layout_height="match_parent"
app:cardCornerRadius="8dp"
app:cardUseCompatPadding="true">
android:layout_margin="16dp"
app:cardCornerRadius="16dp"
app:cardElevation="8dp">
<ImageView
<androidx.appcompat.widget.AppCompatImageView
android:id="@+id/player_image"
android:layout_width="match_parent"
android:layout_height="match_parent"

View file

@ -75,9 +75,7 @@
android:gravity="center"
android:marqueeRepeatLimit="marquee_forever"
android:paddingStart="16dp"
android:paddingTop="8dp"
android:paddingEnd="16dp"
android:paddingBottom="4dp"
android:scrollHorizontally="true"
android:singleLine="true"
android:textAppearance="@style/TextViewHeadline6"
@ -95,9 +93,9 @@
android:gravity="center"
android:maxLines="1"
android:paddingStart="16dp"
android:paddingTop="4dp"
android:paddingTop="8dp"
android:paddingEnd="16dp"
android:paddingBottom="12dp"
android:paddingBottom="8dp"
android:textAppearance="@style/TextViewBody1"
android:textColor="?android:attr/textColorSecondary"
app:layout_constrainedWidth="true"

View file

@ -114,8 +114,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginTop="4dp"
android:layout_marginBottom="4dp"
android:layout_marginBottom="8dp"
android:ellipsize="end"
android:gravity="center"
android:maxLines="1"

View file

@ -13,7 +13,8 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="?attr/roundSelector"
android:padding="14dp"
android:paddingHorizontal="16dp"
android:paddingVertical="12dp"
app:layout_constraintBottom_toBottomOf="@+id/titleContainer"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="@id/titleContainer"
@ -66,7 +67,8 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="?attr/roundSelector"
android:padding="14dp"
android:paddingHorizontal="16dp"
android:paddingVertical="12dp"
app:layout_constraintBottom_toBottomOf="@+id/titleContainer"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="@+id/titleContainer"

View file

@ -74,10 +74,7 @@
android:freezesText="true"
android:gravity="center"
android:marqueeRepeatLimit="marquee_forever"
android:paddingStart="16dp"
android:paddingTop="8dp"
android:paddingEnd="16dp"
android:paddingBottom="8dp"
android:paddingHorizontal="16dp"
android:scrollHorizontally="true"
android:singleLine="true"
android:textAppearance="@style/TextViewHeadline6"
@ -94,10 +91,8 @@
android:ellipsize="end"
android:gravity="center"
android:maxLines="1"
android:paddingStart="16dp"
android:paddingTop="8dp"
android:paddingEnd="16dp"
android:paddingBottom="8dp"
android:paddingHorizontal="16dp"
android:paddingVertical="8dp"
android:textAppearance="@style/TextViewBody1"
android:textColor="?android:attr/textColorSecondary"
app:layout_constrainedWidth="true"
@ -113,8 +108,7 @@
android:ellipsize="end"
android:gravity="center"
android:maxLines="2"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:paddingHorizontal="16dp"
android:textColor="?android:attr/textColorSecondary"
android:textSize="12sp"
app:layout_constraintBottom_toTopOf="@+id/playPauseButton"

View file

@ -2,25 +2,19 @@
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="112dp"
android:layout_width="96dp"
android:layout_height="wrap_content"
android:layout_margin="8dp"
android:background="?attr/rectSelector"
android:orientation="vertical">
<code.name.monkey.retromusic.views.WidthFitSquareLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<code.name.monkey.retromusic.views.RetroShapeableImageView
android:id="@+id/image"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_width="96dp"
android:layout_height="wrap_content"
android:background="@android:color/transparent"
app:civ_border="false"
app:retroCornerSize="56dp"
app:retroCornerSize="46dp"
tools:src="@tools:sample/avatars" />
</code.name.monkey.retromusic.views.WidthFitSquareLayout>
<com.google.android.material.textview.MaterialTextView
android:id="@+id/title"

View file

@ -29,13 +29,14 @@
android:id="@+id/icon"
android:layout_width="42dp"
android:layout_height="42dp"
android:scaleType="centerCrop"
app:civ_border="false"
app:civ_shadow="false"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:retroCornerSize="21dp"
app:srcCompat="@drawable/ic_person_flat"
app:srcCompat="@drawable/ic_account_white_24dp"
tools:srcCompat="@tools:sample/backgrounds/scenic[20]" />
<com.google.android.material.textview.MaterialTextView

View file

@ -32,7 +32,7 @@
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
tools:text="Genre name" />
tools:text="@tools:sample/first_names" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/text"
@ -43,7 +43,7 @@
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/title"
tools:text="Genre details" />
tools:text="@tools:sample/first_names" />
</androidx.constraintlayout.widget.ConstraintLayout>

View file

@ -17,15 +17,14 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_vertical"
android:orientation="horizontal"
>
android:orientation="horizontal">
<com.google.android.material.button.MaterialButton
android:id="@+id/playAction"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="16dp"
android:layout_marginEnd="2dp"
android:layout_marginEnd="4dp"
android:layout_weight="1"
android:text="@string/action_play_all"
app:backgroundTint="?attr/colorSurface"
@ -35,8 +34,8 @@
android:id="@+id/shuffleAction"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="16dp"
android:layout_marginEnd="2dp"
android:layout_marginStart="4dp"
android:layout_marginEnd="16dp"
android:layout_weight="1"
android:text="@string/shuffle"
app:backgroundTint="?attr/colorSurface"

View file

@ -3,7 +3,8 @@
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/background"
android:layout_width="match_parent"
android:layout_height="wrap_content">
android:layout_height="wrap_content"
tools:background="@color/md_red_500">
<RelativeLayout
android:id="@+id/image"

View file

@ -11,14 +11,15 @@
android:id="@+id/title"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:padding="16dp"
android:paddingHorizontal="16dp"
android:paddingVertical="12dp"
android:textAppearance="@style/TextViewHeadline6"
android:textStyle="bold"
app:layout_constrainedWidth="true"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
tools:text="@tools:sample/lorem" />
tools:text="@tools:sample/full_names" />
<code.name.monkey.retromusic.views.MetalRecyclerViewPager
android:id="@+id/recyclerView"
@ -27,7 +28,7 @@
android:nestedScrollingEnabled="false"
android:overScrollMode="never"
android:visibility="gone"
app:itemMargin="28dp"
app:itemMargin="96dp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/title"

View file

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/root_layout"
@ -10,10 +10,14 @@
<com.google.android.material.card.MaterialCardView
android:id="@+id/imageContainer"
android:layout_width="match_parent"
android:layout_height="172dp"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_margin="8dp"
app:cardCornerRadius="16dp">
app:cardCornerRadius="16dp"
app:layout_constraintDimensionRatio="16:9"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">
<androidx.appcompat.widget.AppCompatImageView
android:id="@+id/image"
@ -24,40 +28,48 @@
<androidx.appcompat.widget.AppCompatImageButton
android:id="@+id/playSongs"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_width="42dp"
android:layout_height="42dp"
android:layout_gravity="bottom|end"
android:layout_margin="12dp"
android:background="@drawable/color_circle_gradient"
android:backgroundTint="@color/eighty_percent_black_overlay"
android:padding="8dp"
android:padding="16dp"
app:srcCompat="@drawable/ic_play_arrow_white_32dp" />
</com.google.android.material.card.MaterialCardView>
<com.google.android.material.textview.MaterialTextView
android:id="@+id/text"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginTop="12dp"
android:ellipsize="end"
android:maxLines="1"
android:paddingStart="16dp"
android:paddingTop="6dp"
android:paddingEnd="8dp"
android:paddingBottom="4dp"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toBottomOf="@id/imageContainer"
tools:ignore="MissingPrefix"
tools:text="My top tracks" />
tools:text="@tools:sample/full_names" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/title"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:ellipsize="end"
android:maxLines="1"
android:paddingStart="16dp"
app:layout_constraintStart_toStartOf="parent"
android:paddingEnd="8dp"
android:textAppearance="@style/TextViewSubtitle1"
android:textStyle="bold"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toBottomOf="@id/text"
tools:ignore="MissingPrefix"
tools:text="My top tracks" />
tools:text="@tools:sample/full_names" />
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>

View file

@ -12,7 +12,8 @@
android:id="@+id/title"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:padding="16dp"
android:paddingHorizontal="16dp"
android:paddingVertical="12dp"
android:textAppearance="@style/TextViewHeadline6"
android:textStyle="bold"
app:layout_constrainedWidth="true"

View file

@ -10,7 +10,7 @@
app:showAsAction="ifRoom" />
<item
android:id="@+id/now_playing"
android:icon="@drawable/ic_playlist_play_white_24dp"
android:icon="@drawable/ic_queue_music_white_24dp"
android:orderInCategory="2"
android:title="@string/now_playing_queue"
app:showAsAction="ifRoom" />