前提・実現したいこと
Google Playで公開中のアプリで以下のクラッシュログが出てきた。
MediaPlayer.prepareでIllegalStateExceptionとなる場合があるが原因が分からない。
IllegalStateExceptionとならないように改修したい。
なお、play、stop、stopNotFocusはボタンと連携しているため連打もしてみたが自分では再現できない。
発生している問題・エラーメッセージ
クラッシュログ
Sony Xperia XZs(602SO), Android 7.1 java.lang.IllegalStateException: at android.media.MediaPlayer._prepare (MediaPlayer.java) at android.media.MediaPlayer.prepare (MediaPlayer.java:1217)
該当のソースコード
java
1//再生停止処理 2public class SoundPlayer { 3 4 static MediaPlayer mPlayer; 5 6 static AudioManager adm; 7 static AudioManager.OnAudioFocusChangeListener afChangeListener; 8 9 public void SoundPlayer(){ 10 //オーディオフォーカスのコールバック 11 afChangeListener = 12 new AudioManager.OnAudioFocusChangeListener() { 13 public void onAudioFocusChange(int focusChange) { 14 //フォーカスを完全に失ったら 15 if (focusChange == AudioManager.AUDIOFOCUS_LOSS) { 16 } else if (focusChange == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT) {//一時的なフォーカスロスト 17 } else if (focusChange == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK) {//通知音とかによるフォーカスロスト(ボリュームを下げて再生し続けるべき) 18 } else if (focusChange == AudioManager.AUDIOFOCUS_GAIN) {//フォーカスを再度得た場合 19 //停止していないので、本来は再生すべきだが何もしない 20 } 21 } 22 }; 23 } 24 25 //再生処理 26 public void play(Uri i_sound){ 27 28 // 現在のメディア音量を表示する 29 // AudioManagerを取得する 30 adm = (AudioManager)Globals.getAppContext().getSystemService(Context.AUDIO_SERVICE); 31 // 現在の音量を取得する 32 int ringVolume = adm.getStreamVolume(AudioManager.STREAM_MUSIC); 33 // 音量を設定する 34 adm.setStreamVolume(AudioManager.STREAM_MUSIC, ringVolume, AudioManager.FLAG_SHOW_UI); 35 36 // フォーカスを排他的に奪う(他のアプリの音楽を停止) 37 adm.requestAudioFocus(afChangeListener, AudioManager.STREAM_MUSIC, AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_EXCLUSIVE); 38 39 if(!i_sound.toString().equals("")){ 40 mPlayer = new MediaPlayer(); 41 42 mPlayer.reset(); 43 44 //音設定 45 try { 46 mPlayer.setDataSource(Globals.getAppContext(), i_sound); // 音楽を設定 47 } catch (IOException e) { 48 e.printStackTrace(); 49 } 50 mPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC); // ミュージックボリュームで再生 51 mPlayer.setLooping(true); // ループ再生を設定 52 try { 53 mPlayer.prepare(); // 音楽を読み込み 54 } catch (IOException e) { 55 e.printStackTrace(); 56 } 57 58 //音再生 59 mPlayer.start(); // 再生 60 } 61 62 } 63 64 //音停止処理 65 public void stop(){ 66 if(mPlayer != null){ 67 // 音が再生されていれば停止する 68 if(mPlayer.isPlaying()) { 69 mPlayer.stop(); // 停止 70 } 71 72 // メディアプレイヤー を解放する 73 mPlayer.reset(); 74 mPlayer.release(); 75 mPlayer = null; 76 77 } 78 79 // フォーカスを明け渡す 80 if(adm != null){ 81 // フォーカスを明け渡す(他のアプリの音楽を停止を解除) 82 adm.abandonAudioFocus(afChangeListener); 83 } 84 85 } 86 87 //音停止処理(フォーカス明け渡さないバージョン) 88 public void stopNotFocus(){ 89 if(mPlayer != null){ 90 // 音が再生されていれば停止する 91 if(mPlayer.isPlaying()) { 92 mPlayer.stop(); // 停止 93 } 94 95 // メディアプレイヤー を解放する 96 mPlayer.reset(); 97 mPlayer.release(); 98 mPlayer = null; 99 } 100 101 } 102 103}
補足情報(FW/ツールのバージョンなど)
Android Studio3.4
APIレベル19から28まで対象