我正在处理一个图像库,其中包含音频,该音频是如何发音的,这些声音是用户在屏幕上查看的事物的发音,该音频通过还包含在屏幕中的按钮执行。
以下代码有效,但是有时音频在完成再现之前就被剪切掉了,问题是我没有收到任何错误日志。
View.OnClickListener eventoPlay = (v) → {
@Override
public void onClick(View v) {
btnPlaySound.setClickable(false);
try{
Uri myUri = Uri.parse(urlroot + urlAudio); //global variables by current image
final MediaPlayer mediaPlayer = new MediaPlayer();
mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
mediaPlayer.setDataSource(getApplicationContext(), myUri);
mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
@Override
public void onPrepared(MediaPlayer mp) {
mediaPlayer.start();
}
});
mediaPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
@Override
public void onCompletion(MediaPlayer mp) {
mp.release();
btnPlaySound.setClickable(true);
}
});
mediaPlayer.setOnErrorListener(new MediaPlayer.OnErrorListener() {
@Override
public boolean onError(MediaPlayer mp, int what, int extra) {
btnPlaySound.setClickable(true);
Log.e("Error in media player", String.valueOf(what));
Log.e("Error in media player", String.valueOf(extra));
return false;
}
});
mediaPlayer.prepareAsync();
}catch (Exception e){
e.printStackTrace();
btnPlaySound.setClickable(true);
}
}
};
btnPlaySound.setOnClickListener(eventoPlay);
btnPlaySound.performClick();
这些是我调试过的方案:
-setOnPreparedListener()
总是自然地通话(音频总是开始播放)。
-setOnCompletionListener()
仅在音频完成播放(如果音频未剪切)时呼叫。
-setOnErrorListener()
永远不会调用,无论音频是否被剪切。
-catch
不管音频是否被剪切,也永远不会执行此块。
我在三星Tab S3,三星Tab E,三星Tab A,阿尔卡特A3,小米MiA2,Swissmobility等设备中进行了测试。 在功能最强大的设备中,发生频率较低。但我希望这种失败永远不会发生。
Tnks。
答案 0 :(得分:1)
您可能要确保在UI线程上正在调用btnPlaySound.setClickable(true)。可能导致错误。另外,媒体播放器可能会在完成垃圾回收之前,保持对MediaPlayer的(强烈)引用以防止垃圾回收。
尝试以下操作以测试是否被垃圾回收了:
View.OnClickListener eventoPlay = (v) → {
@Override
public void onClick(View v) {
btnPlaySound.setClickable(false);
try{
Uri myUri = Uri.parse(urlroot + urlAudio); //global variables by current image
// KEEP A STRONG REFERENCE
mediaPlayer = new MediaPlayer();
mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
mediaPlayer.setDataSource(getApplicationContext(), myUri);
mediaPlayer.setLooping(false);
mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
@Override
public void onPrepared(MediaPlayer mp) {
mp.start();
}
});
mediaPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
@Override
public void onCompletion(MediaPlayer mp) {
mp.release();
btnPlaySound.setClickable(true);
}
});
mediaPlayer.setOnErrorListener(new MediaPlayer.OnErrorListener() {
@Override
public boolean onError(MediaPlayer mp, int what, int extra) {
mp.release();
btnPlaySound.setClickable(true);
Log.e("Error in media player", String.valueOf(what));
Log.e("Error in media player", String.valueOf(extra));
return false;
}
});
mediaPlayer.prepareAsync();
}catch (Exception e){
e.printStackTrace();
btnPlaySound.setClickable(true);
}
}
};
btnPlaySound.setOnClickListener(eventoPlay);
btnPlaySound.performClick();