MediaPlayer的setDataSource方法中出现了IllegalStateException异常

9
我在MediaPlayer的onCompletion监听器中使用以下代码,其中我正在重复当前歌曲。
if (isRepeat) {
                if (mMediaPlayer.isPlaying()) {
                    mMediaPlayer.stop();
                    mMediaPlayer.reset();
                }
                try {
                    mMediaPlayer.setDataSource(MainActivity.localTrackList.get(MainActivity.currentOffset).getPath());
                    mMediaPlayer.prepareAsync();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }

但是我遇到了以下错误信息:
  at android.media.MediaPlayer._setDataSource(Native Method)
09-15 09:05:19.884 12545-12545/ W/System.err:     at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1115)
09-15 09:05:19.884 12545-12545/ W/System.err:     at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1100)
09-15 09:05:19.884 12545-12545/ W/System.err:     at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1079)
09-15 09:05:19.884 12545-12545/ W/System.err:     at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1028)

我该怎么处理这个问题?

3个回答

7
如果您的MediaPlayer没有播放任何内容或曲目已经结束,它将不会被重置。请将mMediaPlayer.reset();移出if条件。
try {
    mMediaPlayer.reset();
    mMediaPlayer.setDataSource(MainActivity.localTrackList.get(MainActivity.currentOffset).getPath());
    mMediaPlayer.prepareAsync();
} catch (IOException e) {
    e.printStackTrace();
}

在使用setDataSource()之前,您应该调用reset()

如果媒体正在播放,则您的条件绝对正确,但当曲目结束时,它会变为false。


prepareAsync 对我不起作用,而 prepare 是可以的。你能解释一下为什么会这样吗? - Rino

3
当MediaPlayer的状态为Idle时, MediaPlayer.setDataSource()才有用。您在 onCompletion中调用了此方法,因此Android系统向您返回了IllStateException异常。在 onCompletion方法中,mMediaPlayer.isPlaying()似乎始终返回false。
实际上,您不需要再次setDataSource,只需调用MediaPlayer.start()即可从头开始播放数据。
请参阅此状态图(摘自https://developer.android.com/reference/android/media/MediaPlayer.html#StateDiagram):

1
假设您有一个歌曲列表,并在单击歌曲时必须从文件播放该歌曲。您需要重新初始化MediaPlayer。设置isLooping是可选的。
这里的文件路径来自内部目录“/system/media/audio/alarms/Osmium.ogg”。
fun onItemClick(item: FetchMedia.SongModel) {
    if(mediaPlayer.isPlaying()){
        mediaPlayer.setLooping(false);
        mediaPlayer.stop();
    }
    mediaPlayer = MediaPlayer();
    mediaPlayer.setDataSource(item.DATA);
    mediaPlayer.prepare();
    mediaPlayer.start();
    mediaPlayer.setLooping(true);
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接