我目前正在使用OpenAL来播放游戏音乐。它工作正常,除了它不能用于除原始WAV文件之外的任何东西。这意味着我最终得到了一个~9mb的音轨。
我是OpenAL的新手,我直接使用Apple的示例代码(https://developer.apple.com/library/ios/#samplecode/MusicCube/Listings/Classes_MyOpenALSupport_h.html%23//apple_ref/doc/uid/DTS40008978-Classes_MyOpenALSupport_h-DontLinkElementID_9)来获取缓冲区数据。
问题:有没有办法修改此功能,以便它读取压缩音频并动态解码?
我不是那么担心音频文件格式,只要它可以播放和压缩(如mp3,aac,caf)。我想要这样做(显然)的唯一原因是减小文件大小。
编辑似乎OpenAL中的问题并不像我用来获取缓冲区的方法那么多。 https://developer.apple.com/library/ios/#samplecode/MusicCube/Listings/Classes_MyOpenALSupport_h.html%23//apple_ref/doc/uid/DTS40008978-Classes_MyOpenALSupport_h-DontLinkElementID_9处的功能使用AudioFileOpenURL
和AudioFileReadBytes
。有没有办法让框架使用ExtAudioFileOpenURL
和ExtAudioFileRead
为我解码音频?
我在这里尝试了代码:https://devforums.apple.com/message/10678#10678,但我不知道该怎么做。我用来获取缓冲区的函数是https://developer.apple.com/library/ios/#samplecode/MusicCube/Listings/Classes_MyOpenALSupport_h.html%23//apple_ref/doc/uid/DTS40008978-Classes_MyOpenALSupport_h-DontLinkElementID_9,我还没有真正修改它,所以这就是我需要构建的东西。
我开始获得赏金,因为我真的需要这个,希望有人可以指出我正确的方向。
答案 0 :(得分:4)
您需要使用音频服务来加载其他格式。请记住,OpenAL ONLY仅支持未压缩的PCM数据,因此您加载的任何数据都需要在加载期间解压缩。
以下是一些代码,可以加载iOS支持的任何格式:https://github.com/kstenerud/ObjectAL-for-iPhone/blob/master/ObjectAL/ObjectAL/Support/OALAudioFile.m
如果您想要流式传输压缩的音轨类型音频,请使用AVAudioPlayer,因为它直接从磁盘播放压缩音频。
答案 1 :(得分:3)
您不需要任何第三方库来打开存档文件。在AudioToolbox/AudioToolbox.h
框架的帮助下,您可以打开并读取.caf
文件的数据,这是一个非常好的选择(在性能方面优于mp3或ogg)(最小的CPU影响)在减压期间)。因此,当数据到达OpenAL时,它已经是PCM
,准备填充缓冲区。以下是一些有关如何实现此目标的示例代码:
-(void) prepareFiles:(NSString *) filePath{
// get the full path of the file
NSString* fileName = [[NSBundle mainBundle] pathForResource:filePath ofType:@"caf"];
// open the file using the custom created methods (see below)
AudioFileID fileID = [self openAudioFile:fileName];
preparedAudioFileSize = [self audioFileSize:fileID];
if (preparedAudioFile){
free(preparedAudioFile);
preparedAudioFile = nil;
}
else{
;
}
preparedAudioFile = malloc(preparedAudioFileSize);
//read the data from the file into soundOutData var
AudioFileReadBytes(fileID, false, 0, &preparedAudioFileSize, preparedAudioFile);
//close the file
AudioFileClose(fileID);
}
-(AudioFileID)openAudioFile:(NSString*)filePath
{
AudioFileID fileID;
NSURL * url = [NSURL fileURLWithPath:filePath];
OSStatus result = AudioFileOpenURL((CFURLRef)url, kAudioFileReadPermission, 0, &fileID);
if (result != noErr) {
NSLog(@"fail to open: %@",filePath);
}
else {
;
}
return fileID;
}
-(UInt32)audioFileSize:(AudioFileID)fileDescriptor
{
UInt64 outDataSize = 0;
UInt32 thePropSize = sizeof(UInt64);
OSStatus result = AudioFileGetProperty(fileDescriptor, kAudioFilePropertyAudioDataByteCount, &thePropSize, &outDataSize);
if(result != 0) NSLog(@"cannot find file size");
return (UInt32)outDataSize;
}
答案 2 :(得分:1)
基于Karl上面的回复,我制作了一个最小的单个c ++函数,它打开一个文件并返回一个pcm音频缓冲区(适用于OpenAL)以及创建OpenAL声音所需的所有信息(格式,采样率,缓冲区等)。
您需要的两个文件位于: https://gist.github.com/ofTheo/5171369
希望它有所帮助! 西奥答案 3 :(得分:0)
答案 4 :(得分:0)
您可能尝试使用第三方库将mp3-ogg加载到char *缓冲区中,然后将此缓冲区提供给openAL。这将解决文件大小问题。
对于ogg,您应该在website
上找到这些库对于mp3,老实说我不知道在哪里可以找到一个可以做到这一点的轻量级库。但那应该存在。