使用 Android 流式传输 AAC 音频
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1650983/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Streaming AAC audio with Android
提问by bdls
As I understand it, Android will only play AAC format audio if it's encoded as MPEG-4 or 3GPP.
据我了解,如果编码为 MPEG-4 或 3GPP,Android 只会播放 AAC 格式的音频。
I'm able to play AAC audio encoded as M4A when it's local to the app, but it fails when obtaining it from a server.
当它在应用程序本地时,我可以播放编码为 M4A 的 AAC 音频,但是从服务器获取它时失败。
The following works, as the m4a file is held locally in the res/raw directory.
以下工作,因为 m4a 文件本地保存在 res/raw 目录中。
MediaPlayer mp = MediaPlayer.create(this, R.raw.*file*);
mp.start();
The following doesn't work. (But does with MP3's).
以下不起作用。(但与 MP3 的)。
Uri uri = Uri.parse("http://*example.com*/blah.m4a");
MediaPlayer mp = MediaPlayer.create(this, uri);
mp.start();
Can anyone shed any light on why it fails when the m4a audio file is not local?
当 m4a 音频文件不在本地时,任何人都可以解释为什么它会失败?
Here's (some of) the error...
这是(一些)错误...
ERROR/PlayerDriver(542): Command PLAYER_INIT completed with an error or info UNKNOWN PVMFStatus
ERROR/MediaPlayer(769): error (200, -32)
WARN/PlayerDriver(542): PVMFInfoErrorHandlingComplete
DEBUG/MediaPlayer(769): create failed:
DEBUG/MediaPlayer(769): java.io.IOException: Prepare failed.: status=0xC8
DEBUG/MediaPlayer(769): at android.media.MediaPlayer.prepare(Native Method)
DEBUG/MediaPlayer(769): at android.media.MediaPlayer.create(MediaPlayer.java:530)
DEBUG/MediaPlayer(769): at android.media.MediaPlayer.create(MediaPlayer.java:507)
...
I'm targeting SDK 1.6.
我的目标是 SDK 1.6。
回答by bdls
This work-aroundallows you to play M4A files from the net (and AAC files in other containers such as MP4 & 3GP). It simply downloads the file and plays from the cache.
此变通方法允许您从网络播放 M4A 文件(以及其他容器中的 AAC 文件,例如 MP4 和 3GP)。它只是下载文件并从缓存中播放。
private File mediaFile;
private void playAudio(String mediaUrl) {
try {
URLConnection cn = new URL(mediaUrl).openConnection();
InputStream is = cn.getInputStream();
// create file to store audio
mediaFile = new File(this.getCacheDir(),"mediafile");
FileOutputStream fos = new FileOutputStream(mediaFile);
byte buf[] = new byte[16 * 1024];
Log.i("FileOutputStream", "Download");
// write to file until complete
do {
int numread = is.read(buf);
if (numread <= 0)
break;
fos.write(buf, 0, numread);
} while (true);
fos.flush();
fos.close();
Log.i("FileOutputStream", "Saved");
MediaPlayer mp = new MediaPlayer();
// create listener to tidy up after playback complete
MediaPlayer.OnCompletionListener listener = new MediaPlayer.OnCompletionListener() {
public void onCompletion(MediaPlayer mp) {
// free up media player
mp.release();
Log.i("MediaPlayer.OnCompletionListener", "MediaPlayer Released");
}
};
mp.setOnCompletionListener(listener);
FileInputStream fis = new FileInputStream(mediaFile);
// set mediaplayer data source to file descriptor of input stream
mp.setDataSource(fis.getFD());
mp.prepare();
Log.i("MediaPlayer", "Start Player");
mp.start();
} catch (Exception e) {
e.printStackTrace();
}
}
回答by radhoo
There is a the open source OpenMXPlayerthat illustrates how to handle audio both for local files or online/streaming sources. It supports not only AAC, but also the other popular formats.
有一个开源 OpenMXPlayer说明了如何处理本地文件或在线/流媒体源的音频。它不仅支持 AAC,还支持其他流行的格式。
The idea behind it , is to use the MEdiaCodec API, introduced in Android 4.1 .
其背后的想法是使用 Android 4.1 中引入的 MEdiaCodec API。
Hope this provides a good starting point, for anyone needing a quick and hassle free audio player implementation.
希望这为任何需要快速且轻松的音频播放器实现的人提供了一个良好的起点。
回答by Sheraz Ahmad Khilji
There is a Freeware Advanced Audio (AAC) Decoder for Android. You can use this for help and Guidance or use Multiplayer class in it to playback aac audio. There is a sample app and library in it to help you understand
有一个适用于 Android的免费软件高级音频 (AAC) 解码器。您可以将其用于帮助和指导,或使用其中的 Multiplayer 类来播放 aac 音频。里面有一个示例应用程序和库可以帮助您理解
Hope this helps
希望这可以帮助
回答by Cristofer
I tried it too but I could not find out the solution!
我也试过了,但我找不到解决方案!
At the last Google I/O I saw something that helped me a lot. It is Extending from MediaPlayer and improve a lot of things! Take a look.
在上次 Google I/OI 上看到了一些对我帮助很大的东西。它是从 MediaPlayer 扩展并改进了很多东西!看一看。
EXOPLAYER CAN HELP YOU A LOT
EXOPLAYER 可以为您提供很多帮助
Check this part of the example:
检查示例的这一部分:
private static final int BUFFER_SEGMENT_SIZE = 64 * 1024;
private static final int BUFFER_SEGMENT_COUNT = 256;
...
// String with the url of the radio you want to play
String url = getRadioUrl();
Uri radioUri = Uri.parse(url);
// Settings for exoPlayer
Allocator allocator = new DefaultAllocator(BUFFER_SEGMENT_SIZE);
String userAgent = Util.getUserAgent(context, "ExoPlayerDemo");
DataSource dataSource = new DefaultUriDataSource(context, null, userAgent);
ExtractorSampleSource sampleSource = new ExtractorSampleSource(
radioUri, dataSource, allocator, BUFFER_SEGMENT_SIZE * BUFFER_SEGMENT_COUNT);
audioRenderer = new MediaCodecAudioTrackRenderer(sampleSource);
// Prepare ExoPlayer
exoPlayer.prepare(audioRenderer);
EXOPLAYER- I can play anything from streamings (video and audio)!
EXOPLAYER-我可以播放任何流媒体(视频和音频)!
LET ME KNOW IF YOU NEED HELP TO IMPLEMENT IT! :)
如果您需要帮助来实施它,请告诉我!:)
回答by Joel Grenon
I wrote a smal blog on a cloud-based solution I use for a music player I'm developing. It's based on the young Android Cloud Services (ACS) project, which isn't available yet, but still, it shows a potential solution using cloud-based transcoding to stream any media files. Have a look : http://positivelydisruptive.blogspot.com/2010/08/streaming-m4a-files-using-android-cloud.html
我写了一篇关于基于云的解决方案的小型博客,用于我正在开发的音乐播放器。它基于年轻的 Android 云服务 (ACS) 项目,该项目尚不可用,但它仍然展示了使用基于云的转码来流式传输任何媒体文件的潜在解决方案。看看:http: //positivelydisruptive.blogspot.com/2010/08/streaming-m4a-files-using-android-cloud.html
Joel
乔尔
回答by Goyuix
This is a wild shot in the dark, but I have seen similar behavior with the flash player where it actually ignores the file name and only relies on the MIME type sent by the server. Any idea what headers are being sent down from example.com? You might want to try wrapping your blah.m4a in a page that can set the headers and then stream the binary data. Give these types a shot and the community would appreciate a confirmation of what works:
这是在黑暗中疯狂的拍摄,但我已经看到 Flash Player 的类似行为,它实际上忽略了文件名,只依赖于服务器发送的 MIME 类型。知道从example.com发送哪些标头吗?您可能想尝试将 blah.m4a 包装在可以设置标题然后流式传输二进制数据的页面中。试一试这些类型,社区会很感激确认什么是有效的:
audio/mpeg audio/mp4a audio/mp4a-latm audio/aac audio/x-aac
音频/mpeg 音频/mp4a 音频/mp4a-latm 音频/aac 音频/x-aac
回答by subbarao
try --
尝试 -
1) MP.prepareAsync()
1) MP.prepareAsync()
2) onPrepared() { mp.start() }
2) onPrepared() { mp.start() }