检测缓冲错误(或超时)Android MediaPlayer - 使用计时器超时?

时间:2013-03-18 16:39:42

标签: android timer android-mediaplayer

显然没有抛出任何异常,因此我可以在缓冲流音频内容时识别错误。例如,我已断开我的路由器,应用程序将继续尝试缓冲整个时间。当我重新连接然后它完成缓冲并且甚至在断开连接超过一分钟后继续!

所以问题是我不能让我的用户长时间坐在那里而不考虑问题。检测Android媒体播放器缓冲问题的正确方法是什么?

我正在考虑使用Timer进行超时。我可能会在15秒后开始(使用代理我测试了5kbps连接,这是最糟糕的情况,能够在6-10秒内开始播放,所以我认为15秒将是一个合理的超时时间)。这听起来像个好计划吗?如果是这样,我应该在每次缓冲区尝试时创建一个新的Timer,还是应该在播放服务的整个生命周期内保持相同的Timer?

所以基本上我问两个问题:

1)检测缓冲区是否有问题的正确方法是什么?我有一个倾听的倾听者吗?我已经尝试了MediaPlayer.OnErrorListener当然不会在我的测试中触发。我的结论是我必须超时才能检测到缓冲错误。

2)如果我在第一名上是正确的,那么使用计时器的正确方法是什么?每次缓冲区尝试创建一个或重用相同的缓冲区? 编辑我还应该重启(或取消并创建一个新的)Timer onBufferUpdate吗?使用onBufferUpdate监听器,我应该知道有些数据会返回,所以应该重置计时器。

4 个答案:

答案 0 :(得分:4)

根据您的问题,我了解主要目标是检测您的播放器因缓冲而停滞并采取某些措施的情况。为了处理这种情况,我觉得以下2个听众可能有助于识别相同的内容。

MediaPlayer.onBufferingUpdate将提供缓冲的及时进度。因此,如果有2个具有相同percent值的回调,则可能表示可能存在缓冲。

还有另一个听众MediaPlayer.onInfoListener,其中包含一些您可能感兴趣的特定事件。在此监听器上,如果whatMEDIA_INFO_BUFFERING_START,则表示播放器正在暂停播放以进行缓冲,即触发逻辑。同样地,MEDIA_INFO_BUFFERING_END表示在填充缓冲区后重新开始播放。

答案 1 :(得分:1)

你应该看到这篇文章。媒体播放器有一个ErrorListener来获取任何错误。

http://developer.android.com/reference/android/media/MediaPlayer.OnErrorListener.html

答案 2 :(得分:0)

int count=40;//for 40 seconds to wait for buffering after it will finish the activity
//boolean timeoutflag=false;

timeout = new Handler(Looper.getMainLooper()) {
            @Override
            public void handleMessage(Message msg) {
                System.out.println("value of count="+msg.getData().getLong("count"));
                if (msg.getData().getBoolean("valid")) {
                    if (msg.getData().getLong("count") == 0 && !timeoutflag) 
                    {

                        if (pDialog != null && pDialog.isShowing()) 
                                {   
                                try
                                {
                                pDialog.dismiss();
                                }catch(Exception e)
                                {
                                    e.printStackTrace();
                                }
                                }
                            Toast.makeText(getApplicationContext(),
                                    "Unable To Load This Video", Toast.LENGTH_LONG).show();
                        finish();

                    } else {
                    }

                }

            }
        };
        timeout.postDelayed(null, 0);
        new Thread(new Runnable() {

            @Override
            public void run() {
                while (count > 0) {
                    try {
                        Thread.sleep(1020);
                    } catch (Exception e) {
                    }

                    Message msg = new Message();
                    Bundle b = new Bundle();
                    b.putBoolean("valid", true);
                    b.putLong("count", --count);
                    msg.setData(b);
                    timeout.sendMessage(msg);

                }

            }
        }).start();
        // set timeoutflag=true; in setOnPreparedListener of video view

答案 3 :(得分:0)

对于准备期间的缓冲,您必须设置自己的计时器,在一段时间后调用player.reset()。这会让玩家回到初始状态。

对于准备后的缓冲(在播放期间),您必须监视getPosition()。如果它落后于某个最大值,则调用reset()。这允许您为播放设置体验阈值。处理不仅连接失败,而且连接断断续续。

最佳解决方案是不使用MediaPlayer。请改用公共VLC衍生产品。 MP有太多内化的私有设计限制,需要可怕的解决方法(例如,CANT添加编解码器)。在这种情况下,RTFM给你错误的希望。

除非你正在做一个非常直接的Android应用程序,不要依赖任何android api。一些开源替代品得到了更好的支持,并且有充分的理由。

(真正令人愉快地完成了令人满意的编辑咆哮删除)