在SDK 8中使用Android MediaPlayer进行流媒体传输

14

SDK 8(Froyo)引入了MediaPlayer本地连接流媒体源(例如Shoutcast)的功能。之前的SDK版本可以使用一些解决方法,比如在设备上运行本地代理(参见 NPR)。

我采用了与NPR相同的方法,并使用StreamProxy。但是,NPR首先检查当前运行的SDK是否低于8。如果是,则使用代理。否则,它会直接连接。

我的StreamProxy从Shoutcast服务器请求元数据,因此它不仅仅是将数据从Shoutcast路由到客户端。相反,它解析元数据并根据需要使用它,并且只路由音乐数据。

当尝试在SDK级别8或以上使用StreamProxy时,MediaPlayer无法准备。我的StreamProxy接收连接并接受它,在成功向客户端写出状态行和头文件后,下一次写操作产生java.net.SocketException: Connection reset by peer。这导致客户端的mediaplayer抛出一个Error(1,-1007)

我正在努力找出为什么MediaPlayer无法连接到我的本地代理。它应该与连接原始源相同而没有元数据,这个方法是有效的。我通过我的代理转发所有来自外部源的标头,包括内容类型。

我会继续研究,但感觉已经走到了死胡同。如果需要更多细节,请让我知道。


如何播放SHOUTcast?https://dev59.com/nWoy5IYBdhLWcg3wQr1i#8833346 - Yaqub Ahmad
2个回答

12

编辑:好的,我现在相信我已经有了答案!

当涉及到HTTP头中的行尾时,Stagefright是严格的;它们必须是CR,LF而不仅仅是之前有效的LF。

因此,如果您构建自己的头,请用"\r\n"替换任何"\n",然后问题就解决了。

(如果您想自己检查这一点,请查看media/libstagefright/HTTPStream.cpp中的receive_line()

现在我可以在2.2 / Stagefright手机上流式传输带元数据的shoutcast ...

...

我遇到了同样的问题;

首先,我尝试将流式传输的数据写入固定长度的文件并使用setLooping(true)进行包装和播放。当MP3循环时,会出现故障,即使我提取整个MP3帧并尝试使用0xff和0x00填充结尾处的不平衡字节。如果您有足够大的文件,这仍然可能是可接受的解决方案。

然后,我做了代理的事情,在我的三星Galaxy S(v2.2)上工作,但不在模拟器中,显然也不在Desire上(不起作用=错误-1007如上所述)。

一个提示可能是Galaxy S Mediaplayer要求HTTP1.0,而在模拟器中为1.1。

暴力方法是并行打开两个流,从一个读取元数据,从另一个传输数据 ;)

无论如何,我也想听听其他人是否有更多的运气...


-1007 错误发生在 Stagefright 而不是 Opencore 上。似乎 Galaxy S v2.2 仍然使用 OpenCore。 - Sasq

1

MediaPlayer自API级别1以来就提供了流媒体功能。一年半前,我做了一个演示RTSP视频播放器。Nagare shoutcast客户端现在已经两岁了。

我错过了什么吗?


直接连接Shoutcast源在2.2之前从未起作用。 SDK 8引入了StageFright(http://developer.android.com/sdk/android-2.2-highlights.html#PlatformTechnologies),一个新的媒体播放器框架。 我会查看他们如何在Nagare中实现它,并且我很想知道它是否对2.2之前和之后都能做到同样的事情。 - Dharwin
没问题!我自己也没有完全理解这些变化的能力。 不过,这让我想知道是否可以将我的媒体播放器设置为使用旧的框架。现在正在研究这个问题。 - Dharwin
1
看起来Nagare只是将音频流式传输到一个越来越大的文件中。这也导致MediaPlayer经常跳过。我不确定我能否使用该方法。 - Dharwin

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