From eba94bb2c6122414af0ea478f7b2b65ad1b2b39c Mon Sep 17 00:00:00 2001 From: Scott Jackson Date: Sat, 1 Mar 2014 10:24:02 -0800 Subject: #175 Abstract audiofx controllers out, add bass booster/voice booster --- .../dsub/audiofx/AudioEffectsController.java | 82 +++++++ .../dsub/audiofx/EqualizerController.java | 248 ++++++++++++--------- .../dsub/audiofx/LoudnessEnhancerController.java | 77 +++++++ .../dsub/audiofx/VisualizerController.java | 109 +++++---- .../dsub/fragments/DownloadFragment.java | 3 - .../dsub/fragments/EqualizerFragment.java | 113 +++++++++- .../daneren2005/dsub/service/DownloadService.java | 55 ++--- 7 files changed, 486 insertions(+), 201 deletions(-) create mode 100644 src/github/daneren2005/dsub/audiofx/AudioEffectsController.java create mode 100644 src/github/daneren2005/dsub/audiofx/LoudnessEnhancerController.java (limited to 'src/github') diff --git a/src/github/daneren2005/dsub/audiofx/AudioEffectsController.java b/src/github/daneren2005/dsub/audiofx/AudioEffectsController.java new file mode 100644 index 00000000..16e30c6d --- /dev/null +++ b/src/github/daneren2005/dsub/audiofx/AudioEffectsController.java @@ -0,0 +1,82 @@ +/* + This file is part of Subsonic. + + Subsonic is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Subsonic is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Subsonic. If not, see . + + Copyright 2014 (C) Scott Jackson +*/ +package github.daneren2005.dsub.audiofx; + +import android.content.Context; +import android.media.MediaPlayer; +import android.media.audiofx.AudioEffect; +import android.media.audiofx.LoudnessEnhancer; +import android.os.Build; +import android.util.Log; + +public class AudioEffectsController { + private static final String TAG = AudioEffectsController.class.getSimpleName(); + + private final Context context; + private int audioSessionId = 0; + + private boolean available = false; + + private EqualizerController equalizerController; + private VisualizerController visualizerController; + + public AudioEffectsController(Context context, MediaPlayer mediaPlayer) { + this.context = context; + audioSessionId = mediaPlayer.getAudioSessionId(); + + if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.GINGERBREAD) { + available = true; + } + } + + public boolean isAvailable() { + return available; + } + + public void release() { + if(equalizerController != null) { + equalizerController.release(); + } + if(visualizerController != null) { + visualizerController.release(); + } + } + + public EqualizerController getEqualizerController() { + if (available && equalizerController == null) { + equalizerController = new EqualizerController(context, audioSessionId); + if (!equalizerController.isAvailable()) { + equalizerController = null; + } else { + equalizerController.loadSettings(); + } + } + return equalizerController; + } + public VisualizerController getVisualizerController() { + if (available && visualizerController == null) { + visualizerController = new VisualizerController(context, audioSessionId); + if (!visualizerController.isAvailable()) { + visualizerController = null; + } + } + return visualizerController; + } +} + diff --git a/src/github/daneren2005/dsub/audiofx/EqualizerController.java b/src/github/daneren2005/dsub/audiofx/EqualizerController.java index 0e1c49b5..254f168d 100644 --- a/src/github/daneren2005/dsub/audiofx/EqualizerController.java +++ b/src/github/daneren2005/dsub/audiofx/EqualizerController.java @@ -21,8 +21,9 @@ package github.daneren2005.dsub.audiofx; import java.io.Serializable; import android.content.Context; -import android.media.MediaPlayer; +import android.media.audiofx.BassBoost; import android.media.audiofx.Equalizer; +import android.os.Build; import android.util.Log; import github.daneren2005.dsub.util.FileUtil; @@ -34,125 +35,170 @@ import github.daneren2005.dsub.util.FileUtil; */ public class EqualizerController { - private static final String TAG = EqualizerController.class.getSimpleName(); + private static final String TAG = EqualizerController.class.getSimpleName(); - private final Context context; - private Equalizer equalizer; + private final Context context; + private Equalizer equalizer; + private BassBoost bass; + private boolean loudnessAvailable = false; + private LoudnessEnhancerController loudnessEnhancerController; private boolean released = false; private int audioSessionId = 0; - // Class initialization fails when this throws an exception. - static { - try { - Class.forName("android.media.audiofx.Equalizer"); - } catch (Exception ex) { - throw new RuntimeException(ex); - } - } - - /** - * Throws an exception if the {@link Equalizer} class is not available. - */ - public static void checkAvailable() throws Throwable { - // Calling here forces class initialization. - } - - public EqualizerController(Context context, MediaPlayer mediaPlayer) { - this.context = context; - try { - audioSessionId = mediaPlayer.getAudioSessionId(); - equalizer = new Equalizer(0, audioSessionId); - } catch (Throwable x) { - Log.w(TAG, "Failed to create equalizer.", x); - } - } - - public void saveSettings() { - try { - if (isAvailable()) { - FileUtil.serialize(context, new EqualizerSettings(equalizer), "equalizer.dat"); - } - } catch (Throwable x) { - Log.w(TAG, "Failed to save equalizer settings.", x); - } - } - - public void loadSettings() { - try { - if (isAvailable()) { - EqualizerSettings settings = FileUtil.deserialize(context, "equalizer.dat", EqualizerSettings.class); - if (settings != null) { - settings.apply(equalizer); - } - } - } catch (Throwable x) { - Log.w(TAG, "Failed to load equalizer settings.", x); - } - } - - public boolean isAvailable() { - return equalizer != null; - } - - public boolean isEnabled() { - try { - return isAvailable() && equalizer.getEnabled(); - } catch(Exception e) { - return false; - } - } - - public void release() { - if (isAvailable()) { + public EqualizerController(Context context, int audioSessionId) { + this.context = context; + try { + this.audioSessionId = audioSessionId; + init(); + } catch (Throwable x) { + Log.w(TAG, "Failed to create equalizer.", x); + } + } + + private void init() { + equalizer = new Equalizer(0, audioSessionId); + bass = new BassBoost(0, audioSessionId); + if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { + loudnessAvailable = true; + loudnessEnhancerController = new LoudnessEnhancerController(context, audioSessionId); + } + } + + public void saveSettings() { + try { + if (isAvailable()) { + FileUtil.serialize(context, new EqualizerSettings(equalizer, bass, loudnessEnhancerController), "equalizer.dat"); + } + } catch (Throwable x) { + Log.w(TAG, "Failed to save equalizer settings.", x); + } + } + + public void loadSettings() { + try { + if (isAvailable()) { + EqualizerSettings settings = FileUtil.deserialize(context, "equalizer.dat", EqualizerSettings.class); + if (settings != null) { + settings.apply(equalizer, bass, loudnessEnhancerController); + } + } + } catch (Throwable x) { + Log.w(TAG, "Failed to load equalizer settings.", x); + } + } + + public boolean isAvailable() { + return equalizer != null && bass != null; + } + + public boolean isEnabled() { + try { + return isAvailable() && equalizer.getEnabled(); + } catch(Exception e) { + return false; + } + } + + public void release() { + if (isAvailable()) { released = true; - equalizer.release(); - } - } + equalizer.release(); + bass.release(); + if(loudnessEnhancerController != null && loudnessEnhancerController.isAvailable()) { + loudnessEnhancerController.release(); + } + } + } - public Equalizer getEqualizer() { + public Equalizer getEqualizer() { if(released) { released = false; try { - equalizer = new Equalizer(0, audioSessionId); + init(); } catch (Throwable x) { equalizer = null; Log.w(TAG, "Failed to create equalizer.", x); } } - return equalizer; - } + return equalizer; + } + public BassBoost getBassBoost() { + if(released) { + released = false; + try { + init(); + } catch (Throwable x) { + bass = null; + Log.w(TAG, "Failed to create bass booster.", x); + } + } + return bass; + } + public LoudnessEnhancerController getLoudnessEnhancerController() { + if(loudnessAvailable && released) { + released = false; + try { + init(); + } catch (Throwable x) { + loudnessEnhancerController = null; + Log.w(TAG, "Failed to create loudness enhancer.", x); + } + } + return loudnessEnhancerController; + } - private static class EqualizerSettings implements Serializable { + private static class EqualizerSettings implements Serializable { - private short[] bandLevels; - private short preset; - private boolean enabled; + private short[] bandLevels; + private short preset; + private boolean enabled; + private short bass; + private int loudness; public EqualizerSettings() { } - public EqualizerSettings(Equalizer equalizer) { - enabled = equalizer.getEnabled(); - bandLevels = new short[equalizer.getNumberOfBands()]; - for (short i = 0; i < equalizer.getNumberOfBands(); i++) { - bandLevels[i] = equalizer.getBandLevel(i); - } - try { - preset = equalizer.getCurrentPreset(); - } catch (Exception x) { - preset = -1; - } - } - - public void apply(Equalizer equalizer) { - for (short i = 0; i < bandLevels.length; i++) { - equalizer.setBandLevel(i, bandLevels[i]); - } - if (preset >= 0 && preset < equalizer.getNumberOfPresets()) { - equalizer.usePreset(preset); - } - equalizer.setEnabled(enabled); - } - } + public EqualizerSettings(Equalizer equalizer, BassBoost boost, LoudnessEnhancerController loudnessEnhancerController) { + enabled = equalizer.getEnabled(); + bandLevels = new short[equalizer.getNumberOfBands()]; + for (short i = 0; i < equalizer.getNumberOfBands(); i++) { + bandLevels[i] = equalizer.getBandLevel(i); + } + try { + preset = equalizer.getCurrentPreset(); + } catch (Exception x) { + preset = -1; + } + try { + bass = boost.getRoundedStrength(); + } catch(Exception e) { + bass = 0; + } + + try { + loudness = (int) loudnessEnhancerController.getGain(); + } catch(Exception e) { + loudness = 0; + } + } + + public void apply(Equalizer equalizer, BassBoost boost, LoudnessEnhancerController loudnessController) { + for (short i = 0; i < bandLevels.length; i++) { + equalizer.setBandLevel(i, bandLevels[i]); + } + if (preset >= 0 && preset < equalizer.getNumberOfPresets()) { + equalizer.usePreset(preset); + } + equalizer.setEnabled(enabled); + if(bass != 0) { + boost.setEnabled(true); + boost.setStrength(bass); + } + if(loudness != 0) { + loudnessController.enable(); + loudnessController.setGain(loudness); + } + } + } } diff --git a/src/github/daneren2005/dsub/audiofx/LoudnessEnhancerController.java b/src/github/daneren2005/dsub/audiofx/LoudnessEnhancerController.java new file mode 100644 index 00000000..df6fdb1c --- /dev/null +++ b/src/github/daneren2005/dsub/audiofx/LoudnessEnhancerController.java @@ -0,0 +1,77 @@ +/* + This file is part of Subsonic. + + Subsonic is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Subsonic is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Subsonic. If not, see . + + Copyright 2014 (C) Scott Jackson +*/ +package github.daneren2005.dsub.audiofx; + +import android.content.Context; +import android.media.audiofx.LoudnessEnhancer; +import android.util.Log; + +public class LoudnessEnhancerController { + private static final String TAG = LoudnessEnhancerController.class.getSimpleName(); + + private final Context context; + private LoudnessEnhancer enhancer; + private boolean released = false; + private int audioSessionId = 0; + + public LoudnessEnhancerController(Context context, int audioSessionId) { + this.context = context; + try { + this.audioSessionId = audioSessionId; + enhancer = new LoudnessEnhancer(audioSessionId); + } catch (Throwable x) { + Log.w(TAG, "Failed to create enhancer", x); + } + } + + public boolean isAvailable() { + return enhancer != null; + } + + public boolean isEnabled() { + try { + return isAvailable() && enhancer.getEnabled(); + } catch(Exception e) { + return false; + } + } + + public void enable() { + enhancer.setEnabled(true); + } + public void disable() { + enhancer.setEnabled(false); + } + + public float getGain() { + return enhancer.getTargetGain(); + } + public void setGain(int gain) { + enhancer.setTargetGain(gain); + } + + public void release() { + if (isAvailable()) { + enhancer.release(); + released = true; + } + } + +} + diff --git a/src/github/daneren2005/dsub/audiofx/VisualizerController.java b/src/github/daneren2005/dsub/audiofx/VisualizerController.java index b32245f4..92e3712c 100644 --- a/src/github/daneren2005/dsub/audiofx/VisualizerController.java +++ b/src/github/daneren2005/dsub/audiofx/VisualizerController.java @@ -19,7 +19,6 @@ package github.daneren2005.dsub.audiofx; import android.content.Context; -import android.media.MediaPlayer; import android.media.audiofx.Visualizer; import android.util.Log; @@ -31,63 +30,63 @@ import android.util.Log; */ public class VisualizerController { - private static final String TAG = VisualizerController.class.getSimpleName(); - private static final int PREFERRED_CAPTURE_SIZE = 128; // Must be a power of two. + private static final String TAG = VisualizerController.class.getSimpleName(); + private static final int PREFERRED_CAPTURE_SIZE = 128; // Must be a power of two. - private final Context context; - private Visualizer visualizer; + private final Context context; + private Visualizer visualizer; private boolean released = false; private int audioSessionId = 0; - // Class initialization fails when this throws an exception. - static { - try { - Class.forName("android.media.audiofx.Visualizer"); - } catch (Exception ex) { - throw new RuntimeException(ex); - } - } - - /** - * Throws an exception if the {@link Visualizer} class is not available. - */ - public static void checkAvailable() throws Throwable { - // Calling here forces class initialization. - } - - public VisualizerController(Context context, MediaPlayer mediaPlayer) { - this.context = context; - try { - audioSessionId = mediaPlayer.getAudioSessionId(); - visualizer = new Visualizer(audioSessionId); - } catch (Throwable x) { - Log.w(TAG, "Failed to create visualizer.", x); - } - - if (visualizer != null) { - int[] captureSizeRange = Visualizer.getCaptureSizeRange(); - int captureSize = Math.max(PREFERRED_CAPTURE_SIZE, captureSizeRange[0]); - captureSize = Math.min(captureSize, captureSizeRange[1]); - visualizer.setCaptureSize(captureSize); - } - } - - public boolean isAvailable() { - return visualizer != null; - } - - public boolean isEnabled() { - return isAvailable() && visualizer.getEnabled(); - } - - public void release() { - if (isAvailable()) { - visualizer.release(); + // Class initialization fails when this throws an exception. + static { + try { + Class.forName("android.media.audiofx.Visualizer"); + } catch (Exception ex) { + throw new RuntimeException(ex); + } + } + + /** + * Throws an exception if the {@link Visualizer} class is not available. + */ + public static void checkAvailable() throws Throwable { + // Calling here forces class initialization. + } + + public VisualizerController(Context context, int audioSessionId) { + this.context = context; + try { + this.audioSessionId = audioSessionId; + visualizer = new Visualizer(audioSessionId); + } catch (Throwable x) { + Log.w(TAG, "Failed to create visualizer.", x); + } + + if (visualizer != null) { + int[] captureSizeRange = Visualizer.getCaptureSizeRange(); + int captureSize = Math.max(PREFERRED_CAPTURE_SIZE, captureSizeRange[0]); + captureSize = Math.min(captureSize, captureSizeRange[1]); + visualizer.setCaptureSize(captureSize); + } + } + + public boolean isAvailable() { + return visualizer != null; + } + + public boolean isEnabled() { + return isAvailable() && visualizer.getEnabled(); + } + + public void release() { + if (isAvailable()) { + visualizer.release(); released = true; - } - } + } + } - public Visualizer getVisualizer() { + public Visualizer getVisualizer() { if(released) { released = false; try { @@ -97,8 +96,8 @@ public class VisualizerController { Log.w(TAG, "Failed to create visualizer.", x); } } - - return visualizer; - } + + return visualizer; + } } diff --git a/src/github/daneren2005/dsub/fragments/DownloadFragment.java b/src/github/daneren2005/dsub/fragments/DownloadFragment.java index 835394ae..d9091b55 100644 --- a/src/github/daneren2005/dsub/fragments/DownloadFragment.java +++ b/src/github/daneren2005/dsub/fragments/DownloadFragment.java @@ -464,13 +464,10 @@ public class DownloadFragment extends SubsonicFragment implements OnGestureListe downloadService.setShufflePlayEnabled(true); } - boolean visualizerAvailable = downloadService != null && downloadService.getVisualizerAvailable(); boolean equalizerAvailable = downloadService != null && downloadService.getEqualizerAvailable(); if (!equalizerAvailable) { equalizerButton.setVisibility(View.GONE); - } - if (!visualizerAvailable) { visualizerButton.setVisibility(View.GONE); } else { visualizerView = new VisualizerView(context); diff --git a/src/github/daneren2005/dsub/fragments/EqualizerFragment.java b/src/github/daneren2005/dsub/fragments/EqualizerFragment.java index 71067d7c..1475ccdd 100644 --- a/src/github/daneren2005/dsub/fragments/EqualizerFragment.java +++ b/src/github/daneren2005/dsub/fragments/EqualizerFragment.java @@ -19,8 +19,10 @@ package github.daneren2005.dsub.fragments; import android.content.SharedPreferences; +import android.media.audiofx.BassBoost; import android.media.audiofx.Equalizer; import android.os.Bundle; +import android.util.Log; import android.view.ContextMenu; import android.view.LayoutInflater; import android.view.MenuItem; @@ -37,6 +39,7 @@ import java.util.Map; import github.daneren2005.dsub.R; import github.daneren2005.dsub.audiofx.EqualizerController; +import github.daneren2005.dsub.audiofx.LoudnessEnhancerController; import github.daneren2005.dsub.service.DownloadService; import github.daneren2005.dsub.util.Constants; import github.daneren2005.dsub.util.Util; @@ -50,20 +53,28 @@ public class EqualizerFragment extends SubsonicFragment { private static final int MENU_GROUP_PRESET = 100; private final Map bars = new HashMap(); + private SeekBar bassBar; + private SeekBar loudnessBar; private EqualizerController equalizerController; private Equalizer equalizer; + private BassBoost bass; + private LoudnessEnhancerController loudnessEnhancer; private short masterLevel = 0; @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle bundle) { rootView = inflater.inflate(R.layout.equalizer, container, false); - equalizerController = DownloadService.getInstance().getEqualizerController(); + DownloadService service = DownloadService.getInstance(); + equalizerController = service.getEqualizerController(); equalizer = equalizerController.getEqualizer(); + bass = equalizerController.getBassBoost(); + loudnessEnhancer = equalizerController.getLoudnessEnhancerController(); try { initEqualizer(); } catch(Exception e) { + Log.e(TAG, "Failed to initialize EQ", e); Util.toast(context, "Failed to initialize EQ"); context.onBackPressed(); } @@ -106,6 +117,7 @@ public class EqualizerFragment extends SubsonicFragment { super.onResume(); equalizerController = DownloadService.getInstance().getEqualizerController(); equalizer = equalizerController.getEqualizer(); + bass = equalizerController.getBassBoost(); } @Override @@ -180,6 +192,11 @@ public class EqualizerFragment extends SubsonicFragment { } } + bassBar.setEnabled(isEnabled); + if(loudnessBar != null) { + loudnessBar.setEnabled(isEnabled); + } + if(!isEnabled) { masterLevel = 0; SharedPreferences prefs = Util.getPreferences(context); @@ -240,6 +257,98 @@ public class EqualizerFragment extends SubsonicFragment { }); layout.addView(bandBar); } + + LinearLayout specialLayout = (LinearLayout) rootView.findViewById(R.id.special_effects_layout); + + // Setup bass booster + View bandBar = LayoutInflater.from(context).inflate(R.layout.equalizer_bar, null); + TextView freqTextView = (TextView) bandBar.findViewById(R.id.equalizer_frequency); + final TextView bassTextView = (TextView) bandBar.findViewById(R.id.equalizer_level); + bassBar = (SeekBar) bandBar.findViewById(R.id.equalizer_bar); + + freqTextView.setText(R.string.equalizer_bass_booster); + bassBar.setEnabled(equalizer.getEnabled()); + short bassLevel = 0; + if(bass.getEnabled()) { + bassLevel = bass.getRoundedStrength(); + } + bassTextView.setText(context.getResources().getString(R.string.equalizer_bass_size, bassLevel)); + bassBar.setMax(1000); + bassBar.setProgress(bassLevel); + bassBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() { + @Override + public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) { + bassTextView.setText(context.getResources().getString(R.string.equalizer_bass_size, progress)); + if(fromUser) { + if(progress > 0) { + if(!bass.getEnabled()) { + bass.setEnabled(true); + } + bass.setStrength((short) progress); + } else if(progress == 0 && bass.getEnabled()) { + bass.setStrength((short) progress); + bass.setEnabled(false); + } + } + } + + @Override + public void onStartTrackingTouch(SeekBar seekBar) { + + } + + @Override + public void onStopTrackingTouch(SeekBar seekBar) { + + } + }); + specialLayout.addView(bandBar); + + if(loudnessEnhancer != null && loudnessEnhancer.isAvailable()) { + // Setup loudness enhancer + bandBar = LayoutInflater.from(context).inflate(R.layout.equalizer_bar, null); + freqTextView = (TextView) bandBar.findViewById(R.id.equalizer_frequency); + final TextView loudnessTextView = (TextView) bandBar.findViewById(R.id.equalizer_level); + loudnessBar = (SeekBar) bandBar.findViewById(R.id.equalizer_bar); + + freqTextView.setText(R.string.equalizer_voice_booster); + loudnessBar.setEnabled(equalizer.getEnabled()); + int loudnessLevel = 0; + if(loudnessEnhancer.isEnabled()) { + loudnessLevel = (int) loudnessEnhancer.getGain(); + } + loudnessBar.setProgress(loudnessLevel / 100); + loudnessTextView.setText(context.getResources().getString(R.string.equalizer_db_size, loudnessLevel / 100)); + loudnessBar.setMax(15); + loudnessBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() { + @Override + public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) { + loudnessTextView.setText(context.getResources().getString(R.string.equalizer_db_size, progress)); + if(fromUser) { + if(progress > 0) { + if(!loudnessEnhancer.isEnabled()) { + loudnessEnhancer.enable(); + } + loudnessEnhancer.setGain(progress * 100); + } else if(progress == 0 && loudnessEnhancer.isEnabled()) { + loudnessEnhancer.setGain(progress * 100); + loudnessEnhancer.disable(); + } + } + } + + @Override + public void onStartTrackingTouch(SeekBar seekBar) { + + } + + @Override + public void onStopTrackingTouch(SeekBar seekBar) { + + } + }); + specialLayout.addView(bandBar); + } } private void initPregain(LinearLayout layout, final short minEQLevel, final short maxEQLevel) { @@ -285,6 +394,6 @@ public class EqualizerFragment extends SubsonicFragment { } private void updateLevelText(TextView levelTextView, short level) { - levelTextView.setText((level > 0 ? "+" : "") + level / 100 + " dB"); + levelTextView.setText((level > 0 ? "+" : "") + context.getResources().getString(R.string.equalizer_db_size, level / 100)); } } diff --git a/src/github/daneren2005/dsub/service/DownloadService.java b/src/github/daneren2005/dsub/service/DownloadService.java index ce3c3799..fcf49ce6 100644 --- a/src/github/daneren2005/dsub/service/DownloadService.java +++ b/src/github/daneren2005/dsub/service/DownloadService.java @@ -27,7 +27,10 @@ import static github.daneren2005.dsub.domain.PlayerState.PREPARED; import static github.daneren2005.dsub.domain.PlayerState.PREPARING; import static github.daneren2005.dsub.domain.PlayerState.STARTED; import static github.daneren2005.dsub.domain.PlayerState.STOPPED; + +import github.daneren2005.dsub.audiofx.AudioEffectsController; import github.daneren2005.dsub.audiofx.EqualizerController; +import github.daneren2005.dsub.audiofx.LoudnessEnhancerController; import github.daneren2005.dsub.audiofx.VisualizerController; import github.daneren2005.dsub.domain.Bookmark; import github.daneren2005.dsub.domain.MusicDirectory; @@ -128,10 +131,7 @@ public class DownloadService extends Service { private boolean downloadOngoing = false; private DownloadFile lastDownloaded = null; - private static boolean equalizerAvailable; - private static boolean visualizerAvailable; - private EqualizerController equalizerController; - private VisualizerController visualizerController; + private AudioEffectsController effectsController; private boolean showVisualization; private RemoteControlState remoteState = RemoteControlState.LOCAL; private PositionCache positionCache; @@ -143,17 +143,11 @@ public class DownloadService extends Service { private MediaRouteManager mediaRouter; - static { - if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.GINGERBREAD) { - equalizerAvailable = true; - visualizerAvailable = true; - } - } - @Override public void onCreate() { super.onCreate(); + final SharedPreferences prefs = Util.getPreferences(this); new Thread(new Runnable() { public void run() { Looper.prepare(); @@ -178,6 +172,7 @@ public class DownloadService extends Service { // Froyo or lower } + effectsController = new AudioEffectsController(DownloadService.this, mediaPlayer); if(prefs.getBoolean(Constants.PREFERENCES_EQUALIZER_ON, false)) { getEqualizerController(); } @@ -205,7 +200,6 @@ public class DownloadService extends Service { wakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, this.getClass().getName()); wakeLock.setReferenceCounted(false); - SharedPreferences prefs = Util.getPreferences(this); try { timerDuration = Integer.parseInt(prefs.getString(Constants.PREFERENCES_KEY_SLEEP_TIMER_DURATION, "5")); } catch(Throwable e) { @@ -255,12 +249,7 @@ public class DownloadService extends Service { } mediaPlayerLooper.quit(); shufflePlayBuffer.shutdown(); - if (equalizerController != null) { - equalizerController.release(); - } - if (visualizerController != null) { - visualizerController.release(); - } + effectsController.release(); if (mRemoteControl != null) { mRemoteControl.unregister(this); mRemoteControl = null; @@ -1079,33 +1068,15 @@ public class DownloadService extends Service { } public boolean getEqualizerAvailable() { - return equalizerAvailable; - } - - public boolean getVisualizerAvailable() { - return visualizerAvailable; + return effectsController.isAvailable(); } public EqualizerController getEqualizerController() { - if (equalizerAvailable && equalizerController == null) { - equalizerController = new EqualizerController(this, mediaPlayer); - if (!equalizerController.isAvailable()) { - equalizerController = null; - } else { - equalizerController.loadSettings(); - } - } - return equalizerController; + return effectsController.getEqualizerController(); } public VisualizerController getVisualizerController() { - if (visualizerAvailable && visualizerController == null) { - visualizerController = new VisualizerController(this, mediaPlayer); - if (!visualizerController.isAvailable()) { - visualizerController = null; - } - } - return visualizerController; + return effectsController.getVisualizerController(); } public MediaRouteSelector getRemoteSelector() { @@ -1500,7 +1471,11 @@ public class DownloadService extends Service { } private void handleErrorNext(Exception x) { Log.w(TAG, "Next Media player error: " + x, x); - nextMediaPlayer.reset(); + try { + nextMediaPlayer.reset(); + } catch(Exception e) { + Log.e(TAG, "Failed to reset next media player", x); + } setNextPlayerState(IDLE); } -- cgit v1.2.3