无法从IP摄像机接收RTSP实时流

3

我想使用RTSP从IP摄像头接收实时流,但是我得到了'无法播放此视频'的提示,并且出现了以下异常:

07-16 14:06:26.945: D/MediaPlayer(19411): setDataSource IOException happend : 
07-16 14:06:26.945: D/MediaPlayer(19411): java.io.FileNotFoundException: No content provider: rtsp://192.168.30.108:554
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.content.ContentResolver.openTypedAssetFileDescriptor(ContentResolver.java:1052)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.content.ContentResolver.openAssetFileDescriptor(ContentResolver.java:907)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.content.ContentResolver.openAssetFileDescriptor(ContentResolver.java:834)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.media.MediaPlayer.setDataSource(MediaPlayer.java:973)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.widget.VideoView.openVideo(VideoView.java:337)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.widget.VideoView.setVideoURI(VideoView.java:247)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.widget.VideoView.setVideoURI(VideoView.java:237)
07-16 14:06:26.945: D/MediaPlayer(19411):   at com.example.video_rtsp.MainActivity$2.run(MainActivity.java:59)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.os.Handler.handleCallback(Handler.java:733)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.os.Handler.dispatchMessage(Handler.java:95)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.os.Looper.loop(Looper.java:157)
07-16 14:06:26.945: D/MediaPlayer(19411):   at android.app.ActivityThread.main(ActivityThread.java:5293)
07-16 14:06:26.945: D/MediaPlayer(19411):   at java.lang.reflect.Method.invokeNative(Native Method)
07-16 14:06:26.945: D/MediaPlayer(19411):   at java.lang.reflect.Method.invoke(Method.java:515)
07-16 14:06:26.945: D/MediaPlayer(19411):   at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
07-16 14:06:26.945: D/MediaPlayer(19411):   at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
07-16 14:06:26.945: D/MediaPlayer(19411):   at dalvik.system.NativeStart.main(Native Method)
07-16 14:06:26.945: D/MediaPlayer(19411): Couldn't open file on client side, trying server side
07-16 14:06:26.955: V/MediaPlayer(19411): setVideoSurfaceTexture
07-16 14:06:26.955: V/MediaPlayer-JNI(19411): setAudioStreamType: 3
07-16 14:06:26.955: V/MediaPlayer(19411): MediaPlayer::setAudioStreamType
07-16 14:06:26.955: V/MediaPlayer(19411): setVideoSurfaceTexture
07-16 14:06:26.955: V/MediaPlayer(19411): prepareAsync
07-16 14:06:26.965: D/ProgressBar(19411): setProgressDrawable drawableHeight = 48
07-16 14:06:26.985: D/AbsSeekBar(19411): AbsSeekBar Constructor: misSeebarAnimationAvailable = true

我使用以下方法:
VideoView videoView = (VideoView) ((Activity) ctx).findViewById(R.id.videoView);

//add controls to a MediaPlayer like play, pause.
MediaController mc = new MediaController(ctx);
videoView.setMediaController(mc);

//Set the path of Video or URI
videoView.setVideoURI(Uri.parse("rtsp://192.168.30.108:554"));

//Set the focus
videoView.requestFocus();

我不能确定这是否是问题,但我认为可能是因为相机软件需要进行身份验证,但如果是这样的话,我不知道如何向其提供身份验证。


在使用setDataSource时,使用MediaPlayer后,我得到了以下异常:

07-21 12:04:11.677: W/System.err(17714): java.io.IOException: Prepare failed.: status=0x1
07-21 12:04:11.677: W/System.err(17714):    at android.media.MediaPlayer.prepare(Native Method)

我不确定这是否与设置标头的方式有关:

Uri uri = Uri.parse("rtsp://192.168.30.108:554");
Map<String , String> headres = new HashMap<String, String>();
headres.put("Authorization", "Basic ce0ca0f0864513c28c7be98f0f929be7b1f5db79"); //Also tried it without "Basic"
headres.put("encryption", "Default");
headres.put("mac", "9002A9D89200");
headres.put("random", "1715377261");
headres.put("realm", "Login to 90:02:a9:d8:92:00");

mediaPlayer.setDataSource(getApplicationContext(), uri, headres);

以下是使用Firebug获取登录过程中的头部信息和JSON数据的截图:

enter image description here

enter image description here


@aergistal 是的,我试过了,没有什么新的。 - Muhammed Refaat
1
尝试使用另一个播放器(如VLC)在同一台机器上播放流。 - aergistal
1
你是否尝试将身份验证信息放入URI中(在VLC中也是如此),就像@aergistal在他的第一条评论中提到的那样? 在你的例子中,使用rtsp://username:password@192.168.30.108:554而不是rtsp://192.168.30.108:554 - Levite
我不确定那个base64编码是否正确。你是怎么获取它的? - aergistal
@MuhammedRefaat:你找到解决方案了吗?我在尝试连接DLink IP摄像头时遇到了相同的异常。 - Christopher
显示剩余5条评论
1个回答

1
如果身份验证机制是HTTP基本身份验证,则可能有设置所需的HTTP标头的方法:MediaPlayer类具有一个接受Map参数用于标头的setDataSource方法: public void setDataSource(Context context, Uri uri, Map<String, String> headers) 您必须设置Authorization标头: Authorization: Basic _credentials_ _credentials_username:password字符串的RFC2045-MIME Base64编码。

谢谢您的回答,请看一下我的更新。 - Muhammed Refaat
当我执行解码时,它给我一个二进制数据文件而不是特定的单词组合,而且当我手动编码用户名:密码时,它并没有给我上面的代码。 - Muhammed Refaat

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