我试图在Swift中将MIDI文件转换为音频文件(.m4a)。
现在,我正在使用米米迪作为一个工具来对MIDI文件进行排序和回放,但是它不包括将播放保存到文件中的能力。MIKMID的创建者概述了执行此这里的过程。为了捕获输出并将输出保存到音频文件中,我遵循这个例子尝试用Swift中的GeneralIO节点替换MIKMIDI的RemoteIO节点。当我试图使用AudioUnitRender和ExtAudioFileWrite将输出保存到文件时,它们都返回错误-50 (kAudio_ParamError)。
var channels = 2
var buffFrames = 512
var bufferList = AudioBufferList.allocate(maximumBuffers: 1)
for i in 0...bufferList.count-1{
var buffer = AudioBuffer()
buffer.mNumberChannels = 2
buffer.mDataByteSize = UInt32(buffFrames*sizeofValue(AudioUnitSampleType))
buffer.mData = calloc(buffFrames, sizeofValue(AudioUnitSampleType))
bufferList[i] = buffer
result = AudioUnitRender(generalIOAudioUnit, &flags, &inTimeStamp, busNum, UInt32(buffFrames), bufferList.unsafeMutablePointer)
inTimeStamp.mSampleTime += 1
result = ExtAudioFileWrite(extAudioFile, UInt32(buffFrames), bufferList.unsafeMutablePointer)
}是什么导致了错误-50,我如何解析它来将MIDI (脱机)呈现为.m4a文件?
UPDATE:我已经通过将mNumberChannels和通道更改为= 1来解决ExtAudioFileWrite错误-50。现在我得到了一个带有噪声的1秒音频文件。AudioUnitRender仍然返回错误-50。
发布于 2016-09-07 13:03:57
您的代码有几个问题:
AudioBufferList不符合客户端格式,请尝试
设bufferList = AudioBufferList.allocate(maximumBuffers: Int(clientFormat.mChannelsPerFrame))AUGraph替换错误的节点,并将剩余的节点连接到自身,从而在AudioUnitRender上产生一个无限循环。但主要的问题是,您没有实现作者建议的解决方案。您希望可以使用示例时间戳调用AudioUnitRender,速度比实时快,但是作者说没有,如果需要,您必须手动将示例时间转换为主机时间,并实现midi播放器的更好部分。
因此,您可以这样做(听起来很难),或者提交功能请求,或者在听音乐时记录到实时文件,方法是使用AudioUnitAddRenderNotify向图形的远程IO音频单元添加呈现通知,并在kAudioUnitRenderAction_PostRender阶段编写示例。
https://stackoverflow.com/questions/39310065
复制相似问题