Cleaned up MusicService and MusicPlayerRemote even more.
This commit is contained in:
parent
049bf90620
commit
60cae85ecb
7 changed files with 200 additions and 169 deletions
|
|
@ -30,10 +30,13 @@ public class App extends Application {
|
||||||
public void onCreate() {
|
public void onCreate() {
|
||||||
super.onCreate();
|
super.onCreate();
|
||||||
if (!BuildConfig.DEBUG) Fabric.with(this, new Crashlytics());
|
if (!BuildConfig.DEBUG) Fabric.with(this, new Crashlytics());
|
||||||
MusicPlayerRemote.init(this);
|
|
||||||
|
MusicPlayerRemote.startAndBindService(this);
|
||||||
|
|
||||||
ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(this).build();
|
ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(this).build();
|
||||||
ImageLoader.getInstance().init(config);
|
ImageLoader.getInstance().init(config);
|
||||||
L.writeLogs(false); // turns off UILs annoying LogCat output
|
L.writeLogs(false); // turns off UILs annoying LogCat output
|
||||||
|
|
||||||
TagOptionSingleton.getInstance().isAndroid();
|
TagOptionSingleton.getInstance().isAndroid();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -5,18 +5,13 @@ import android.content.Context;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.content.ServiceConnection;
|
import android.content.ServiceConnection;
|
||||||
import android.media.audiofx.AudioEffect;
|
import android.media.audiofx.AudioEffect;
|
||||||
import android.net.Uri;
|
|
||||||
import android.os.IBinder;
|
import android.os.IBinder;
|
||||||
import android.preference.PreferenceManager;
|
|
||||||
import android.util.Log;
|
|
||||||
import android.widget.Toast;
|
import android.widget.Toast;
|
||||||
|
|
||||||
import com.kabouzeid.gramophone.R;
|
import com.kabouzeid.gramophone.R;
|
||||||
import com.kabouzeid.gramophone.loader.SongLoader;
|
import com.kabouzeid.gramophone.loader.SongLoader;
|
||||||
import com.kabouzeid.gramophone.misc.AppKeys;
|
|
||||||
import com.kabouzeid.gramophone.model.Song;
|
import com.kabouzeid.gramophone.model.Song;
|
||||||
import com.kabouzeid.gramophone.service.MusicService;
|
import com.kabouzeid.gramophone.service.MusicService;
|
||||||
import com.kabouzeid.gramophone.util.InternalStorageUtil;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
@ -27,25 +22,18 @@ import java.util.Random;
|
||||||
*/
|
*/
|
||||||
public class MusicPlayerRemote {
|
public class MusicPlayerRemote {
|
||||||
|
|
||||||
private static final String TAG = MusicPlayerRemote.class.getSimpleName();
|
public static final String TAG = MusicPlayerRemote.class.getSimpleName();
|
||||||
|
|
||||||
private static int position = -1;
|
public static final String SERVICE_BOUND = "com.kabouzeid.gramophone.SERVICE_BOUND";
|
||||||
private static boolean startAfterConnected = false;
|
|
||||||
|
|
||||||
private static ArrayList<Song> playingQueue;
|
|
||||||
private static ArrayList<Song> restoredOriginalQueue;
|
|
||||||
|
|
||||||
private static Context context;
|
|
||||||
private static MusicService musicService;
|
private static MusicService musicService;
|
||||||
private static Intent musicServiceIntent;
|
|
||||||
|
|
||||||
private static final ServiceConnection musicConnection = new ServiceConnection() {
|
private static final ServiceConnection musicConnection = new ServiceConnection() {
|
||||||
@Override
|
@Override
|
||||||
public void onServiceConnected(ComponentName name, IBinder service) {
|
public void onServiceConnected(ComponentName name, IBinder service) {
|
||||||
MusicService.MusicBinder binder = (MusicService.MusicBinder) service;
|
MusicService.MusicBinder binder = (MusicService.MusicBinder) service;
|
||||||
musicService = binder.getService();
|
musicService = binder.getService();
|
||||||
musicService.restorePreviousState(restoredOriginalQueue, playingQueue, position);
|
musicService.sendBroadcast(new Intent(SERVICE_BOUND));
|
||||||
if (startAfterConnected) resumePlaying();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -54,20 +42,14 @@ public class MusicPlayerRemote {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
public static void init(final Context context) {
|
public static void startAndBindService(final Context context) {
|
||||||
MusicPlayerRemote.context = context;
|
Intent musicServiceIntent = new Intent(context, MusicService.class);
|
||||||
playingQueue = new ArrayList<>();
|
context.bindService(musicServiceIntent, musicConnection, Context.BIND_AUTO_CREATE);
|
||||||
restoredOriginalQueue = new ArrayList<>();
|
context.startService(musicServiceIntent);
|
||||||
startAndBindService();
|
|
||||||
restorePreviousState();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void startAndBindService() {
|
public static boolean isServiceConnected() {
|
||||||
if (musicServiceIntent == null) {
|
return musicService != null;
|
||||||
musicServiceIntent = new Intent(context, MusicService.class);
|
|
||||||
context.bindService(musicServiceIntent, musicConnection, Context.BIND_AUTO_CREATE);
|
|
||||||
context.startService(musicServiceIntent);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void playSongAt(final int position) {
|
public static void playSongAt(final int position) {
|
||||||
|
|
@ -111,11 +93,8 @@ public class MusicPlayerRemote {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void openQueue(final ArrayList<Song> playingQueue, final int startPosition, final boolean startPlaying) {
|
public static void openQueue(final ArrayList<Song> playingQueue, final int startPosition, final boolean startPlaying) {
|
||||||
MusicPlayerRemote.playingQueue = playingQueue;
|
|
||||||
position = startPosition;
|
|
||||||
startAfterConnected = startPlaying;
|
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.openQueue(MusicPlayerRemote.playingQueue, startPosition, startPlaying);
|
musicService.openAndPlayQueue(playingQueue, startPosition, startPlaying);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -123,25 +102,21 @@ public class MusicPlayerRemote {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
return musicService.getCurrentSong();
|
return musicService.getCurrentSong();
|
||||||
}
|
}
|
||||||
try {
|
|
||||||
return getPlayingQueue().get(getPosition());
|
|
||||||
} catch (Exception ignored) {
|
|
||||||
}
|
|
||||||
return new Song();
|
return new Song();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int getPosition() {
|
public static int getPosition() {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
position = musicService.getPosition();
|
return musicService.getPosition();
|
||||||
}
|
}
|
||||||
return position;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Song> getPlayingQueue() {
|
public static ArrayList<Song> getPlayingQueue() {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
playingQueue = musicService.getPlayingQueue();
|
return musicService.getPlayingQueue();
|
||||||
}
|
}
|
||||||
return playingQueue;
|
return new ArrayList<>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int getSongProgressMillis() {
|
public static int getSongProgressMillis() {
|
||||||
|
|
@ -168,26 +143,30 @@ public class MusicPlayerRemote {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
return musicService.getRepeatMode();
|
return musicService.getRepeatMode();
|
||||||
}
|
}
|
||||||
return PreferenceManager.getDefaultSharedPreferences(context).getInt(AppKeys.SP_REPEAT_MODE, 0);
|
return MusicService.REPEAT_MODE_NONE;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int getShuffleMode() {
|
public static int getShuffleMode() {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
return musicService.getShuffleMode();
|
return musicService.getShuffleMode();
|
||||||
}
|
}
|
||||||
return PreferenceManager.getDefaultSharedPreferences(context).getInt(AppKeys.SP_SHUFFLE_MODE, 0);
|
return MusicService.SHUFFLE_MODE_NONE;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void cycleRepeatMode() {
|
public static boolean cycleRepeatMode() {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.cycleRepeatMode();
|
musicService.cycleRepeatMode();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void toggleShuffleMode() {
|
public static boolean toggleShuffleMode() {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.toggleShuffle();
|
musicService.toggleShuffle();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static boolean setShuffleMode(final int shuffleMode) {
|
public static boolean setShuffleMode(final int shuffleMode) {
|
||||||
|
|
@ -198,103 +177,78 @@ public class MusicPlayerRemote {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void forceSetShuffleMode(final Context context, final int shuffleMode) {
|
public static boolean shuffleAllSongs(final Context context) {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.setShuffleMode(shuffleMode);
|
ArrayList<Song> songs = SongLoader.getAllSongs(context);
|
||||||
} else {
|
if (!songs.isEmpty()) {
|
||||||
PreferenceManager.getDefaultSharedPreferences(context).edit()
|
MusicPlayerRemote.openQueue(songs, new Random().nextInt(songs.size()), true);
|
||||||
.putInt(AppKeys.SP_SHUFFLE_MODE, shuffleMode)
|
setShuffleMode(MusicService.SHUFFLE_MODE_SHUFFLE);
|
||||||
.apply();
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void shuffleAllSongs(final Context context) {
|
public static boolean playNext(Song song) {
|
||||||
ArrayList<Song> songs = SongLoader.getAllSongs(context);
|
|
||||||
if (!songs.isEmpty()) {
|
|
||||||
MusicPlayerRemote.openQueue(songs, new Random().nextInt(songs.size()), true);
|
|
||||||
forceSetShuffleMode(context, MusicService.SHUFFLE_MODE_SHUFFLE);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void playNext(Song song) {
|
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.addSong(getPosition() + 1, song);
|
musicService.addSong(getPosition() + 1, song);
|
||||||
Toast.makeText(musicService, musicService.getResources().getString(R.string.added_title_to_playing_queue), Toast.LENGTH_SHORT).show();
|
Toast.makeText(musicService, musicService.getResources().getString(R.string.added_title_to_playing_queue), Toast.LENGTH_SHORT).show();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void enqueue(Song song) {
|
public static boolean enqueue(Song song) {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.addSong(song);
|
musicService.addSong(song);
|
||||||
Toast.makeText(musicService, musicService.getResources().getString(R.string.added_title_to_playing_queue), Toast.LENGTH_SHORT).show();
|
Toast.makeText(musicService, musicService.getResources().getString(R.string.added_title_to_playing_queue), Toast.LENGTH_SHORT).show();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void enqueue(List<Song> songs) {
|
public static boolean enqueue(List<Song> songs) {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.addSongs(songs);
|
musicService.addSongs(songs);
|
||||||
final String toast = songs.size() == 1 ? musicService.getResources().getString(R.string.added_title_to_playing_queue) : musicService.getResources().getString(R.string.added_x_titles_to_playing_queue, songs.size());
|
final String toast = songs.size() == 1 ? musicService.getResources().getString(R.string.added_title_to_playing_queue) : musicService.getResources().getString(R.string.added_x_titles_to_playing_queue, songs.size());
|
||||||
Toast.makeText(musicService, toast, Toast.LENGTH_SHORT).show();
|
Toast.makeText(musicService, toast, Toast.LENGTH_SHORT).show();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void removeFromQueue(Song song) {
|
public static boolean removeFromQueue(Song song) {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.removeSong(song);
|
musicService.removeSong(song);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void removeFromQueue(int position) {
|
public static boolean removeFromQueue(int position) {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.removeSong(position);
|
musicService.removeSong(position);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void moveSong(int from, int to) {
|
public static boolean moveSong(int from, int to) {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
musicService.moveSong(from, to);
|
musicService.moveSong(from, to);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int getAudioSessionId() {
|
public static int getAudioSessionId() {
|
||||||
if (musicService != null) {
|
if (musicService != null) {
|
||||||
return musicService.getAudioSessionId();
|
return musicService.getAudioSessionId();
|
||||||
}
|
}
|
||||||
return AudioEffect.ERROR_BAD_VALUE;
|
return AudioEffect.ERROR_NO_INIT;
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
public static void playFile(String path) {
|
||||||
public static void restorePreviousState() {
|
|
||||||
try {
|
|
||||||
ArrayList<Song> restoredQueue = (ArrayList<Song>) InternalStorageUtil.readObject(context, AppKeys.IS_PLAYING_QUEUE);
|
|
||||||
ArrayList<Song> restoredOriginalQueue = (ArrayList<Song>) InternalStorageUtil.readObject(context, AppKeys.IS_ORIGINAL_PLAYING_QUEUE);
|
|
||||||
int restoredPosition = (int) InternalStorageUtil.readObject(context, AppKeys.IS_POSITION_IN_QUEUE);
|
|
||||||
|
|
||||||
if (musicService != null) {
|
|
||||||
musicService.restorePreviousState(restoredOriginalQueue, restoredQueue, restoredPosition);
|
|
||||||
}
|
|
||||||
|
|
||||||
playingQueue = restoredQueue;
|
|
||||||
MusicPlayerRemote.restoredOriginalQueue = restoredOriginalQueue;
|
|
||||||
position = restoredPosition;
|
|
||||||
} catch (Exception e) {
|
|
||||||
Log.e(TAG, "error while restoring music service state", e);
|
|
||||||
playingQueue = new ArrayList<>();
|
|
||||||
position = -1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void playFile(Uri uri) {
|
|
||||||
// if (musicService != null && uri != null) {
|
|
||||||
// String filename;
|
|
||||||
// String scheme = uri.getScheme();
|
|
||||||
// if ("file".equals(scheme)) {
|
|
||||||
// filename = uri.getPath();
|
|
||||||
// } else {
|
|
||||||
// filename = uri.toString();
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
//TODO
|
//TODO
|
||||||
Toast.makeText(context, "Sorry, this feature is not available yet!", Toast.LENGTH_SHORT).show();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -16,6 +16,9 @@ import com.kabouzeid.gramophone.util.PreferenceUtils;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.lang.ref.WeakReference;
|
import java.lang.ref.WeakReference;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author Andrew Neal, Karim Abou Zeid (kabouzeid)
|
||||||
|
*/
|
||||||
public class MultiPlayer implements MediaPlayer.OnErrorListener,
|
public class MultiPlayer implements MediaPlayer.OnErrorListener,
|
||||||
MediaPlayer.OnCompletionListener {
|
MediaPlayer.OnCompletionListener {
|
||||||
public static final String TAG = MultiPlayer.class.getSimpleName();
|
public static final String TAG = MultiPlayer.class.getSimpleName();
|
||||||
|
|
@ -41,13 +44,16 @@ public class MultiPlayer implements MediaPlayer.OnErrorListener,
|
||||||
/**
|
/**
|
||||||
* @param path The path of the file, or the http/rtsp URL of the stream
|
* @param path The path of the file, or the http/rtsp URL of the stream
|
||||||
* you want to play
|
* you want to play
|
||||||
|
* @return True if the <code>player</code> has been prepared and is
|
||||||
|
* ready to play, false otherwise
|
||||||
*/
|
*/
|
||||||
public void setDataSource(final String path) {
|
public boolean setDataSource(final String path) {
|
||||||
mIsInitialized = false;
|
mIsInitialized = false;
|
||||||
mIsInitialized = setDataSourceImpl(mCurrentMediaPlayer, path);
|
mIsInitialized = setDataSourceImpl(mCurrentMediaPlayer, path);
|
||||||
if (mIsInitialized) {
|
if (mIsInitialized) {
|
||||||
setNextDataSource(null);
|
setNextDataSource(null);
|
||||||
}
|
}
|
||||||
|
return mIsInitialized;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -234,6 +240,10 @@ public class MultiPlayer implements MediaPlayer.OnErrorListener,
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public boolean onError(final MediaPlayer mp, final int what, final int extra) {
|
public boolean onError(final MediaPlayer mp, final int what, final int extra) {
|
||||||
|
mIsInitialized = false;
|
||||||
|
mCurrentMediaPlayer.release();
|
||||||
|
mCurrentMediaPlayer = new MediaPlayer();
|
||||||
|
mCurrentMediaPlayer.setWakeMode(mService.get(), PowerManager.PARTIAL_WAKE_LOCK);
|
||||||
Toast.makeText(mService.get(), mService.get().getResources().getString(R.string.unplayable_file), Toast.LENGTH_SHORT).show();
|
Toast.makeText(mService.get(), mService.get().getResources().getString(R.string.unplayable_file), Toast.LENGTH_SHORT).show();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -48,6 +48,9 @@ import java.lang.ref.WeakReference;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author Karim Abou Zeid (kabouzeid), Andrew Neal
|
||||||
|
*/
|
||||||
public class MusicService extends Service {
|
public class MusicService extends Service {
|
||||||
public static final String PHONOGRAPH_PACKAGE_NAME = "com.kabouzeid.gramophone";
|
public static final String PHONOGRAPH_PACKAGE_NAME = "com.kabouzeid.gramophone";
|
||||||
public static final String MUSIC_PACKAGE_NAME = "com.android.music";
|
public static final String MUSIC_PACKAGE_NAME = "com.android.music";
|
||||||
|
|
@ -64,7 +67,9 @@ public class MusicService extends Service {
|
||||||
public static final String PLAYSTATE_CHANGED = "com.kabouzeid.gramophone.playstatechanged";
|
public static final String PLAYSTATE_CHANGED = "com.kabouzeid.gramophone.playstatechanged";
|
||||||
public static final String REPEATMODE_CHANGED = "com.kabouzeid.gramophone.repeatmodechanged";
|
public static final String REPEATMODE_CHANGED = "com.kabouzeid.gramophone.repeatmodechanged";
|
||||||
public static final String SHUFFLEMODE_CHANGED = "com.kabouzeid.gramophone.shufflemodechanged";
|
public static final String SHUFFLEMODE_CHANGED = "com.kabouzeid.gramophone.shufflemodechanged";
|
||||||
public static final String POSITION_IN_SONG_CHANGED = "com.kabouzeid.phonograph.positionchanged";
|
|
||||||
|
public static final String SETTING_GAPLESS_PLAYBACK_CHANGED = "com.kabouzeid.gramophone.SETTING_GAPLESS_PLAYBACK_CHANGED";
|
||||||
|
public static final String SETTING_GAPLESS_PLAYBACK_CHANGED_VALUE_EXTRA = "com.kabouzeid.gramophone.SETTING_GAPLESS_PLAYBACK_CHANGED_VALUE_EXTRA";
|
||||||
|
|
||||||
private static final int FOCUS_CHANGE = 5;
|
private static final int FOCUS_CHANGE = 5;
|
||||||
private static final int DUCK = 6;
|
private static final int DUCK = 6;
|
||||||
|
|
@ -93,11 +98,12 @@ public class MusicService extends Service {
|
||||||
private int shuffleMode;
|
private int shuffleMode;
|
||||||
private int repeatMode;
|
private int repeatMode;
|
||||||
private boolean pausedByTransientLossOfFocus;
|
private boolean pausedByTransientLossOfFocus;
|
||||||
private boolean thingsRegistered;
|
private boolean receiversAndRemoteControlClientRegistered;
|
||||||
private boolean saveQueuesAgain;
|
private boolean saveQueuesAgain;
|
||||||
private boolean isSavingQueues;
|
private boolean isSavingQueues;
|
||||||
private PlayingNotificationHelper playingNotificationHelper;
|
private PlayingNotificationHelper playingNotificationHelper;
|
||||||
private AudioManager audioManager;
|
private AudioManager audioManager;
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
private RemoteControlClient remoteControlClient;
|
private RemoteControlClient remoteControlClient;
|
||||||
private PowerManager.WakeLock wakeLock;
|
private PowerManager.WakeLock wakeLock;
|
||||||
private String currentAlbumArtUri;
|
private String currentAlbumArtUri;
|
||||||
|
|
@ -108,13 +114,22 @@ public class MusicService extends Service {
|
||||||
private final BroadcastReceiver becomingNoisyReceiver = new BroadcastReceiver() {
|
private final BroadcastReceiver becomingNoisyReceiver = new BroadcastReceiver() {
|
||||||
@Override
|
@Override
|
||||||
public void onReceive(Context context, Intent intent) {
|
public void onReceive(Context context, Intent intent) {
|
||||||
if (intent.getAction().compareTo(AudioManager.ACTION_AUDIO_BECOMING_NOISY) == 0) {
|
if (intent.getAction().equals(AudioManager.ACTION_AUDIO_BECOMING_NOISY)) {
|
||||||
pause(true);
|
pause(true);
|
||||||
pause(false);
|
pause(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
private final BroadcastReceiver gaplessPlaybackSettingChangedReceiver = new BroadcastReceiver() {
|
||||||
|
@Override
|
||||||
|
public void onReceive(Context context, Intent intent) {
|
||||||
|
if (intent.getAction().equals(SETTING_GAPLESS_PLAYBACK_CHANGED)) {
|
||||||
|
setGaplessPlaybackEnabled(intent.getBooleanExtra(SETTING_GAPLESS_PLAYBACK_CHANGED_VALUE_EXTRA, true));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
private final AudioManager.OnAudioFocusChangeListener audioFocusListener = new AudioManager.OnAudioFocusChangeListener() {
|
private final AudioManager.OnAudioFocusChangeListener audioFocusListener = new AudioManager.OnAudioFocusChangeListener() {
|
||||||
@Override
|
@Override
|
||||||
public void onAudioFocusChange(final int focusChange) {
|
public void onAudioFocusChange(final int focusChange) {
|
||||||
|
|
@ -127,6 +142,7 @@ public class MusicService extends Service {
|
||||||
super.onCreate();
|
super.onCreate();
|
||||||
playingQueue = new ArrayList<>();
|
playingQueue = new ArrayList<>();
|
||||||
originalPlayingQueue = new ArrayList<>();
|
originalPlayingQueue = new ArrayList<>();
|
||||||
|
|
||||||
playingNotificationHelper = new PlayingNotificationHelper(this);
|
playingNotificationHelper = new PlayingNotificationHelper(this);
|
||||||
|
|
||||||
shuffleMode = PreferenceManager.getDefaultSharedPreferences(this).getInt(AppKeys.SP_SHUFFLE_MODE, 0);
|
shuffleMode = PreferenceManager.getDefaultSharedPreferences(this).getInt(AppKeys.SP_SHUFFLE_MODE, 0);
|
||||||
|
|
@ -144,17 +160,19 @@ public class MusicService extends Service {
|
||||||
player = new MultiPlayer(this);
|
player = new MultiPlayer(this);
|
||||||
player.setHandler(playerHandler);
|
player.setHandler(playerHandler);
|
||||||
|
|
||||||
registerEverything();
|
registerReceiversAndRemoteControlClient();
|
||||||
|
|
||||||
|
restoreQueueAndPosition();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void registerEverything() {
|
private void registerReceiversAndRemoteControlClient() {
|
||||||
if (!thingsRegistered) {
|
if (!receiversAndRemoteControlClientRegistered) {
|
||||||
IntentFilter intentFilter = new IntentFilter();
|
registerReceiver(becomingNoisyReceiver, new IntentFilter(AudioManager.ACTION_AUDIO_BECOMING_NOISY));
|
||||||
intentFilter.addAction(AudioManager.ACTION_AUDIO_BECOMING_NOISY);
|
registerReceiver(gaplessPlaybackSettingChangedReceiver, new IntentFilter(SETTING_GAPLESS_PLAYBACK_CHANGED));
|
||||||
registerReceiver(becomingNoisyReceiver, intentFilter);
|
//noinspection deprecation
|
||||||
getAudioManager().registerMediaButtonEventReceiver(new ComponentName(getApplicationContext(), MediaButtonIntentReceiver.class));
|
getAudioManager().registerMediaButtonEventReceiver(new ComponentName(getApplicationContext(), MediaButtonIntentReceiver.class));
|
||||||
initRemoteControlClient();
|
initRemoteControlClient();
|
||||||
thingsRegistered = true;
|
receiversAndRemoteControlClientRegistered = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -165,6 +183,7 @@ public class MusicService extends Service {
|
||||||
return audioManager;
|
return audioManager;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
private void initRemoteControlClient() {
|
private void initRemoteControlClient() {
|
||||||
remoteControlClient = new RemoteControlClient(getMediaButtonIntent());
|
remoteControlClient = new RemoteControlClient(getMediaButtonIntent());
|
||||||
remoteControlClient.setTransportControlFlags(
|
remoteControlClient.setTransportControlFlags(
|
||||||
|
|
@ -210,7 +229,7 @@ public class MusicService extends Service {
|
||||||
stop();
|
stop();
|
||||||
break;
|
break;
|
||||||
case ACTION_QUIT:
|
case ACTION_QUIT:
|
||||||
killEverythingAndReleaseResources();
|
saveAndQuit();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -220,17 +239,9 @@ public class MusicService extends Service {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onDestroy() {
|
public void onDestroy() {
|
||||||
closeAudioEffectSession();
|
saveAndQuit();
|
||||||
unregisterEverything();
|
releaseResources();
|
||||||
|
wakeLock.release();
|
||||||
playerHandler.removeCallbacksAndMessages(null);
|
|
||||||
if (Build.VERSION.SDK_INT >= 18) {
|
|
||||||
handlerThread.quitSafely();
|
|
||||||
} else {
|
|
||||||
handlerThread.quit();
|
|
||||||
}
|
|
||||||
|
|
||||||
killEverythingAndReleaseResources();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -238,43 +249,51 @@ public class MusicService extends Service {
|
||||||
return musicBind;
|
return musicBind;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
private void unregisterReceiversAndRemoteControlClient() {
|
||||||
public boolean onUnbind(Intent intent) {
|
if (receiversAndRemoteControlClientRegistered) {
|
||||||
unregisterEverything();
|
|
||||||
killEverythingAndReleaseResources();
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void unregisterEverything() {
|
|
||||||
if (thingsRegistered) {
|
|
||||||
unregisterReceiver(becomingNoisyReceiver);
|
unregisterReceiver(becomingNoisyReceiver);
|
||||||
|
unregisterReceiver(gaplessPlaybackSettingChangedReceiver);
|
||||||
|
//noinspection deprecation
|
||||||
getAudioManager().unregisterRemoteControlClient(remoteControlClient);
|
getAudioManager().unregisterRemoteControlClient(remoteControlClient);
|
||||||
|
//noinspection deprecation
|
||||||
getAudioManager().unregisterMediaButtonEventReceiver(new ComponentName(getApplicationContext(), MediaButtonIntentReceiver.class));
|
getAudioManager().unregisterMediaButtonEventReceiver(new ComponentName(getApplicationContext(), MediaButtonIntentReceiver.class));
|
||||||
getAudioManager().abandonAudioFocus(audioFocusListener);
|
receiversAndRemoteControlClientRegistered = false;
|
||||||
thingsRegistered = false;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void killEverythingAndReleaseResources() {
|
private void saveAndQuit() {
|
||||||
|
unregisterReceiversAndRemoteControlClient();
|
||||||
|
closeAudioEffectSession();
|
||||||
stop();
|
stop();
|
||||||
playingNotificationHelper.killNotification();
|
playingNotificationHelper.killNotification();
|
||||||
savePosition();
|
savePosition();
|
||||||
saveQueues();
|
saveQueuesImpl();
|
||||||
stopSelf();
|
stopSelf();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void releaseResources() {
|
||||||
|
playerHandler.removeCallbacksAndMessages(null);
|
||||||
|
if (Build.VERSION.SDK_INT >= 18) {
|
||||||
|
handlerThread.quitSafely();
|
||||||
|
} else {
|
||||||
|
handlerThread.quit();
|
||||||
|
}
|
||||||
|
player.release();
|
||||||
|
player = null;
|
||||||
|
}
|
||||||
|
|
||||||
public void stop() {
|
public void stop() {
|
||||||
pausedByTransientLossOfFocus = false;
|
pausedByTransientLossOfFocus = false;
|
||||||
player.stop();
|
player.stop();
|
||||||
player.release();
|
|
||||||
notifyChange(PLAYSTATE_CHANGED);
|
notifyChange(PLAYSTATE_CHANGED);
|
||||||
|
getAudioManager().abandonAudioFocus(audioFocusListener);
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isPlayingAndNotFadingDown() {
|
public boolean isPlayingAndNotFadingDown() {
|
||||||
return player.isPlaying() && !isFadingDown;
|
return player.isPlaying() && !isFadingDown;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void saveQueues() {
|
public void saveQueuesImpl() {
|
||||||
try {
|
try {
|
||||||
InternalStorageUtil.writeObject(MusicService.this, AppKeys.IS_PLAYING_QUEUE, playingQueue);
|
InternalStorageUtil.writeObject(MusicService.this, AppKeys.IS_PLAYING_QUEUE, playingQueue);
|
||||||
InternalStorageUtil.writeObject(MusicService.this, AppKeys.IS_ORIGINAL_PLAYING_QUEUE, originalPlayingQueue);
|
InternalStorageUtil.writeObject(MusicService.this, AppKeys.IS_ORIGINAL_PLAYING_QUEUE, originalPlayingQueue);
|
||||||
|
|
@ -312,7 +331,7 @@ public class MusicService extends Service {
|
||||||
synchronized (this) {
|
synchronized (this) {
|
||||||
setPosition(position);
|
setPosition(position);
|
||||||
boolean prepared = openCurrent();
|
boolean prepared = openCurrent();
|
||||||
prepareNext();
|
if (prepared) prepareNext();
|
||||||
notifyChange(META_CHANGED);
|
notifyChange(META_CHANGED);
|
||||||
return prepared;
|
return prepared;
|
||||||
}
|
}
|
||||||
|
|
@ -321,8 +340,7 @@ public class MusicService extends Service {
|
||||||
private boolean openCurrent() {
|
private boolean openCurrent() {
|
||||||
synchronized (this) {
|
synchronized (this) {
|
||||||
try {
|
try {
|
||||||
player.setDataSource(getTrackUri(getCurrentSong()));
|
return player.setDataSource(getTrackUri(getCurrentSong()));
|
||||||
return true;
|
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
@ -389,6 +407,7 @@ public class MusicService extends Service {
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateRemoteControlClientBitmap(final Bitmap albumArt) {
|
private void updateRemoteControlClientBitmap(final Bitmap albumArt) {
|
||||||
|
//noinspection deprecation
|
||||||
remoteControlClient
|
remoteControlClient
|
||||||
.editMetadata(false)
|
.editMetadata(false)
|
||||||
.putBitmap(RemoteControlClient.MetadataEditor.BITMAP_KEY_ARTWORK, albumArt)
|
.putBitmap(RemoteControlClient.MetadataEditor.BITMAP_KEY_ARTWORK, albumArt)
|
||||||
|
|
@ -473,7 +492,7 @@ public class MusicService extends Service {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void openQueue(final ArrayList<Song> playingQueue, final int startPosition, final boolean startPlaying) {
|
public void openAndPlayQueue(final ArrayList<Song> playingQueue, final int startPosition, final boolean startPlaying) {
|
||||||
if (playingQueue != null && !playingQueue.isEmpty() && startPosition >= 0 && startPosition < playingQueue.size()) {
|
if (playingQueue != null && !playingQueue.isEmpty() && startPosition >= 0 && startPosition < playingQueue.size()) {
|
||||||
originalPlayingQueue = playingQueue;
|
originalPlayingQueue = playingQueue;
|
||||||
this.playingQueue = new ArrayList<>(originalPlayingQueue);
|
this.playingQueue = new ArrayList<>(originalPlayingQueue);
|
||||||
|
|
@ -505,7 +524,7 @@ public class MusicService extends Service {
|
||||||
isSavingQueues = true;
|
isSavingQueues = true;
|
||||||
do {
|
do {
|
||||||
saveQueuesAgain = false;
|
saveQueuesAgain = false;
|
||||||
saveQueues();
|
saveQueuesImpl();
|
||||||
} while (saveQueuesAgain);
|
} while (saveQueuesAgain);
|
||||||
isSavingQueues = false;
|
isSavingQueues = false;
|
||||||
}
|
}
|
||||||
|
|
@ -513,11 +532,21 @@ public class MusicService extends Service {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void restorePreviousState(final ArrayList<Song> originalPlayingQueue, final ArrayList<Song> playingQueue, int position) {
|
private void restoreQueueAndPosition() {
|
||||||
this.originalPlayingQueue = originalPlayingQueue;
|
try {
|
||||||
this.playingQueue = playingQueue;
|
@SuppressWarnings("unchecked")
|
||||||
this.position = position;
|
ArrayList<Song> restoredQueue = (ArrayList<Song>) InternalStorageUtil.readObject(this, AppKeys.IS_PLAYING_QUEUE);
|
||||||
saveState();
|
@SuppressWarnings("unchecked")
|
||||||
|
ArrayList<Song> restoredOriginalQueue = (ArrayList<Song>) InternalStorageUtil.readObject(this, AppKeys.IS_ORIGINAL_PLAYING_QUEUE);
|
||||||
|
int restoredPosition = (int) InternalStorageUtil.readObject(this, AppKeys.IS_POSITION_IN_QUEUE);
|
||||||
|
|
||||||
|
this.originalPlayingQueue = restoredOriginalQueue;
|
||||||
|
this.playingQueue = restoredQueue;
|
||||||
|
|
||||||
|
openTrackAndPrepareNextAt(restoredPosition);
|
||||||
|
} catch (IOException | ClassNotFoundException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void addSong(int position, Song song) {
|
public void addSong(int position, Song song) {
|
||||||
|
|
@ -620,7 +649,10 @@ public class MusicService extends Service {
|
||||||
playerHandler.removeMessages(FADE_DOWN_AND_PAUSE);
|
playerHandler.removeMessages(FADE_DOWN_AND_PAUSE);
|
||||||
playerHandler.sendEmptyMessage(FADE_UP_AND_RESUME);
|
playerHandler.sendEmptyMessage(FADE_UP_AND_RESUME);
|
||||||
} else {
|
} else {
|
||||||
if (player != null) player.setVolume(1f);
|
try {
|
||||||
|
player.setVolume(1f);
|
||||||
|
} catch (IllegalStateException ignored) {
|
||||||
|
}
|
||||||
playImpl();
|
playImpl();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -633,6 +665,7 @@ public class MusicService extends Service {
|
||||||
if (!player.isInitialized()) {
|
if (!player.isInitialized()) {
|
||||||
playSongAt(getPosition());
|
playSongAt(getPosition());
|
||||||
} else {
|
} else {
|
||||||
|
registerReceiversAndRemoteControlClient();
|
||||||
player.start();
|
player.start();
|
||||||
notifyChange(PLAYSTATE_CHANGED);
|
notifyChange(PLAYSTATE_CHANGED);
|
||||||
}
|
}
|
||||||
|
|
@ -769,6 +802,7 @@ public class MusicService extends Service {
|
||||||
final boolean isPlaying = isPlayingAndNotFadingDown();
|
final boolean isPlaying = isPlayingAndNotFadingDown();
|
||||||
playingNotificationHelper.updatePlayState(isPlaying);
|
playingNotificationHelper.updatePlayState(isPlaying);
|
||||||
MusicPlayerWidget.updateWidgetsPlayState(this, isPlaying);
|
MusicPlayerWidget.updateWidgetsPlayState(this, isPlaying);
|
||||||
|
//noinspection deprecation
|
||||||
remoteControlClient.setPlaybackState(isPlaying ? RemoteControlClient.PLAYSTATE_PLAYING : RemoteControlClient.PLAYSTATE_PAUSED);
|
remoteControlClient.setPlaybackState(isPlaying ? RemoteControlClient.PLAYSTATE_PLAYING : RemoteControlClient.PLAYSTATE_PAUSED);
|
||||||
} else if (what.equals(META_CHANGED)) {
|
} else if (what.equals(META_CHANGED)) {
|
||||||
updateNotification();
|
updateNotification();
|
||||||
|
|
@ -778,8 +812,6 @@ public class MusicService extends Service {
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getAudioSessionId() {
|
public int getAudioSessionId() {
|
||||||
if (player == null)
|
|
||||||
return AudioEffect.ERROR_BAD_VALUE;
|
|
||||||
return player.getAudioSessionId();
|
return player.getAudioSessionId();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -793,6 +825,14 @@ public class MusicService extends Service {
|
||||||
wakeLock.acquire(milli);
|
wakeLock.acquire(milli);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void setGaplessPlaybackEnabled(boolean setEnabled) {
|
||||||
|
if (setEnabled) {
|
||||||
|
prepareNext();
|
||||||
|
} else {
|
||||||
|
player.setNextDataSource(null);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public class MusicBinder extends Binder {
|
public class MusicBinder extends Binder {
|
||||||
public MusicService getService() {
|
public MusicService getService() {
|
||||||
return MusicService.this;
|
return MusicService.this;
|
||||||
|
|
@ -824,8 +864,7 @@ public class MusicService extends Service {
|
||||||
} else {
|
} else {
|
||||||
currentDuckVolume = .2f;
|
currentDuckVolume = .2f;
|
||||||
}
|
}
|
||||||
if (service.player != null)
|
service.player.setVolume(currentDuckVolume);
|
||||||
service.player.setVolume(currentDuckVolume);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNDUCK:
|
case UNDUCK:
|
||||||
|
|
@ -835,8 +874,7 @@ public class MusicService extends Service {
|
||||||
} else {
|
} else {
|
||||||
currentDuckVolume = 1.0f;
|
currentDuckVolume = 1.0f;
|
||||||
}
|
}
|
||||||
if (service.player != null)
|
service.player.setVolume(currentDuckVolume);
|
||||||
service.player.setVolume(currentDuckVolume);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case FADE_DOWN_AND_PAUSE:
|
case FADE_DOWN_AND_PAUSE:
|
||||||
|
|
@ -852,8 +890,7 @@ public class MusicService extends Service {
|
||||||
service.isFadingDown = false;
|
service.isFadingDown = false;
|
||||||
service.pause(true);
|
service.pause(true);
|
||||||
}
|
}
|
||||||
if (service.player != null)
|
service.player.setVolume(currentPlayPauseFadeVolume);
|
||||||
service.player.setVolume(currentPlayPauseFadeVolume);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case FADE_UP_AND_RESUME:
|
case FADE_UP_AND_RESUME:
|
||||||
|
|
@ -868,8 +905,10 @@ public class MusicService extends Service {
|
||||||
} else {
|
} else {
|
||||||
currentPlayPauseFadeVolume = 1.0f;
|
currentPlayPauseFadeVolume = 1.0f;
|
||||||
}
|
}
|
||||||
if (service.player != null)
|
try {
|
||||||
service.player.setVolume(currentPlayPauseFadeVolume);
|
service.player.setVolume(currentPlayPauseFadeVolume);
|
||||||
|
} catch (IllegalStateException ignored) {
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case TRACK_WENT_TO_NEXT:
|
case TRACK_WENT_TO_NEXT:
|
||||||
|
|
@ -893,7 +932,7 @@ public class MusicService extends Service {
|
||||||
case FOCUS_CHANGE:
|
case FOCUS_CHANGE:
|
||||||
switch (msg.arg1) {
|
switch (msg.arg1) {
|
||||||
case AudioManager.AUDIOFOCUS_GAIN:
|
case AudioManager.AUDIOFOCUS_GAIN:
|
||||||
service.registerEverything();
|
service.registerReceiversAndRemoteControlClient();
|
||||||
if (!service.isPlayingAndNotFadingDown() && service.pausedByTransientLossOfFocus) {
|
if (!service.isPlayingAndNotFadingDown() && service.pausedByTransientLossOfFocus) {
|
||||||
service.play(false);
|
service.play(false);
|
||||||
}
|
}
|
||||||
|
|
@ -904,7 +943,7 @@ public class MusicService extends Service {
|
||||||
case AudioManager.AUDIOFOCUS_LOSS:
|
case AudioManager.AUDIOFOCUS_LOSS:
|
||||||
// Lost focus for an unbounded amount of time: stop playback and release media player
|
// Lost focus for an unbounded amount of time: stop playback and release media player
|
||||||
service.pause(true);
|
service.pause(true);
|
||||||
service.unregisterEverything();
|
service.unregisterReceiversAndRemoteControlClient();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT:
|
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT:
|
||||||
|
|
|
||||||
|
|
@ -248,11 +248,6 @@ public class MainActivity extends AbsFabActivity
|
||||||
return TAG;
|
return TAG;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onResume() {
|
|
||||||
super.onResume();
|
|
||||||
updateNavigationDrawerHeader();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void updateNavigationDrawerHeader() {
|
private void updateNavigationDrawerHeader() {
|
||||||
Song song = MusicPlayerRemote.getCurrentSong();
|
Song song = MusicPlayerRemote.getCurrentSong();
|
||||||
|
|
@ -305,6 +300,12 @@ public class MainActivity extends AbsFabActivity
|
||||||
updateNavigationDrawerHeader();
|
updateNavigationDrawerHeader();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onServiceConnected() {
|
||||||
|
super.onServiceConnected();
|
||||||
|
updateNavigationDrawerHeader();
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean onCreateOptionsMenu(Menu menu) {
|
public boolean onCreateOptionsMenu(Menu menu) {
|
||||||
if (isAlbumPage()) {
|
if (isAlbumPage()) {
|
||||||
|
|
@ -411,7 +412,7 @@ public class MainActivity extends AbsFabActivity
|
||||||
MusicPlayerRemote.openQueue(SearchQueryHelper.getSongs(this, intent.getExtras()), 0, true);
|
MusicPlayerRemote.openQueue(SearchQueryHelper.getSongs(this, intent.getExtras()), 0, true);
|
||||||
}
|
}
|
||||||
if (uri != null && uri.toString().length() > 0) {
|
if (uri != null && uri.toString().length() > 0) {
|
||||||
MusicPlayerRemote.playFile(uri);
|
MusicPlayerRemote.playFile(uri.toString());
|
||||||
handled = true;
|
handled = true;
|
||||||
} else if (MediaStore.Audio.Playlists.CONTENT_TYPE.equals(mimeType)) {
|
} else if (MediaStore.Audio.Playlists.CONTENT_TYPE.equals(mimeType)) {
|
||||||
final int id = (int) parseIdFromIntent(intent, "playlistId", "playlist");
|
final int id = (int) parseIdFromIntent(intent, "playlistId", "playlist");
|
||||||
|
|
|
||||||
|
|
@ -20,6 +20,7 @@ import com.kabouzeid.gramophone.dialogs.ColorChooserDialog;
|
||||||
import com.kabouzeid.gramophone.helper.PlayingNotificationHelper;
|
import com.kabouzeid.gramophone.helper.PlayingNotificationHelper;
|
||||||
import com.kabouzeid.gramophone.model.UIPreferenceChangedEvent;
|
import com.kabouzeid.gramophone.model.UIPreferenceChangedEvent;
|
||||||
import com.kabouzeid.gramophone.prefs.ColorChooserPreference;
|
import com.kabouzeid.gramophone.prefs.ColorChooserPreference;
|
||||||
|
import com.kabouzeid.gramophone.service.MusicService;
|
||||||
import com.kabouzeid.gramophone.ui.activities.base.AbsBaseActivity;
|
import com.kabouzeid.gramophone.ui.activities.base.AbsBaseActivity;
|
||||||
import com.kabouzeid.gramophone.util.NavigationUtil;
|
import com.kabouzeid.gramophone.util.NavigationUtil;
|
||||||
import com.kabouzeid.gramophone.util.PreferenceUtils;
|
import com.kabouzeid.gramophone.util.PreferenceUtils;
|
||||||
|
|
@ -146,6 +147,15 @@ public class SettingsActivity extends AbsBaseActivity implements ColorChooserDia
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
Preference gaplessPlayback = findPreference("gapless_playback");
|
||||||
|
gaplessPlayback.setOnPreferenceChangeListener(new Preference.OnPreferenceChangeListener() {
|
||||||
|
@Override
|
||||||
|
public boolean onPreferenceChange(Preference preference, Object newValue) {
|
||||||
|
getActivity().sendBroadcast(new Intent(MusicService.SETTING_GAPLESS_PLAYBACK_CHANGED).putExtra(MusicService.SETTING_GAPLESS_PLAYBACK_CHANGED_VALUE_EXTRA, (boolean) newValue));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
equalizer = findPreference("equalizer");
|
equalizer = findPreference("equalizer");
|
||||||
resolveEqualizer();
|
resolveEqualizer();
|
||||||
equalizer.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() {
|
equalizer.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() {
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,7 @@ import android.content.Context;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.content.IntentFilter;
|
import android.content.IntentFilter;
|
||||||
|
|
||||||
|
import com.kabouzeid.gramophone.helper.MusicPlayerRemote;
|
||||||
import com.kabouzeid.gramophone.service.MusicService;
|
import com.kabouzeid.gramophone.service.MusicService;
|
||||||
|
|
||||||
import java.lang.ref.WeakReference;
|
import java.lang.ref.WeakReference;
|
||||||
|
|
@ -13,7 +14,7 @@ import java.lang.ref.WeakReference;
|
||||||
* @author Karim Abou Zeid (kabouzeid)
|
* @author Karim Abou Zeid (kabouzeid)
|
||||||
*/
|
*/
|
||||||
public abstract class AbsPlaybackStatusActivity extends AbsBaseActivity {
|
public abstract class AbsPlaybackStatusActivity extends AbsBaseActivity {
|
||||||
private PlaybackStatus playbackStatus;
|
private PlaybackStatusReceiver playbackStatusReceiver;
|
||||||
|
|
||||||
public void onPlayingMetaChanged() {
|
public void onPlayingMetaChanged() {
|
||||||
|
|
||||||
|
|
@ -31,35 +32,45 @@ public abstract class AbsPlaybackStatusActivity extends AbsBaseActivity {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void onServiceConnected() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onStart() {
|
protected void onStart() {
|
||||||
super.onStart();
|
super.onStart();
|
||||||
|
|
||||||
playbackStatus = new PlaybackStatus(this);
|
playbackStatusReceiver = new PlaybackStatusReceiver(this);
|
||||||
|
|
||||||
|
// ensures that onServiceConnected() is called even if the service is already connected and wont sent the Intent again.
|
||||||
|
if (MusicPlayerRemote.isServiceConnected()) {
|
||||||
|
onServiceConnected();
|
||||||
|
}
|
||||||
|
|
||||||
final IntentFilter filter = new IntentFilter();
|
final IntentFilter filter = new IntentFilter();
|
||||||
filter.addAction(MusicService.PLAYSTATE_CHANGED);
|
filter.addAction(MusicService.PLAYSTATE_CHANGED);
|
||||||
filter.addAction(MusicService.SHUFFLEMODE_CHANGED);
|
filter.addAction(MusicService.SHUFFLEMODE_CHANGED);
|
||||||
filter.addAction(MusicService.REPEATMODE_CHANGED);
|
filter.addAction(MusicService.REPEATMODE_CHANGED);
|
||||||
filter.addAction(MusicService.META_CHANGED);
|
filter.addAction(MusicService.META_CHANGED);
|
||||||
|
filter.addAction(MusicPlayerRemote.SERVICE_BOUND);
|
||||||
|
|
||||||
registerReceiver(playbackStatus, filter);
|
registerReceiver(playbackStatusReceiver, filter);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onStop() {
|
protected void onStop() {
|
||||||
super.onStop();
|
super.onStop();
|
||||||
try {
|
try {
|
||||||
unregisterReceiver(playbackStatus);
|
unregisterReceiver(playbackStatusReceiver);
|
||||||
} catch (Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static final class PlaybackStatus extends BroadcastReceiver {
|
private static final class PlaybackStatusReceiver extends BroadcastReceiver {
|
||||||
|
|
||||||
private final WeakReference<AbsPlaybackStatusActivity> reference;
|
private final WeakReference<AbsPlaybackStatusActivity> reference;
|
||||||
|
|
||||||
public PlaybackStatus(final AbsPlaybackStatusActivity activity) {
|
public PlaybackStatusReceiver(final AbsPlaybackStatusActivity activity) {
|
||||||
reference = new WeakReference<>(activity);
|
reference = new WeakReference<>(activity);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -79,6 +90,9 @@ public abstract class AbsPlaybackStatusActivity extends AbsBaseActivity {
|
||||||
case MusicService.SHUFFLEMODE_CHANGED:
|
case MusicService.SHUFFLEMODE_CHANGED:
|
||||||
reference.get().onShuffleModeChanged();
|
reference.get().onShuffleModeChanged();
|
||||||
break;
|
break;
|
||||||
|
case MusicPlayerRemote.SERVICE_BOUND:
|
||||||
|
reference.get().onServiceConnected();
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue