From ee2b661eb41256967f6260df10b1afb19bb1a534 Mon Sep 17 00:00:00 2001 From: Karim Abou Zeid Date: Wed, 22 Apr 2015 21:17:38 +0200 Subject: [PATCH] Replaced Ion with Glide. Big performance boost, and should also fix the FCs many people get because of recycled bitmaps. Fixed the ripple flickering by using ?selectableItemBackground on Lollipop again instead of custom ripple. Search is broken for now, remake in progress. --- app/build.gradle | 6 +- app/proguard-rules.pro | 5 + .../gramophone/adapter/AlbumAdapter.java | 95 +++++++------- .../gramophone/adapter/ArtistAdapter.java | 22 +--- .../adapter/ArtistAlbumAdapter.java | 25 ++-- .../gramophone/adapter/SearchAdapter.java | 96 ++++---------- .../songadapter/ArtistSongAdapter.java | 11 +- .../songadapter/PlaylistSongAdapter.java | 18 +-- .../adapter/songadapter/SongAdapter.java | 27 ++-- .../appwidget/MusicPlayerWidget.java | 46 ++++--- .../gramophone/dialogs/DeleteSongsDialog.java | 2 +- .../helper/PlayingNotificationHelper.java | 86 ++++++++----- .../com/kabouzeid/gramophone/model/Album.java | 36 +----- .../kabouzeid/gramophone/model/Artist.java | 41 +----- .../gramophone/model/SearchEntry.java | 15 --- .../com/kabouzeid/gramophone/model/Song.java | 20 +-- .../gramophone/service/MusicService.java | 34 +++-- .../ui/activities/AlbumDetailActivity.java | 93 +++++++------- .../ui/activities/ArtistDetailActivity.java | 84 ++++++------ .../ui/activities/MainActivity.java | 23 +--- .../activities/MusicControllerActivity.java | 96 +++++++------- .../ui/activities/SearchActivity.java | 120 ++---------------- .../tageditor/AbsTagEditorActivity.java | 7 +- .../tageditor/AlbumTagEditorActivity.java | 55 +++++--- .../kabouzeid/gramophone/util/MusicUtil.java | 13 +- .../res/drawable-v21/rect_ripple_selector.xml | 6 - .../rect_ripple_selector_dark.xml | 6 - .../drawable-v21/round_ripple_selector.xml | 4 +- .../round_ripple_selector_dark.xml | 2 +- app/src/main/res/layout/activity_search.xml | 15 +-- .../layout/notification_playing_expanded.xml | 4 +- app/src/main/res/values-v21/styles.xml | 4 +- app/src/main/res/values/colors.xml | 1 - app/src/main/res/values/dimens.xml | 1 + 34 files changed, 450 insertions(+), 669 deletions(-) delete mode 100644 app/src/main/java/com/kabouzeid/gramophone/model/SearchEntry.java delete mode 100644 app/src/main/res/drawable-v21/rect_ripple_selector.xml delete mode 100644 app/src/main/res/drawable-v21/rect_ripple_selector_dark.xml diff --git a/app/build.gradle b/app/build.gradle index 98166c56..1bbbc0f7 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -59,9 +59,6 @@ dependencies { compile 'com.android.support:support-v13:22.1.0' compile 'com.android.support:cardview-v7:22.1.0' - compile 'com.nhaarman.listviewanimations:lib-core:+@aar' - compile 'com.nhaarman.listviewanimations:lib-manipulation:+@aar' - compile 'com.nhaarman.listviewanimations:lib-core-slh:+@aar' compile 'com.github.ksoichiro:android-observablescrollview:1.5.0' compile 'asia.ivity.android:drag-sort-listview:1.0' @@ -69,9 +66,8 @@ dependencies { compile 'com.mcxiaoke.volley:library:1.0.15' compile 'com.squareup:otto:1.3.6' - compile 'com.squareup.okhttp:okhttp:2.2.0' compile 'de.hdodenhof:circleimageview:1.2.2' - compile 'com.koushikdutta.ion:ion:2.1.3' + compile 'com.github.bumptech.glide:glide:3.5.2' compile 'com.afollestad:material-dialogs:0.7.2.6' compile 'com.jpardogo.materialtabstrip:library:1.0.9' diff --git a/app/proguard-rules.pro b/app/proguard-rules.pro index eaf91897..eef77cc6 100644 --- a/app/proguard-rules.pro +++ b/app/proguard-rules.pro @@ -17,5 +17,10 @@ #} -keep class !android.support.v7.internal.view.menu.**,** {*;} +-keep public class * implements com.bumptech.glide.module.GlideModule +-keep public enum com.bumptech.glide.load.resource.bitmap.ImageHeaderParser$** { + **[] $VALUES; + public *; +} -dontwarn -ignorewarnings \ No newline at end of file diff --git a/app/src/main/java/com/kabouzeid/gramophone/adapter/AlbumAdapter.java b/app/src/main/java/com/kabouzeid/gramophone/adapter/AlbumAdapter.java index bef12e6d..f4129f18 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/adapter/AlbumAdapter.java +++ b/app/src/main/java/com/kabouzeid/gramophone/adapter/AlbumAdapter.java @@ -2,6 +2,7 @@ package com.kabouzeid.gramophone.adapter; import android.app.Activity; import android.graphics.Bitmap; +import android.net.Uri; import android.support.v4.util.Pair; import android.support.v7.graphics.Palette; import android.support.v7.widget.RecyclerView; @@ -12,6 +13,12 @@ import android.widget.ImageView; import android.widget.TextView; import com.afollestad.materialdialogs.util.DialogUtils; +import com.bumptech.glide.Glide; +import com.bumptech.glide.load.resource.bitmap.GlideBitmapDrawable; +import com.bumptech.glide.load.resource.drawable.GlideDrawable; +import com.bumptech.glide.request.Request; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.kabouzeid.gramophone.App; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.loader.AlbumLoader; @@ -23,11 +30,6 @@ import com.kabouzeid.gramophone.util.MusicUtil; import com.kabouzeid.gramophone.util.NavigationUtil; import com.kabouzeid.gramophone.util.PreferenceUtils; import com.kabouzeid.gramophone.util.ViewUtil; -import com.koushikdutta.async.future.Future; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.ImageViewBitmapInfo; -import com.koushikdutta.ion.Ion; -import com.koushikdutta.ion.bitmap.BitmapInfo; import com.squareup.otto.Subscribe; import java.util.List; @@ -51,9 +53,9 @@ public class AlbumAdapter extends RecyclerView.Adapter @Override public void onViewRecycled(ViewHolder holder) { super.onViewRecycled(holder); - Object tag = holder.image.getTag(); - if (tag instanceof Future) { - ((Future) tag).cancel(); + Object tag = holder.albumArt.getTag(); + if (tag instanceof Request) { + ((Request) tag).clear(); } } @@ -63,35 +65,30 @@ public class AlbumAdapter extends RecyclerView.Adapter resetColors(holder.title, holder.artist, holder.footer); + holder.title.setText(album.title); holder.artist.setText(album.artistName); - holder.image.setTag( - Ion.with(activity) - .load(MusicUtil.getAlbumArtUri(album.id).toString()) - .withBitmap() - .resize(holder.image.getWidth(), holder.image.getHeight()) - .centerCrop() - .intoImageView(holder.image) - .withBitmapInfo() - .setCallback(new FutureCallback() { + holder.albumArt.setTag( + Glide.with(activity) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(album.id)) + .error(R.drawable.default_album_art) + .listener(new RequestListener() { @Override - public void onCompleted(Exception e, ImageViewBitmapInfo result) { - if (result != null) { - BitmapInfo info = result.getBitmapInfo(); - if (info != null) { - Bitmap bitmap = info.bitmap; - if (bitmap != null) { - if (usePalette) - applyPalette(bitmap, holder.title, holder.artist, holder.footer); - return; - } - } - } - holder.image.setImageResource(R.drawable.default_album_art); + public boolean onException(Exception e, Uri model, Target target, boolean isFirstResource) { if (usePalette) - paletteBlackAndWhite(holder.title, holder.artist, holder.footer); + applyPalette(null, holder.title, holder.artist, holder.footer); + return false; + } + + @Override + public boolean onResourceReady(GlideDrawable resource, Uri model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + if (usePalette) + applyPalette(((GlideBitmapDrawable) resource).getBitmap(), holder.title, holder.artist, holder.footer); + return false; } }) + .into(holder.albumArt) + .getRequest() ); } @@ -101,14 +98,14 @@ public class AlbumAdapter extends RecyclerView.Adapter } public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener { - final ImageView image; + final ImageView albumArt; final TextView title; final TextView artist; final View footer; public ViewHolder(View itemView) { super(itemView); - image = (ImageView) itemView.findViewById(R.id.album_art); + albumArt = (ImageView) itemView.findViewById(R.id.album_art); title = (TextView) itemView.findViewById(R.id.album_title); artist = (TextView) itemView.findViewById(R.id.album_interpret); footer = itemView.findViewById(R.id.footer); @@ -118,7 +115,7 @@ public class AlbumAdapter extends RecyclerView.Adapter @Override public void onClick(View v) { Pair[] albumPairs = new Pair[]{ - Pair.create(image, + Pair.create(albumArt, activity.getResources().getString(R.string.transition_album_cover) )}; if (activity instanceof AbsFabActivity) @@ -138,20 +135,24 @@ public class AlbumAdapter extends RecyclerView.Adapter } private void applyPalette(Bitmap bitmap, final TextView title, final TextView artist, final View footer) { - Palette.from(bitmap) - .generate(new Palette.PaletteAsyncListener() { - @Override - public void onGenerated(Palette palette) { - final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); - if (vibrantSwatch != null) { - title.setTextColor(vibrantSwatch.getTitleTextColor()); - artist.setTextColor(vibrantSwatch.getTitleTextColor()); - ViewUtil.animateViewColor(footer, DialogUtils.resolveColor(activity, R.attr.default_bar_color), vibrantSwatch.getRgb()); - } else { - paletteBlackAndWhite(title, artist, footer); + if (bitmap != null) { + Palette.from(bitmap) + .generate(new Palette.PaletteAsyncListener() { + @Override + public void onGenerated(Palette palette) { + final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); + if (vibrantSwatch != null) { + title.setTextColor(vibrantSwatch.getTitleTextColor()); + artist.setTextColor(vibrantSwatch.getTitleTextColor()); + ViewUtil.animateViewColor(footer, DialogUtils.resolveColor(activity, R.attr.default_bar_color), vibrantSwatch.getRgb()); + } else { + paletteBlackAndWhite(title, artist, footer); + } } - } - }); + }); + } else { + paletteBlackAndWhite(title, artist, footer); + } } private void paletteBlackAndWhite(final TextView title, final TextView artist, final View footer) { diff --git a/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAdapter.java b/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAdapter.java index c707b6b7..cb183818 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAdapter.java +++ b/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAdapter.java @@ -1,7 +1,6 @@ package com.kabouzeid.gramophone.adapter; import android.app.Activity; -import android.graphics.Bitmap; import android.support.v4.util.Pair; import android.support.v7.widget.RecyclerView; import android.view.LayoutInflater; @@ -10,6 +9,7 @@ import android.view.ViewGroup; import android.widget.ImageView; import android.widget.TextView; +import com.bumptech.glide.Glide; import com.kabouzeid.gramophone.App; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.lastfm.artist.LastFMArtistThumbnailUrlLoader; @@ -17,9 +17,8 @@ import com.kabouzeid.gramophone.loader.ArtistLoader; import com.kabouzeid.gramophone.model.Artist; import com.kabouzeid.gramophone.model.DataBaseChangedEvent; import com.kabouzeid.gramophone.ui.activities.base.AbsFabActivity; +import com.kabouzeid.gramophone.util.MusicUtil; import com.kabouzeid.gramophone.util.NavigationUtil; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; import com.squareup.otto.Subscribe; import java.util.List; @@ -51,25 +50,16 @@ public class ArtistAdapter extends RecyclerView.Adapter() { - @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) - holder.artistImage.setImageBitmap(result); - else { - holder.artistImage.setImageResource(R.drawable.default_artist_image); - } - } - }); + .error(R.drawable.default_artist_image) + .into(holder.artistImage); } }); } diff --git a/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAlbumAdapter.java b/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAlbumAdapter.java index 73888c16..b738b070 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAlbumAdapter.java +++ b/app/src/main/java/com/kabouzeid/gramophone/adapter/ArtistAlbumAdapter.java @@ -9,12 +9,13 @@ import android.view.ViewGroup; import android.widget.ImageView; import android.widget.TextView; +import com.bumptech.glide.Glide; +import com.bumptech.glide.request.Request; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.model.Album; import com.kabouzeid.gramophone.ui.activities.base.AbsFabActivity; import com.kabouzeid.gramophone.util.MusicUtil; import com.kabouzeid.gramophone.util.NavigationUtil; -import com.koushikdutta.ion.Ion; import java.util.List; @@ -44,17 +45,25 @@ public class ArtistAlbumAdapter extends RecyclerView.Adapter { +public class SearchAdapter extends RecyclerView.Adapter { + private Activity activity; - private final AppCompatActivity activity; - - public SearchAdapter(AppCompatActivity activity, List objects) { - super(activity, R.layout.item_list_search, objects); + public SearchAdapter(AppCompatActivity activity) { this.activity = activity; } @Override - public View getView(int position, View convertView, ViewGroup parent) { - if (convertView == null) { - convertView = LayoutInflater.from(getContext()).inflate(R.layout.item_list_search, parent, false); + public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { + return null; + } + + @Override + public void onBindViewHolder(ViewHolder holder, int position) { + + } + + @Override + public int getItemCount() { + return 0; + } + + public class ViewHolder extends RecyclerView.ViewHolder { + public ViewHolder(View itemView) { + super(itemView); } - - final SearchEntry item = getItem(position); - - final TextView title = (TextView) convertView.findViewById(R.id.title); - final TextView subTitle = (TextView) convertView.findViewById(R.id.sub_title); - final ImageView imageView = (ImageView) convertView.findViewById(R.id.image); - final ImageView overflowButton = (ImageView) convertView.findViewById(R.id.menu); - - if (item instanceof SearchActivity.LabelEntry) { - title.setTypeface(null, Typeface.BOLD); - subTitle.setVisibility(View.GONE); - imageView.setVisibility(View.GONE); - overflowButton.setVisibility(View.GONE); - convertView.setBackgroundColor(DialogUtils.resolveColor(getContext(), R.attr.default_bar_color)); - } else if (item instanceof Song) { - title.setTypeface(null, Typeface.NORMAL); - subTitle.setVisibility(View.VISIBLE); - imageView.setVisibility(View.GONE); - convertView.setBackgroundColor(Color.TRANSPARENT); - overflowButton.setVisibility(View.VISIBLE); - overflowButton.setOnClickListener(new View.OnClickListener() { - @Override - public void onClick(View view) { - PopupMenu popupMenu = new PopupMenu(activity, view); - popupMenu.inflate(R.menu.menu_item_song); - popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() { - @Override - public boolean onMenuItemClick(MenuItem menuItem) { - return MenuItemClickHelper.handleSongMenuClick(activity, (Song) item, menuItem); - } - }); - popupMenu.show(); - } - }); - } else { - title.setTypeface(null, Typeface.NORMAL); - subTitle.setVisibility(View.VISIBLE); - imageView.setVisibility(View.VISIBLE); - overflowButton.setVisibility(View.GONE); - convertView.setBackgroundColor(Color.TRANSPARENT); - } - - title.setText(item.getTitle()); - subTitle.setText(item.getSubTitle()); - - imageView.setImageBitmap(null); - item.loadImage(getContext(), imageView); - - return convertView; } } diff --git a/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/ArtistSongAdapter.java b/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/ArtistSongAdapter.java index 08e6686e..929d9bdf 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/ArtistSongAdapter.java +++ b/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/ArtistSongAdapter.java @@ -11,13 +11,13 @@ import android.widget.ImageView; import android.widget.PopupMenu; import android.widget.TextView; +import com.bumptech.glide.Glide; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.helper.MenuItemClickHelper; import com.kabouzeid.gramophone.model.Song; import com.kabouzeid.gramophone.ui.activities.base.AbsFabActivity; import com.kabouzeid.gramophone.util.MusicUtil; import com.kabouzeid.gramophone.util.NavigationUtil; -import com.koushikdutta.ion.Ion; import java.util.List; @@ -47,13 +47,10 @@ public class ArtistSongAdapter extends ArrayAdapter { songTitle.setText(song.title); songInfo.setText(song.albumName); - Ion.with(activity) - .load(MusicUtil.getAlbumArtUri(song.albumId).toString()) - .withBitmap() - .resize(albumArt.getWidth(), albumArt.getHeight()) - .centerCrop() + Glide.with(activity) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(song.albumId)) .error(R.drawable.default_album_art) - .intoImageView(albumArt); + .into(albumArt); final ImageView overflowButton = (ImageView) convertView.findViewById(R.id.menu); overflowButton.setOnClickListener(new View.OnClickListener() { diff --git a/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/PlaylistSongAdapter.java b/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/PlaylistSongAdapter.java index 67c55576..6785b829 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/PlaylistSongAdapter.java +++ b/app/src/main/java/com/kabouzeid/gramophone/adapter/songadapter/PlaylistSongAdapter.java @@ -11,6 +11,8 @@ import android.widget.ImageView; import android.widget.PopupMenu; import android.widget.TextView; +import com.bumptech.glide.Glide; +import com.bumptech.glide.request.Request; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.helper.MenuItemClickHelper; import com.kabouzeid.gramophone.helper.MusicPlayerRemote; @@ -20,7 +22,6 @@ import com.kabouzeid.gramophone.ui.activities.base.AbsFabActivity; import com.kabouzeid.gramophone.util.MusicUtil; import com.kabouzeid.gramophone.util.NavigationUtil; import com.kabouzeid.gramophone.util.PlaylistsUtil; -import com.koushikdutta.ion.Ion; import java.util.ArrayList; import java.util.List; @@ -48,6 +49,10 @@ public class PlaylistSongAdapter extends RecyclerView.Adapter { return new ViewHolder(view); } + @Override + public void onViewRecycled(ViewHolder holder) { + super.onViewRecycled(holder); + Object tag = holder.albumArt.getTag(); + if (tag instanceof Request) { + ((Request) tag).clear(); + } + } + @Override public int getItemViewType(int position) { return position == 0 ? SHUFFLE_BUTTON : SONG; @@ -67,14 +77,13 @@ public class SongAdapter extends RecyclerView.Adapter { holder.songTitle.setText(song.title); holder.songInfo.setText(song.artistName); - - Ion.with(activity) - .load(MusicUtil.getAlbumArtUri(song.albumId).toString()) - .withBitmap() - .resize(holder.albumArt.getWidth(), holder.albumArt.getHeight()) - .centerCrop() - .error(R.drawable.default_album_art) - .intoImageView(holder.albumArt); + holder.albumArt.setTag( + Glide.with(activity) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(song.albumId)) + .error(R.drawable.default_album_art) + .into(holder.albumArt) + .getRequest() + ); } else { holder.songTitle.setText(activity.getResources().getString(R.string.shuffle_all).toUpperCase()); holder.songTitle.setTextColor(ThemeSingleton.get().positiveColor); diff --git a/app/src/main/java/com/kabouzeid/gramophone/appwidget/MusicPlayerWidget.java b/app/src/main/java/com/kabouzeid/gramophone/appwidget/MusicPlayerWidget.java index 93a0cedb..38cc4de7 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/appwidget/MusicPlayerWidget.java +++ b/app/src/main/java/com/kabouzeid/gramophone/appwidget/MusicPlayerWidget.java @@ -7,21 +7,23 @@ import android.content.ComponentName; import android.content.Context; import android.content.Intent; import android.graphics.Bitmap; +import android.net.Uri; import android.widget.RemoteViews; +import com.bumptech.glide.Glide; +import com.bumptech.glide.request.Request; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.helper.MusicPlayerRemote; import com.kabouzeid.gramophone.model.Song; import com.kabouzeid.gramophone.service.MusicService; import com.kabouzeid.gramophone.ui.activities.MusicControllerActivity; import com.kabouzeid.gramophone.util.MusicUtil; -import com.koushikdutta.async.future.Future; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; public class MusicPlayerWidget extends AppWidgetProvider { private static RemoteViews widgetLayout; - private static Future albumArtTask; + private static Request albumArtRequest; @Override public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) { @@ -59,27 +61,35 @@ public class MusicPlayerWidget extends AppWidgetProvider { } private static void loadAlbumArt(final Context context, final Song song) { - if (albumArtTask != null) albumArtTask.cancel(); - albumArtTask = Ion.with(context) - .load(MusicUtil.getAlbumArtUri(song.albumId).toString()) - .noCache() + if (albumArtRequest != null) albumArtRequest.clear(); + final int notificationAlbumArtSize = context.getResources().getDimensionPixelSize(R.dimen.app_widget_small_artwork_height); + albumArtRequest = Glide.with(context) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(song.albumId)) .asBitmap() - .setCallback(new FutureCallback() { + .skipMemoryCache(true) + .listener(new RequestListener() { @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) setAlbumArt(context, result); - else resetAlbumArt(context); + public boolean onException(Exception e, Uri model, Target target, boolean isFirstResource) { + setAlbumArt(context, null); + return false; } - }); - } - private static void resetAlbumArt(final Context context) { - widgetLayout.setImageViewResource(R.id.album_art, R.drawable.default_album_art); - updateWidgets(context); + @Override + public boolean onResourceReady(Bitmap resource, Uri model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + setAlbumArt(context, resource); + return false; + } + }) + .into(notificationAlbumArtSize, notificationAlbumArtSize) + .getRequest(); } private static void setAlbumArt(final Context context, final Bitmap albumArt) { - widgetLayout.setImageViewBitmap(R.id.album_art, albumArt); + if (albumArt != null) { + widgetLayout.setImageViewBitmap(R.id.album_art, albumArt); + } else { + widgetLayout.setImageViewResource(R.id.album_art, R.drawable.default_album_art); + } updateWidgets(context); } diff --git a/app/src/main/java/com/kabouzeid/gramophone/dialogs/DeleteSongsDialog.java b/app/src/main/java/com/kabouzeid/gramophone/dialogs/DeleteSongsDialog.java index 582c346c..9f5e8619 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/dialogs/DeleteSongsDialog.java +++ b/app/src/main/java/com/kabouzeid/gramophone/dialogs/DeleteSongsDialog.java @@ -44,7 +44,7 @@ public class DeleteSongsDialog extends DialogFragment { content = Html.fromHtml(getString(R.string.delete_x_songs, songs.size())); } else { title = R.string.delete_song_title; - content = Html.fromHtml(getString(R.string.delete_song_x, songs.get(0).getTitle())); + content = Html.fromHtml(getString(R.string.delete_song_x, songs.get(0).title)); } return new MaterialDialog.Builder(getActivity()) .title(title) diff --git a/app/src/main/java/com/kabouzeid/gramophone/helper/PlayingNotificationHelper.java b/app/src/main/java/com/kabouzeid/gramophone/helper/PlayingNotificationHelper.java index fa91ae85..02b4fc8a 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/helper/PlayingNotificationHelper.java +++ b/app/src/main/java/com/kabouzeid/gramophone/helper/PlayingNotificationHelper.java @@ -12,17 +12,19 @@ import android.content.ComponentName; import android.content.Context; import android.content.Intent; import android.graphics.Bitmap; +import android.net.Uri; import android.support.v4.app.NotificationCompat; import android.widget.RemoteViews; +import com.bumptech.glide.Glide; +import com.bumptech.glide.request.Request; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.model.Song; import com.kabouzeid.gramophone.service.MusicService; import com.kabouzeid.gramophone.ui.activities.MusicControllerActivity; import com.kabouzeid.gramophone.util.MusicUtil; -import com.koushikdutta.async.future.Future; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; public class PlayingNotificationHelper { @@ -37,7 +39,8 @@ public class PlayingNotificationHelper { private RemoteViews notificationLayout; private RemoteViews notificationLayoutExpanded; - private Future albumArtTask; + private Request albumArtRequest; + private Song currentSong; public PlayingNotificationHelper(final MusicService service) { this.service = service; @@ -46,6 +49,7 @@ public class PlayingNotificationHelper { } public void buildNotification(final Song song, final boolean isPlaying) { + currentSong = song; notificationLayout = new RemoteViews(service.getPackageName(), R.layout.notification_playing); notificationLayoutExpanded = new RemoteViews(service.getPackageName(), @@ -61,9 +65,9 @@ public class PlayingNotificationHelper { .build(); notification.bigContentView = notificationLayoutExpanded; - setUpCollapsedLayout(song); - setUpExpandedLayout(song); - loadAlbumArt(song); + setUpCollapsedLayout(); + setUpExpandedLayout(); + loadAlbumArt(); setUpPlaybackActions(isPlaying); setUpExpandedPlaybackActions(isPlaying); @@ -140,41 +144,55 @@ public class PlayingNotificationHelper { return null; } - private void setUpCollapsedLayout(final Song song) { - notificationLayout.setTextViewText(R.id.song_title, song.title); - notificationLayout.setTextViewText(R.id.song_artist, song.artistName); + private void setUpCollapsedLayout() { + if (currentSong != null) { + notificationLayout.setTextViewText(R.id.song_title, currentSong.title); + notificationLayout.setTextViewText(R.id.song_artist, currentSong.artistName); + } } - private void setUpExpandedLayout(final Song song) { - notificationLayoutExpanded.setTextViewText(R.id.song_title, song.title); - notificationLayoutExpanded.setTextViewText(R.id.song_artist, song.artistName); - notificationLayoutExpanded.setTextViewText(R.id.album_title, song.albumName); + private void setUpExpandedLayout() { + if (currentSong != null) { + notificationLayoutExpanded.setTextViewText(R.id.song_title, currentSong.title); + notificationLayoutExpanded.setTextViewText(R.id.song_artist, currentSong.artistName); + notificationLayoutExpanded.setTextViewText(R.id.album_title, currentSong.albumName); + } } - private void loadAlbumArt(final Song song) { - if (albumArtTask != null) albumArtTask.cancel(); - albumArtTask = Ion.with(service) - .load(MusicUtil.getAlbumArtUri(song.albumId).toString()) - .noCache() - .asBitmap() - .setCallback(new FutureCallback() { - @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) setAlbumArt(result); - else resetAlbumArt(); - } - }); - } + private void loadAlbumArt() { + if (currentSong != null) { + if (albumArtRequest != null) albumArtRequest.clear(); + final int notificationAlbumArtSize = service.getResources().getDimensionPixelSize(R.dimen.notification_albumart_size); + albumArtRequest = Glide.with(service) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(currentSong.albumId)) + .asBitmap() + .skipMemoryCache(true) + .listener(new RequestListener() { + @Override + public boolean onException(Exception e, Uri model, Target target, boolean isFirstResource) { + setAlbumArt(null); + return false; + } - private void resetAlbumArt() { - notificationLayout.setImageViewResource(R.id.album_art, R.drawable.default_album_art); - notificationLayoutExpanded.setImageViewResource(R.id.album_art, R.drawable.default_album_art); - notificationManager.notify(NOTIFICATION_ID, notification); + @Override + public boolean onResourceReady(Bitmap resource, Uri model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + setAlbumArt(resource); + return false; + } + }) + .into(notificationAlbumArtSize, notificationAlbumArtSize) + .getRequest(); + } } private void setAlbumArt(Bitmap albumArt) { - notificationLayout.setImageViewBitmap(R.id.album_art, albumArt); - notificationLayoutExpanded.setImageViewBitmap(R.id.album_art, albumArt); + if (albumArt != null) { + notificationLayout.setImageViewBitmap(R.id.album_art, albumArt); + notificationLayoutExpanded.setImageViewBitmap(R.id.album_art, albumArt); + } else { + notificationLayout.setImageViewResource(R.id.album_art, R.drawable.default_album_art); + notificationLayoutExpanded.setImageViewResource(R.id.album_art, R.drawable.default_album_art); + } notificationManager.notify(NOTIFICATION_ID, notification); } diff --git a/app/src/main/java/com/kabouzeid/gramophone/model/Album.java b/app/src/main/java/com/kabouzeid/gramophone/model/Album.java index a8d12426..3ab4d6cf 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/model/Album.java +++ b/app/src/main/java/com/kabouzeid/gramophone/model/Album.java @@ -1,16 +1,9 @@ package com.kabouzeid.gramophone.model; -import android.content.Context; -import android.widget.ImageView; - -import com.kabouzeid.gramophone.R; -import com.kabouzeid.gramophone.util.MusicUtil; -import com.koushikdutta.ion.Ion; - /** * @author Karim Abou Zeid (kabouzeid) */ -public class Album implements SearchEntry { +public class Album { public final int id; public int artistId; @@ -36,31 +29,4 @@ public class Album implements SearchEntry { songCount = -1; year = -1; } - - @Override - public String getTitle() { - return title; - } - - @Override - public String getSubTitle() { - return artistName; - } - - @Override - public void loadImage(final Context context, final ImageView imageView) { - imageView.setImageResource(R.drawable.default_album_art); - imageView.post(new Runnable() { - @Override - public void run() { - Ion.with(context) - .load(MusicUtil.getAlbumArtUri(id).toString()) - .withBitmap() - .resize(imageView.getWidth(), imageView.getHeight()) - .centerCrop() - .error(R.drawable.default_album_art) - .intoImageView(imageView); - } - }); - } } diff --git a/app/src/main/java/com/kabouzeid/gramophone/model/Artist.java b/app/src/main/java/com/kabouzeid/gramophone/model/Artist.java index 958e0993..48911ec6 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/model/Artist.java +++ b/app/src/main/java/com/kabouzeid/gramophone/model/Artist.java @@ -1,16 +1,9 @@ package com.kabouzeid.gramophone.model; -import android.content.Context; -import android.widget.ImageView; - -import com.kabouzeid.gramophone.R; -import com.kabouzeid.gramophone.lastfm.artist.LastFMArtistThumbnailUrlLoader; -import com.koushikdutta.ion.Ion; - /** * @author Karim Abou Zeid (kabouzeid) */ -public class Artist implements SearchEntry { +public class Artist { public final int id; public final String name; public final int albumCount; @@ -29,36 +22,4 @@ public class Artist implements SearchEntry { songCount = -1; albumCount = -1; } - - @Override - public String getTitle() { - return name; - } - - @Override - public String getSubTitle() { - return songCount + " Songs | " + albumCount + " Albums"; - } - - @Override - public void loadImage(final Context context, final ImageView imageView) { - imageView.setImageResource(R.drawable.default_artist_image); - LastFMArtistThumbnailUrlLoader.loadArtistThumbnailUrl(context, name, false, new LastFMArtistThumbnailUrlLoader.ArtistThumbnailUrlLoaderCallback() { - @Override - public void onArtistThumbnailUrlLoaded(final String url) { - imageView.post(new Runnable() { - @Override - public void run() { - Ion.with(context) - .load(url) - .withBitmap() - .resize(imageView.getWidth(), imageView.getHeight()) - .centerCrop() - .error(R.drawable.default_artist_image) - .intoImageView(imageView); - } - }); - } - }); - } } diff --git a/app/src/main/java/com/kabouzeid/gramophone/model/SearchEntry.java b/app/src/main/java/com/kabouzeid/gramophone/model/SearchEntry.java deleted file mode 100644 index c5a7ea86..00000000 --- a/app/src/main/java/com/kabouzeid/gramophone/model/SearchEntry.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.kabouzeid.gramophone.model; - -import android.content.Context; -import android.widget.ImageView; - -/** - * @author Karim Abou Zeid (kabouzeid) - */ -public interface SearchEntry { - String getTitle(); - - String getSubTitle(); - - void loadImage(Context context, ImageView imageView); -} diff --git a/app/src/main/java/com/kabouzeid/gramophone/model/Song.java b/app/src/main/java/com/kabouzeid/gramophone/model/Song.java index b7787f1b..58007c3d 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/model/Song.java +++ b/app/src/main/java/com/kabouzeid/gramophone/model/Song.java @@ -1,14 +1,11 @@ package com.kabouzeid.gramophone.model; -import android.content.Context; -import android.widget.ImageView; - import java.io.Serializable; /** * @author Karim Abou Zeid (kabouzeid) */ -public class Song implements Serializable, SearchEntry { +public class Song implements Serializable { public int id; public final int albumId; @@ -41,19 +38,4 @@ public class Song implements Serializable, SearchEntry { this.duration = -1; this.trackNumber = -1; } - - @Override - public String getTitle() { - return title; - } - - @Override - public String getSubTitle() { - return artistName; - } - - @Override - public void loadImage(Context context, ImageView imageView) { - - } } diff --git a/app/src/main/java/com/kabouzeid/gramophone/service/MusicService.java b/app/src/main/java/com/kabouzeid/gramophone/service/MusicService.java index 1a2da568..0599be39 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/service/MusicService.java +++ b/app/src/main/java/com/kabouzeid/gramophone/service/MusicService.java @@ -22,6 +22,10 @@ import android.preference.PreferenceManager; import android.util.Log; import android.widget.Toast; +import com.bumptech.glide.Glide; +import com.bumptech.glide.request.Request; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.kabouzeid.gramophone.App; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.appwidget.MusicPlayerWidget; @@ -32,9 +36,6 @@ import com.kabouzeid.gramophone.model.MusicRemoteEvent; import com.kabouzeid.gramophone.model.Song; import com.kabouzeid.gramophone.util.InternalStorageUtil; import com.kabouzeid.gramophone.util.MusicUtil; -import com.koushikdutta.async.future.Future; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; import java.io.IOException; import java.util.ArrayList; @@ -79,7 +80,7 @@ public class MusicService extends Service implements MediaPlayer.OnPreparedListe private PlayingNotificationHelper playingNotificationHelper; private AudioManager audioManager; private RemoteControlClient remoteControlClient; - private Future remoteControlClientAlbumArtTask; + private Request remoteControlClientAlbumArtRequest; private PowerManager.WakeLock wakeLock; public MusicService() { @@ -357,17 +358,26 @@ public class MusicService extends Service implements MediaPlayer.OnPreparedListe .putLong(MediaMetadataRetriever.METADATA_KEY_DURATION, song.duration) .apply(); - if (remoteControlClientAlbumArtTask != null) remoteControlClientAlbumArtTask.cancel(); - remoteControlClientAlbumArtTask = Ion.with(this) - .load(MusicUtil.getAlbumArtUri(song.albumId).toString()) - .noCache() + if (remoteControlClientAlbumArtRequest != null) remoteControlClientAlbumArtRequest.clear(); + remoteControlClientAlbumArtRequest = Glide.with(this) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(song.albumId)) .asBitmap() - .setCallback(new FutureCallback() { + .skipMemoryCache(true) + .listener(new RequestListener() { @Override - public void onCompleted(Exception e, Bitmap result) { - updateRemoteControlClientBitmap(result); + public boolean onException(Exception e, Uri model, Target target, boolean isFirstResource) { + updateRemoteControlClientBitmap(null); + return false; } - }); + + @Override + public boolean onResourceReady(Bitmap resource, Uri model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + updateRemoteControlClientBitmap(resource); + return false; + } + }) + .into(-1, -1) + .getRequest(); } private void updateRemoteControlClientBitmap(final Bitmap albumArt) { diff --git a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/AlbumDetailActivity.java b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/AlbumDetailActivity.java index a70cdb53..c17fa71f 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/AlbumDetailActivity.java +++ b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/AlbumDetailActivity.java @@ -4,6 +4,7 @@ import android.annotation.TargetApi; import android.content.Intent; import android.graphics.Bitmap; import android.graphics.Color; +import android.net.Uri; import android.os.Build; import android.os.Bundle; import android.support.v4.util.Pair; @@ -17,6 +18,11 @@ import android.widget.ImageView; import android.widget.TextView; import com.afollestad.materialdialogs.util.DialogUtils; +import com.bumptech.glide.Glide; +import com.bumptech.glide.load.resource.bitmap.GlideBitmapDrawable; +import com.bumptech.glide.load.resource.drawable.GlideDrawable; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.github.ksoichiro.android.observablescrollview.ObservableRecyclerView; import com.kabouzeid.gramophone.App; import com.kabouzeid.gramophone.R; @@ -37,8 +43,6 @@ import com.kabouzeid.gramophone.util.NavigationUtil; import com.kabouzeid.gramophone.util.PreferenceUtils; import com.kabouzeid.gramophone.util.Util; import com.kabouzeid.gramophone.util.ViewUtil; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; import com.nineoldandroids.view.ViewHelper; import com.squareup.otto.Subscribe; @@ -170,51 +174,54 @@ public class AlbumDetailActivity extends AbsFabActivity implements PaletteColorH } private void setUpAlbumArtAndApplyPalette() { - albumArtImageView.post(new Runnable() { - @Override - public void run() { - Ion.with(AlbumDetailActivity.this) - .load(MusicUtil.getAlbumArtUri(album.id).toString()) - .withBitmap() - .smartSize(false) - .asBitmap() - .setCallback(new FutureCallback() { - @TargetApi(Build.VERSION_CODES.LOLLIPOP) - @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) { - albumArtImageView.setImageBitmap(result); - applyPalette(result); - } else { - albumArtImageView.setImageResource(R.drawable.default_album_art); - resetColors(); - } - if (Util.isAtLeastLollipop()) startPostponedEnterTransition(); - } - }); - } - }); + Glide.with(AlbumDetailActivity.this) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(album.id)) + .error(R.drawable.default_album_art) + .listener(new RequestListener() { + @TargetApi(Build.VERSION_CODES.LOLLIPOP) + @Override + public boolean onException(Exception e, Uri model, Target target, boolean isFirstResource) { + applyPalette(null); + if (Util.isAtLeastLollipop()) startPostponedEnterTransition(); + return false; + } + + @TargetApi(Build.VERSION_CODES.LOLLIPOP) + @Override + public boolean onResourceReady(GlideDrawable resource, Uri model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + applyPalette(((GlideBitmapDrawable) resource).getBitmap()); + if (Util.isAtLeastLollipop()) startPostponedEnterTransition(); + // workaround for glide not working well with shared element, dont remove this redundant looking call! + albumArtImageView.setImageDrawable(resource); + return false; + } + }) + .into(albumArtImageView); } private void applyPalette(Bitmap bitmap) { - Palette.from(bitmap) - .generate(new Palette.PaletteAsyncListener() { - @TargetApi(Build.VERSION_CODES.LOLLIPOP) - @Override - public void onGenerated(Palette palette) { - final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); - if (vibrantSwatch != null) { - toolbarColor = vibrantSwatch.getRgb(); - albumTitleView.setBackgroundColor(toolbarColor); - albumTitleView.setTextColor(vibrantSwatch.getTitleTextColor()); - if (Util.isAtLeastLollipop() && PreferenceUtils.getInstance(AlbumDetailActivity.this).coloredNavigationBarAlbumEnabled()) - getWindow().setNavigationBarColor(toolbarColor); - notifyTaskColorChange(toolbarColor); - } else { - resetColors(); + if (bitmap != null) { + Palette.from(bitmap) + .generate(new Palette.PaletteAsyncListener() { + @TargetApi(Build.VERSION_CODES.LOLLIPOP) + @Override + public void onGenerated(Palette palette) { + final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); + if (vibrantSwatch != null) { + toolbarColor = vibrantSwatch.getRgb(); + albumTitleView.setBackgroundColor(toolbarColor); + albumTitleView.setTextColor(vibrantSwatch.getTitleTextColor()); + if (Util.isAtLeastLollipop() && PreferenceUtils.getInstance(AlbumDetailActivity.this).coloredNavigationBarAlbumEnabled()) + getWindow().setNavigationBarColor(toolbarColor); + notifyTaskColorChange(toolbarColor); + } else { + resetColors(); + } } - } - }); + }); + } else { + resetColors(); + } } @TargetApi(Build.VERSION_CODES.LOLLIPOP) diff --git a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/ArtistDetailActivity.java b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/ArtistDetailActivity.java index 66a4d809..c3fec718 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/ArtistDetailActivity.java +++ b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/ArtistDetailActivity.java @@ -24,6 +24,11 @@ import android.widget.Toast; import com.afollestad.materialdialogs.MaterialDialog; import com.afollestad.materialdialogs.util.DialogUtils; +import com.bumptech.glide.Glide; +import com.bumptech.glide.load.resource.bitmap.GlideBitmapDrawable; +import com.bumptech.glide.load.resource.drawable.GlideDrawable; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.github.ksoichiro.android.observablescrollview.ObservableListView; import com.kabouzeid.gramophone.App; import com.kabouzeid.gramophone.R; @@ -47,8 +52,6 @@ import com.kabouzeid.gramophone.util.NavigationUtil; import com.kabouzeid.gramophone.util.PreferenceUtils; import com.kabouzeid.gramophone.util.Util; import com.kabouzeid.gramophone.util.ViewUtil; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; import com.nineoldandroids.view.ViewHelper; import com.squareup.otto.Subscribe; @@ -265,51 +268,50 @@ public class ArtistDetailActivity extends AbsFabActivity implements PaletteColor LastFMArtistImageUrlLoader.loadArtistImageUrl(this, artist.name, forceDownload, new LastFMArtistImageUrlLoader.ArtistImageUrlLoaderCallback() { @Override public void onArtistImageUrlLoaded(final String url) { - artistImage.post(new Runnable() { - @Override - public void run() { - Ion.with(ArtistDetailActivity.this) - .load(url) - .withBitmap() - .smartSize(false) - .asBitmap() - .setCallback(new FutureCallback() { - @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) { - artistImage.setImageBitmap(result); - applyPalette(result); - } else { - artistImage.setImageResource(R.drawable.default_artist_image); - resetColors(); - } - } - }); - } - }); + Glide.with(ArtistDetailActivity.this) + .load(url) + .error(R.drawable.default_artist_image) + .listener(new RequestListener() { + @Override + public boolean onException(Exception e, String model, Target target, boolean isFirstResource) { + applyPalette(null); + return false; + } + + @Override + public boolean onResourceReady(GlideDrawable resource, String model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + applyPalette(((GlideBitmapDrawable) resource).getBitmap()); + return false; + } + }) + .into(artistImage); } }); } private void applyPalette(Bitmap bitmap) { - Palette.from(bitmap) - .generate(new Palette.PaletteAsyncListener() { - @TargetApi(Build.VERSION_CODES.LOLLIPOP) - @Override - public void onGenerated(Palette palette) { - final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); - if (vibrantSwatch != null) { - toolbarColor = vibrantSwatch.getRgb(); - artistNameTv.setBackgroundColor(vibrantSwatch.getRgb()); - artistNameTv.setTextColor(vibrantSwatch.getTitleTextColor()); - if (Util.isAtLeastLollipop() && PreferenceUtils.getInstance(ArtistDetailActivity.this).coloredNavigationBarArtistEnabled()) - getWindow().setNavigationBarColor(vibrantSwatch.getRgb()); - notifyTaskColorChange(toolbarColor); - } else { - resetColors(); + if (bitmap != null) { + Palette.from(bitmap) + .generate(new Palette.PaletteAsyncListener() { + @TargetApi(Build.VERSION_CODES.LOLLIPOP) + @Override + public void onGenerated(Palette palette) { + final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); + if (vibrantSwatch != null) { + toolbarColor = vibrantSwatch.getRgb(); + artistNameTv.setBackgroundColor(vibrantSwatch.getRgb()); + artistNameTv.setTextColor(vibrantSwatch.getTitleTextColor()); + if (Util.isAtLeastLollipop() && PreferenceUtils.getInstance(ArtistDetailActivity.this).coloredNavigationBarArtistEnabled()) + getWindow().setNavigationBarColor(vibrantSwatch.getRgb()); + notifyTaskColorChange(toolbarColor); + } else { + resetColors(); + } } - } - }); + }); + } else { + resetColors(); + } } @Override diff --git a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MainActivity.java b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MainActivity.java index f74edee7..1ad7b956 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MainActivity.java +++ b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MainActivity.java @@ -2,7 +2,6 @@ package com.kabouzeid.gramophone.ui.activities; import android.content.Intent; import android.content.res.Configuration; -import android.graphics.Bitmap; import android.net.Uri; import android.os.Bundle; import android.os.Handler; @@ -28,6 +27,7 @@ import android.widget.FrameLayout; import com.afollestad.materialdialogs.ThemeSingleton; import com.astuetz.PagerSlidingTabStrip; +import com.bumptech.glide.Glide; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.adapter.PagerAdapter; import com.kabouzeid.gramophone.dialogs.AboutDialog; @@ -49,8 +49,6 @@ import com.kabouzeid.gramophone.util.NavigationUtil; import com.kabouzeid.gramophone.util.PreferenceUtils; import com.kabouzeid.gramophone.util.Util; import com.kabouzeid.gramophone.util.ViewUtil; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; import java.lang.reflect.Field; import java.util.ArrayList; @@ -204,22 +202,13 @@ public class MainActivity extends AbsFabActivity if (navigationDrawerFragment != null) { Song song = MusicPlayerRemote.getCurrentSong(); if (song.id != -1) { - Ion.with(this) - .load(MusicUtil.getAlbumArtUri(song.albumId).toString()) - .withBitmap() - .smartSize(false) - .asBitmap() - .setCallback(new FutureCallback() { - @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) - navigationDrawerFragment.getAlbumArtImageView().setImageBitmap(result); - else - navigationDrawerFragment.getAlbumArtImageView().setImageResource(R.drawable.default_album_art); - } - }); navigationDrawerFragment.getSongTitle().setText(song.title); navigationDrawerFragment.getSongArtist().setText(song.artistName); + Glide.with(this) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(song.albumId)) + .error(R.drawable.default_album_art) + .placeholder(R.drawable.default_album_art) + .into(navigationDrawerFragment.getAlbumArtImageView()); } } } diff --git a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MusicControllerActivity.java b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MusicControllerActivity.java index 48d3ac1d..4410c585 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MusicControllerActivity.java +++ b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/MusicControllerActivity.java @@ -5,6 +5,7 @@ import android.content.Intent; import android.content.res.ColorStateList; import android.graphics.Bitmap; import android.graphics.PorterDuff; +import android.net.Uri; import android.os.Build; import android.os.Bundle; import android.support.v7.graphics.Palette; @@ -22,6 +23,11 @@ import android.widget.Toast; import com.afollestad.materialdialogs.ThemeSingleton; import com.afollestad.materialdialogs.util.DialogUtils; +import com.bumptech.glide.Glide; +import com.bumptech.glide.load.resource.bitmap.GlideBitmapDrawable; +import com.bumptech.glide.load.resource.drawable.GlideDrawable; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.kabouzeid.gramophone.App; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.dialogs.AddToPlaylistDialog; @@ -41,8 +47,6 @@ import com.kabouzeid.gramophone.util.NavigationUtil; import com.kabouzeid.gramophone.util.PreferenceUtils; import com.kabouzeid.gramophone.util.Util; import com.kabouzeid.gramophone.util.ViewUtil; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; import com.nineoldandroids.view.ViewPropertyAnimator; import com.squareup.otto.Subscribe; @@ -56,7 +60,7 @@ public class MusicControllerActivity extends AbsFabActivity { private Song song; private ImageView albumArt; - private ImageView artistArt; + private ImageView artistImage; private TextView songTitle; private TextView songArtist; private TextView currentSongProgress; @@ -118,7 +122,7 @@ public class MusicControllerActivity extends AbsFabActivity { repeatButton = (ImageButton) findViewById(R.id.repeat_button); shuffleButton = (ImageButton) findViewById(R.id.shuffle_button); albumArt = (ImageView) findViewById(R.id.album_art); - artistArt = (ImageView) findViewById(R.id.artist_image); + artistImage = (ImageView) findViewById(R.id.artist_image); songTitle = (TextView) findViewById(R.id.song_title); songArtist = (TextView) findViewById(R.id.song_artist); currentSongProgress = (TextView) findViewById(R.id.song_current_progress); @@ -294,48 +298,47 @@ public class MusicControllerActivity extends AbsFabActivity { } private void setUpAlbumArtAndApplyPalette() { - albumArt.post(new Runnable() { - @Override - public void run() { - Ion.with(MusicControllerActivity.this) - .load(MusicUtil.getAlbumArtUri(song.albumId).toString()) - .withBitmap() - .smartSize(false) - .asBitmap() - .setCallback(new FutureCallback() { - @TargetApi(Build.VERSION_CODES.LOLLIPOP) - @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) { - albumArt.setImageBitmap(result); - applyPalette(result); - } else { - albumArt.setImageResource(R.drawable.default_album_art); - resetColors(); - } - } - }); - } - }); + Glide.with(this) + .loadFromMediaStore(MusicUtil.getAlbumArtUri(song.albumId)) + .error(R.drawable.default_album_art) + .placeholder(R.drawable.default_album_art) + .listener(new RequestListener() { + @Override + public boolean onException(Exception e, Uri model, Target target, boolean isFirstResource) { + applyPalette(null); + return false; + } + + @Override + public boolean onResourceReady(GlideDrawable resource, Uri model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + applyPalette(((GlideBitmapDrawable) resource).getBitmap()); + return false; + } + }) + .into(albumArt); } private void applyPalette(Bitmap bitmap) { - Palette.from(bitmap) - .generate(new Palette.PaletteAsyncListener() { - @Override - public void onGenerated(Palette palette) { - final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); - if (vibrantSwatch != null) { - final int swatchRgb = vibrantSwatch.getRgb(); - animateColorChange(swatchRgb); - songTitle.setTextColor(vibrantSwatch.getTitleTextColor()); - songArtist.setTextColor(vibrantSwatch.getBodyTextColor()); - notifyTaskColorChange(swatchRgb); - } else { - resetColors(); + if (bitmap != null) { + Palette.from(bitmap) + .generate(new Palette.PaletteAsyncListener() { + @Override + public void onGenerated(Palette palette) { + final Palette.Swatch vibrantSwatch = palette.getVibrantSwatch(); + if (vibrantSwatch != null) { + final int swatchRgb = vibrantSwatch.getRgb(); + animateColorChange(swatchRgb); + songTitle.setTextColor(vibrantSwatch.getTitleTextColor()); + songArtist.setTextColor(vibrantSwatch.getBodyTextColor()); + notifyTaskColorChange(swatchRgb); + } else { + resetColors(); + } } - } - }); + }); + } else { + resetColors(); + } } private void resetColors() { @@ -364,14 +367,15 @@ public class MusicControllerActivity extends AbsFabActivity { } private void setUpArtistArt() { - if (artistArt != null) { - artistArt.setImageResource(R.drawable.default_artist_image); + if (artistImage != null) { + artistImage.setImageResource(R.drawable.default_artist_image); LastFMArtistImageUrlLoader.loadArtistImageUrl(this, song.artistName, false, new LastFMArtistImageUrlLoader.ArtistImageUrlLoaderCallback() { @Override public void onArtistImageUrlLoaded(String url) { - Ion.with(artistArt) + Glide.with(MusicControllerActivity.this) + .load(url) .error(R.drawable.default_artist_image) - .load(url); + .into(artistImage); } }); } diff --git a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/SearchActivity.java b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/SearchActivity.java index 8453b661..d8327793 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/SearchActivity.java +++ b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/SearchActivity.java @@ -2,49 +2,33 @@ package com.kabouzeid.gramophone.ui.activities; import android.annotation.SuppressLint; import android.app.ActionBar; -import android.content.Context; import android.graphics.PorterDuff; import android.graphics.drawable.Drawable; import android.os.Build; import android.os.Bundle; import android.support.v4.content.ContextCompat; -import android.support.v4.util.Pair; import android.support.v4.view.MenuItemCompat; +import android.support.v7.widget.RecyclerView; import android.support.v7.widget.SearchView; import android.support.v7.widget.Toolbar; import android.view.Menu; import android.view.MenuItem; import android.view.MotionEvent; import android.view.View; -import android.widget.AdapterView; -import android.widget.ArrayAdapter; -import android.widget.ImageView; -import android.widget.ListView; import com.afollestad.materialdialogs.ThemeSingleton; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.adapter.SearchAdapter; -import com.kabouzeid.gramophone.helper.MusicPlayerRemote; -import com.kabouzeid.gramophone.loader.AlbumLoader; -import com.kabouzeid.gramophone.loader.ArtistLoader; -import com.kabouzeid.gramophone.loader.SongLoader; -import com.kabouzeid.gramophone.model.Album; -import com.kabouzeid.gramophone.model.Artist; -import com.kabouzeid.gramophone.model.SearchEntry; -import com.kabouzeid.gramophone.model.Song; import com.kabouzeid.gramophone.ui.activities.base.AbsBaseActivity; -import com.kabouzeid.gramophone.util.NavigationUtil; import com.kabouzeid.gramophone.util.PreferenceUtils; import com.kabouzeid.gramophone.util.Util; -import java.util.ArrayList; -import java.util.List; - public class SearchActivity extends AbsBaseActivity { public static final String TAG = SearchActivity.class.getSimpleName(); - private ListView listView; + private RecyclerView recyclerView; private SearchView searchView; + private SearchAdapter searchAdapter; @SuppressLint("NewApi") @Override @@ -54,38 +38,11 @@ public class SearchActivity extends AbsBaseActivity { super.onCreate(savedInstanceState); setContentView(R.layout.activity_search); - listView = (ListView) findViewById(R.id.list); - listView.setOnItemClickListener(new AdapterView.OnItemClickListener() { - @Override - public void onItemClick(AdapterView parent, View view, int position, long id) { - Object item = parent.getItemAtPosition(position); - if (item instanceof SearchEntry) { - if (item instanceof Song) { - ArrayList playList = new ArrayList<>(); - playList.add((Song) item); - MusicPlayerRemote.openQueue(playList, 0, true); - } else if (item instanceof Album) { - NavigationUtil.goToAlbum(SearchActivity.this, - ((Album) item).id, - new Pair[]{ - Pair.create(view.findViewById(R.id.image), - getResources().getString(R.string.transition_album_cover) - ) - }); - } else if (item instanceof Artist) { - NavigationUtil.goToArtist(SearchActivity.this, - ((Artist) item).id, - new Pair[]{ - Pair.create(view.findViewById(R.id.image), - getResources().getString(R.string.transition_artist_image) - ) - }); - } - } - } - }); + recyclerView = (RecyclerView) findViewById(R.id.recycler_view); + searchAdapter = new SearchAdapter(this); + recyclerView.setAdapter(searchAdapter); - listView.setOnTouchListener(new View.OnTouchListener() { + recyclerView.setOnTouchListener(new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { Util.hideSoftKeyboard(SearchActivity.this); @@ -120,13 +77,13 @@ public class SearchActivity extends AbsBaseActivity { @Override public void enableViews() { super.enableViews(); - listView.setEnabled(true); + recyclerView.setEnabled(true); } @Override public void disableViews() { super.disableViews(); - listView.setEnabled(false); + recyclerView.setEnabled(false); } @Override @@ -192,65 +149,6 @@ public class SearchActivity extends AbsBaseActivity { } private void search(String query) { - List results = new ArrayList<>(); - if (!query.trim().equals("")) { - LabelEntry songLabel = new LabelEntry(getResources().getString(R.string.songs).toUpperCase()); - results.add(songLabel); - List songs = SongLoader.getSongs(this, query); - results.addAll(songs); - songLabel.setNumber(songs.size()); - LabelEntry artistLabel = new LabelEntry(getResources().getString(R.string.artists).toUpperCase()); - results.add(artistLabel); - List artists = ArtistLoader.getArtists(this, query); - results.addAll(artists); - artistLabel.setNumber(artists.size()); - - LabelEntry albumLabel = new LabelEntry(getResources().getString(R.string.albums).toUpperCase()); - results.add(albumLabel); - List albums = AlbumLoader.getAlbums(this, query); - results.addAll(albums); - albumLabel.setNumber(albums.size()); - } - if (results.size() <= 3) { - results.clear(); - results.add(new LabelEntry(getResources().getString(R.string.no_results).toUpperCase())); - } - ArrayAdapter adapter = new SearchAdapter(this, results); - listView.setAdapter(adapter); - } - - - public static class LabelEntry implements SearchEntry { - final String title; - String label; - - public LabelEntry(String label) { - this.label = label; - this.title = label; - } - - public void setNumber(int number) { - if (number != -1) { - label = title + " (" + number + ")"; - } else { - label = title; - } - } - - @Override - public String getTitle() { - return label; - } - - @Override - public String getSubTitle() { - return ""; - } - - @Override - public void loadImage(Context context, ImageView imageView) { - - } } } diff --git a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AbsTagEditorActivity.java b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AbsTagEditorActivity.java index 367bd9cc..d5511b15 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AbsTagEditorActivity.java +++ b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AbsTagEditorActivity.java @@ -32,7 +32,6 @@ import com.kabouzeid.gramophone.util.MusicUtil; import com.kabouzeid.gramophone.util.PreferenceUtils; import com.kabouzeid.gramophone.util.Util; import com.kabouzeid.gramophone.util.ViewUtil; -import com.koushikdutta.ion.Ion; import com.melnykov.fab.FloatingActionButton; import com.nineoldandroids.view.ViewHelper; import com.nineoldandroids.view.ViewPropertyAnimator; @@ -378,11 +377,9 @@ public abstract class AbsTagEditorActivity extends AbsBaseActivity { } if (deleteArtwork) { MusicUtil.deleteAlbumArt(AbsTagEditorActivity.this, getId()); - Ion.getDefault(AbsTagEditorActivity.this).getBitmapCache().clear(); - Ion.getDefault(AbsTagEditorActivity.this).getCache().clear(); + //Glide.get(AbsTagEditorActivity.this).clearMemory(); } else if (artwork != null) { - Ion.getDefault(AbsTagEditorActivity.this).getBitmapCache().clear(); - Ion.getDefault(AbsTagEditorActivity.this).getCache().clear(); + //Glide.get(AbsTagEditorActivity.this).clearMemory(); } runOnUiThread(new Runnable() { @Override diff --git a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AlbumTagEditorActivity.java b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AlbumTagEditorActivity.java index 5209dba7..748fb619 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AlbumTagEditorActivity.java +++ b/app/src/main/java/com/kabouzeid/gramophone/ui/activities/tageditor/AlbumTagEditorActivity.java @@ -9,14 +9,15 @@ import android.util.Log; import android.widget.EditText; import android.widget.Toast; +import com.bumptech.glide.Glide; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.Target; import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.lastfm.album.LastFMAlbumImageUrlLoader; import com.kabouzeid.gramophone.loader.AlbumSongLoader; import com.kabouzeid.gramophone.loader.SongFilePathLoader; import com.kabouzeid.gramophone.model.Song; import com.kabouzeid.gramophone.util.MusicUtil; -import com.koushikdutta.async.future.FutureCallback; -import com.koushikdutta.ion.Ion; import org.jaudiotagger.tag.FieldKey; import org.jaudiotagger.tag.images.Artwork; @@ -94,17 +95,22 @@ public class AlbumTagEditorActivity extends AbsTagEditorActivity implements Text LastFMAlbumImageUrlLoader.loadAlbumImageUrl(this, albumTitleStr, albumArtistNameStr, new LastFMAlbumImageUrlLoader.AlbumImageUrlLoaderCallback() { @Override public void onAlbumImageUrlLoaded(String url) { - Ion.with(AlbumTagEditorActivity.this) + Glide.with(AlbumTagEditorActivity.this) .load(url) - .withBitmap() - .resize(500, 500) - .centerCrop() .asBitmap() - .setCallback(new FutureCallback() { + .centerCrop() + .listener(new RequestListener() { @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) { - albumArtBitmap = result; + public boolean onException(Exception e, String model, Target target, boolean isFirstResource) { + Toast.makeText(AlbumTagEditorActivity.this, + R.string.failed_download_albumart, Toast.LENGTH_SHORT).show(); + return false; + } + + @Override + public boolean onResourceReady(Bitmap resource, String model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + if (resource != null) { + albumArtBitmap = resource; setImageBitmap(albumArtBitmap); deleteAlbumArt = false; dataChanged(); @@ -113,8 +119,10 @@ public class AlbumTagEditorActivity extends AbsTagEditorActivity implements Text Toast.makeText(AlbumTagEditorActivity.this, R.string.failed_download_albumart, Toast.LENGTH_SHORT).show(); } + return false; } - }); + }) + .into(500, 500); } @Override @@ -183,24 +191,29 @@ public class AlbumTagEditorActivity extends AbsTagEditorActivity implements Text @Override protected void loadImageFromFile(final Uri selectedFileUri) { - Ion.with(this) - .load(selectedFileUri.toString()) - .withBitmap() - .resize(500, 500) - .centerCrop() + Glide.with(this) + .load(selectedFileUri) .asBitmap() - .setCallback(new FutureCallback() { + .centerCrop() + .listener(new RequestListener() { @Override - public void onCompleted(Exception e, Bitmap result) { - if (result != null) { - albumArtBitmap = result; + public boolean onException(Exception e, Uri model, Target target, boolean isFirstResource) { + return false; + } + + @Override + public boolean onResourceReady(Bitmap resource, Uri model, Target target, boolean isFromMemoryCache, boolean isFirstResource) { + if (resource != null) { + albumArtBitmap = resource; setImageBitmap(albumArtBitmap); deleteAlbumArt = false; dataChanged(); setResult(RESULT_OK); } + return false; } - }); + }) + .into(500, 500); } @Override diff --git a/app/src/main/java/com/kabouzeid/gramophone/util/MusicUtil.java b/app/src/main/java/com/kabouzeid/gramophone/util/MusicUtil.java index 628116a7..21ec2c4e 100644 --- a/app/src/main/java/com/kabouzeid/gramophone/util/MusicUtil.java +++ b/app/src/main/java/com/kabouzeid/gramophone/util/MusicUtil.java @@ -13,13 +13,14 @@ import android.util.Log; import android.widget.Toast; import com.kabouzeid.gramophone.App; +import com.kabouzeid.gramophone.R; import com.kabouzeid.gramophone.helper.MusicPlayerRemote; import com.kabouzeid.gramophone.loader.SongLoader; +import com.kabouzeid.gramophone.model.Artist; import com.kabouzeid.gramophone.model.DataBaseChangedEvent; import com.kabouzeid.gramophone.model.Song; import java.io.File; -import java.io.FileNotFoundException; import java.io.IOException; import java.util.List; @@ -36,14 +37,8 @@ public class MusicUtil { return ContentUris.withAppendedId(sArtworkUri, album_id); } - public static boolean hasAlbumArt(final Context context, int album_id) { - try { - context.getContentResolver().openFileDescriptor(getAlbumArtUri(album_id), "r"); - } catch (FileNotFoundException e) { - e.printStackTrace(); - return false; - } - return true; + public static String getArtistInfoString(Context context, Artist artist) { + return artist.songCount + " " + context.getResources().getString(R.string.songs) + " | " + artist.albumCount + " " + context.getResources().getString(R.string.albums); } public static String getReadableDurationString(long songDurationMillis) { diff --git a/app/src/main/res/drawable-v21/rect_ripple_selector.xml b/app/src/main/res/drawable-v21/rect_ripple_selector.xml deleted file mode 100644 index 38c78380..00000000 --- a/app/src/main/res/drawable-v21/rect_ripple_selector.xml +++ /dev/null @@ -1,6 +0,0 @@ - - - - - \ No newline at end of file diff --git a/app/src/main/res/drawable-v21/rect_ripple_selector_dark.xml b/app/src/main/res/drawable-v21/rect_ripple_selector_dark.xml deleted file mode 100644 index 8ad440dd..00000000 --- a/app/src/main/res/drawable-v21/rect_ripple_selector_dark.xml +++ /dev/null @@ -1,6 +0,0 @@ - - - - - \ No newline at end of file diff --git a/app/src/main/res/drawable-v21/round_ripple_selector.xml b/app/src/main/res/drawable-v21/round_ripple_selector.xml index f5688ca1..8b0fd07b 100644 --- a/app/src/main/res/drawable-v21/round_ripple_selector.xml +++ b/app/src/main/res/drawable-v21/round_ripple_selector.xml @@ -1,6 +1,6 @@ + xmlns:android="http://schemas.android.com/apk/res/android" + android:color="?android:colorControlHighlight"> diff --git a/app/src/main/res/drawable-v21/round_ripple_selector_dark.xml b/app/src/main/res/drawable-v21/round_ripple_selector_dark.xml index ec08d4ab..da232ca5 100644 --- a/app/src/main/res/drawable-v21/round_ripple_selector_dark.xml +++ b/app/src/main/res/drawable-v21/round_ripple_selector_dark.xml @@ -1,5 +1,5 @@ + android:color="?android:colorControlHighlight"> diff --git a/app/src/main/res/layout/activity_search.xml b/app/src/main/res/layout/activity_search.xml index b2f03341..475ec169 100644 --- a/app/src/main/res/layout/activity_search.xml +++ b/app/src/main/res/layout/activity_search.xml @@ -1,8 +1,8 @@ + xmlns:app="http://schemas.android.com/apk/res-auto" + android:layout_width="match_parent" + android:layout_height="match_parent" + android:orientation="vertical"> - + android:scrollbars="vertical" /> diff --git a/app/src/main/res/layout/notification_playing_expanded.xml b/app/src/main/res/layout/notification_playing_expanded.xml index e522c18d..263e5102 100644 --- a/app/src/main/res/layout/notification_playing_expanded.xml +++ b/app/src/main/res/layout/notification_playing_expanded.xml @@ -24,8 +24,8 @@ @drawable/round_ripple_selector_dark - @drawable/rect_ripple_selector_dark + ?selectableItemBackground @drawable/list_ripple_selector_dark @android:color/transparent @@ -10,7 +10,7 @@