2015-11-06 77 views
1

任何人都可以告诉我为什么后退按钮崩溃的应用程序?无论我在代码中做了什么改变,无论是try/catch,onDestroy,onBackPressed,它每次都会崩溃,但前提是我已经启动了媒体播放器一次。如果我没有从屏幕上启动它,后退按钮不会使应用程序崩溃。我究竟做错了什么?由于Mediaplayer崩溃应用onBackPressed

public class Lesson1Grammar extends Activity implements SeekBar.OnSeekBarChangeListener{ 

private SeekBar seekBar; 
private TextView songCurrentDurationLabel; 
private TextView songTotalDurationLabel; 
MediaPlayer wholeTextPlayer; 
private Utilities utils; 
final Handler handler = new Handler(); 

@Override 
public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.lesson1grammar); 

    final RelativeLayout playerScreen = (RelativeLayout) findViewById(R.id.playerScreen); 
    seekBar = (SeekBar) findViewById(R.id.seekBar); 
    seekBar.setOnSeekBarChangeListener(this); 
    songCurrentDurationLabel = (TextView) findViewById(R.id.songCurrentDurationLabel); 
    songTotalDurationLabel = (TextView) findViewById(R.id.songTotalDurationLabel); 
    utils = new Utilities(); 

    final ImageButton btn_player_screen = (ImageButton) findViewById(R.id.btn_player_screen); 
    btn_player_screen.setOnClickListener(new View.OnClickListener() { 
     //this hides/unhides the part of the layout in which the player is 
     @Override 
     public void onClick(View arg0) { 
      if (playerScreen.isShown()) { 
       playerScreen.setVisibility(View.GONE); 
      } else { 
       playerScreen.setVisibility(View.VISIBLE); 
      } 
     } 
    }); 

    final Button btn_default_acc_whole = (Button) findViewById(R.id.btn_default_acc_whole); 
    btn_default_acc_whole.setOnClickListener(new View.OnClickListener() { 
     public void onClick(View arg0) {//problem here is 
      if (playerState == PlayerState_ScAcc) { 
       stopSentencePlayer(); 
       setEngAu(R.raw.default_acc_audio); 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_DefAcc); 
      }else if (playerState == PlayerState_Sc_Paused){ 
       stopSentencePlayer(); 
       setEngAu(R.raw.default_acc_audio); 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_DefAcc); 
      }else if (playerState == PlayerState_DefAcc) { 
       wholeTextPlayer.pause(); 
       setPlayerState(PlayerState_Def_Paused); 
      } else if (playerState == PlayerState_Def_Paused) { 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_DefAcc); 
      } else { 
       setEngAu(R.raw.default_acc_audio); 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_DefAcc); 
      } 
     } 
    }); 

    final Button btn_scottish_acc_whole = (Button) findViewById(R.id.btn_scottish_acc_whole); 
    btn_scottish_acc_whole.setOnClickListener(new View.OnClickListener() { 
     public void onClick(View arg0) {//problem here is 
      if (playerState == PlayerState_DefAcc) { 
       stopSentencePlayer(); 
       setEngAu(R.raw.scottish_acc_audio); 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_ScAcc); 
      }else if (playerState == PlayerState_Def_Paused){ 
       stopSentencePlayer(); 
       setEngAu(R.raw.scottish_acc_audio); 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_ScAcc); 
      }else 
      if (playerState == PlayerState_ScAcc) { 
       wholeTextPlayer.pause(); 
       setPlayerState(PlayerState_Sc_Paused); 
      } else if (playerState == PlayerState_Sc_Paused) { 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_ScAcc); 
      } else { 
       setEngAu(R.raw.scottish_acc_audio); 
       wholeTextPlayer.start(); 
       setPlayerState(PlayerState_ScAcc); 
      } 
     } 
    }); 
} 

private final int PlayerState_Def_Paused = 1; 
private final int PlayerState_Sc_Paused = 2; 
private final int PlayerState_DefAcc = 3; 
private final int PlayerState_ScAcc = 4; 

private int playerState; 

private void setPlayerState(int state) { 
    playerState = state; 
} 

public void setEngAu(int engAu) { 
    wholeTextPlayer = MediaPlayer.create(this, engAu); 
    seekBar.setProgress(0); 
    seekBar.setMax(100); 
    updateSeekBar(); 
} 

public void updateSeekBar() { 
    handler.postDelayed(mUpdateTimeTask, 100); 
} 

private Runnable mUpdateTimeTask = new Runnable() { 
    public void run() { 
     long totalDuration = wholeTextPlayer.getDuration(); 
     long currentDuration = wholeTextPlayer.getCurrentPosition(); 
     songTotalDurationLabel.setText(""+utils.milliSecondsToTimer(totalDuration)); 
     songCurrentDurationLabel.setText(""+utils.milliSecondsToTimer(currentDuration)); 
     int progress = (int)(utils.getProgressPercentage(currentDuration, totalDuration)); 
     seekBar.setProgress(progress); 
     handler.postDelayed(this, 100); 
    } 
}; 

public void onProgressChanged(SeekBar seekBar, int progress, boolean fromTouch) { 
} 

public void onStartTrackingTouch(SeekBar seekBar) { 
    handler.removeCallbacks(mUpdateTimeTask); 
} 

public void onStopTrackingTouch(SeekBar seekBar) { 
    handler.removeCallbacks(mUpdateTimeTask); 
    int totalDuration = wholeTextPlayer.getDuration(); 
    int currentPosition = utils.progressToTimer(seekBar.getProgress(), totalDuration); 
    wholeTextPlayer.seekTo(currentPosition); 
    updateSeekBar(); 
} 

private void stopSentencePlayer() { 
    if(wholeTextPlayer !=null){ 
     try{ 
      wholeTextPlayer.release(); 
     }catch(Exception e){ 

      e.printStackTrace(); 
     } 
    } 
} 

@Override 
public void onBackPressed(){ 
    if(wholeTextPlayer != null){ 

      wholeTextPlayer.release(); 

     } 
    finish(); 
    super.onBackPressed(); 
} 

} 

另一种选择可能是回到那个启动媒体播放器,并在这种情况下,音频可以暂停,等屏幕相同的状态,但它似乎超出我的能力:(玩家可以在后台播放,这很好。

我希望我抓住正确的部分。我只是一个新手:)

1-06 17:27:02.909 6596-6596/com.tanuljangolulmenetkozben.app E/AndroidRuntime﹕ FATAL EXCEPTION: main 
java.lang.IllegalStateException 
     at android.media.MediaPlayer.getDuration(Native Method) 
     at com.tanuljangolulmenetkozben.app.Lesson1Grammar$4.run(Lesson1Grammar.java:128) 
     at android.os.Handler.handleCallback(Handler.java:587) 
     at android.os.Handler.dispatchMessage(Handler.java:92) 
     at android.os.Looper.loop(Looper.java:130) 
     at android.app.ActivityThread.main(ActivityThread.java:3705) 
     at java.lang.reflect.Method.invokeNative(Native Method) 
     at java.lang.reflect.Method.invoke(Method.java:507) 
     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:839) 
     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:597) 
     at dalvik.system.NativeStart.main(Native Method) 
11-06 17:27:06.022 1675-1835/? E/Omap4ALSA﹕ called drain&close' 
+0

粘贴您的日志请 – droidev

+1

我想,你的处理器继续运行,并导致您在onBackPressed中释放MediaPlayer,'getDuration()'设置为空引用。当您释放媒体播放器时,您应该中断您的线程。 – Fllo

+0

感谢@Fllo的推荐。我将下面一行添加到了onBackPressed方法中,它实现了这个诀窍。 handler.removeCallbacksAndMessages(null); – Immy

回答

1

正如我所评论的,当用户点击onBackPressed()时,Handler继续运行,而您的Activity正在销毁。因此,你必须检查该Handler运行和停止它,你已经在onStopTrackingTouch()方法做:

public void onStopTrackingTouch(SeekBar seekBar) { 
    handler.removeCallbacks(mUpdateTimeTask); 
    ... 
} 

所以,onBackPressed应该看起来像:

@Override 
public void onBackPressed() { 
    if (wholeTextPlayer != null) { 
     wholeTextPlayer.release(); 

     if (handler != null) 
      handler.removeCallbacks(null); 
    } 
    finish(); 
    super.onBackPressed(); 
} 

另一个好行为应该停止它在或onStop

@Override 
protected void onStop() { 
    super.onStop(); 
    if (handler != null) 
     handler.removeCallbacks(null); 
} 
+1

它没有工作,但我不得不使用handler.removeCallbacksAndMessages(null);因为handler.removeCallbacks(null);似乎没有工作。我真的不知道有什么不同,但主要的是,它的工作原理。再次感谢 – Immy

0
private Runnable mUpdateTimeTask = new Runnable() { 
    public void run() { 
     if(wholeTextPlayer != null){ 
     } 
} 
}; 

添加如果条件和检查

+0

我试过了,但没有帮助。 Fllo的回答帮助了我。感谢您试图帮助我,虽然:) – Immy