Tôi đã viết một vòng lặp để mã hóa dữ liệu âm thanh pcm do ứng dụng của tôi tạo ra bằng aac sử dụng Dịch vụ tệp âm thanh mở rộng. Việc mã hóa diễn ra đồng bộ trong một chuỗi nền và không theo thời gian thực.ExtAudioFileWrite thành m4a/aac thất bại trên các thiết bị lõi kép (ipad 2, iphone 4s)
Mã hóa hoạt động hoàn hảo trên ipad 1 và iphone 3gs/4 cho cả ios 4 và 5. Tuy nhiên, đối với các thiết bị lõi kép (iphone 4s, ipad 2) cuộc gọi thứ ba tới ExtAudioFileWrite treo chuỗi mã hóa không có dấu vết ngăn xếp và không có mã lỗi.
Đây là mã trong câu hỏi:
Các định dạng dữ liệu
AudioStreamBasicDescription AUCanonicalASBD(Float64 sampleRate,
UInt32 channel){
AudioStreamBasicDescription audioFormat;
audioFormat.mSampleRate = sampleRate;
audioFormat.mFormatID = kAudioFormatLinearPCM;
audioFormat.mFormatFlags = kAudioFormatFlagsAudioUnitCanonical;
audioFormat.mChannelsPerFrame = channel;
audioFormat.mBytesPerPacket = sizeof(AudioUnitSampleType);
audioFormat.mBytesPerFrame = sizeof(AudioUnitSampleType);
audioFormat.mFramesPerPacket = 1;
audioFormat.mBitsPerChannel = 8 * sizeof(AudioUnitSampleType);
audioFormat.mReserved = 0;
return audioFormat;
}
AudioStreamBasicDescription MixdownAAC(void){
AudioStreamBasicDescription audioFormat;
audioFormat.mSampleRate = 44100.0;
audioFormat.mFormatID = kAudioFormatMPEG4AAC;
audioFormat.mFormatFlags = kMPEG4Object_AAC_Main;
audioFormat.mChannelsPerFrame = 2;
audioFormat.mBytesPerPacket = 0;
audioFormat.mBytesPerFrame = 0;
audioFormat.mFramesPerPacket = 1024;
audioFormat.mBitsPerChannel = 0;
audioFormat.mReserved = 0;
return audioFormat;
}
render loop
OSStatus err;
ExtAudioFileRef outFile;
NSURL *mixdownURL = [NSURL fileURLWithPath:filePath isDirectory:NO];
// internal data format
AudioStreamBasicDescription localFormat = AUCanonicalASBD(44100.0, 2);
// output file format
AudioStreamBasicDescription mixdownFormat = MixdownAAC();
err = ExtAudioFileCreateWithURL((CFURLRef)mixdownURL,
kAudioFileM4AType,
&mixdownFormat,
NULL,
kAudioFileFlags_EraseFile,
&outFile);
err = ExtAudioFileSetProperty(outFile, kExtAudioFileProperty_ClientDataFormat, sizeof(AudioStreamBasicDescription), &localFormat);
// prep
AllRenderData *allData = &allRenderData;
writeBuffer = malloc(sizeof(AudioBufferList) + (2*sizeof(AudioBuffer)));
writeBuffer->mNumberBuffers = 2;
writeBuffer->mBuffers[0].mNumberChannels = 1;
writeBuffer->mBuffers[0].mDataByteSize = bufferBytes;
writeBuffer->mBuffers[0].mData = malloc(bufferBytes);
writeBuffer->mBuffers[1].mNumberChannels = 1;
writeBuffer->mBuffers[1].mDataByteSize = bufferBytes;
writeBuffer->mBuffers[1].mData = malloc(bufferBytes);
memset(writeBuffer->mBuffers[0].mData, 0, bufferBytes);
memset(writeBuffer->mBuffers[1].mData, 0, bufferBytes);
UInt32 framesToGet;
UInt32 frameCount = allData->gLoopStartFrame;
UInt32 startFrame = allData->gLoopStartFrame;
UInt32 lastFrame = allData->gLoopEndFrame;
// write one silent buffer
ExtAudioFileWrite(outFile, bufferFrames, writeBuffer);
while (frameCount < lastFrame){
// how many frames do we need to get
if (lastFrame - frameCount > bufferFrames)
framesToGet = bufferFrames;
else
framesToGet = lastFrame - frameCount;
// get dem frames
err = theBigOlCallback((void*)&allRenderData,
NULL, NULL, 1,
framesToGet, writeBuffer);
// write to output file
ExtAudioFileWrite(outFile, framesToGet, writeBuffer);
frameCount += framesToGet;
}
// write one trailing silent buffer
memset(writeBuffer->mBuffers[0].mData, 0, bufferBytes);
memset(writeBuffer->mBuffers[1].mData, 0, bufferBytes);
processLimiterInPlace8p24(limiter, writeBuffer->mBuffers[0].mData, writeBuffer->mBuffers[1].mData, bufferFrames);
ExtAudioFileWrite(outFile, bufferFrames, writeBuffer);
err = ExtAudioFileDispose(outFile);
Các khung PCM được tạo ra đúng, nhưng ExtAudioFileWrite thất bại thứ 2/lần thứ 3 nó được gọi là.
Bất kỳ ý tưởng nào? Cảm ơn bạn!
Bạn có thể đăng cách bạn điền vào bộ đệm và cách bạn đang gọi ExtAudioFileWrite? – sbooth
Sau nhiều thất vọng và không có sự giúp đỡ từ Apple, đồng nghiệp của tôi đã tìm ra vấn đề. Rõ ràng trên các thiết bị iOS mới hơn (iPad 2 và iPhone 4S), 44,1 kHz không phải là tỷ lệ mẫu hợp lệ cho mã hóa AAC, ít nhất là sử dụng Dịch vụ tệp âm thanh bên ngoài. 48 kHz hoạt động tốt. Tôi đã gửi này cho Apple như một lỗi, hy vọng họ sẽ chăm sóc nó. – roperklacks