提问人:ecyoj 提问时间:8/25/2023 最后编辑:ecyoj 更新时间:8/25/2023 访问量:40
斯威夫特 - 如何以 8kHz 采样率从 iPhone 上的麦克风获取音频输出,缓冲区大小为 16ms 和 1 通道?
swift - how to get audio output from mic on iphone at 8khz sample rate with buffer size of 16ms & 1 channel?
问:
对于 iphone 上的演示应用程序,我想以 8khz 的频率从麦克风获取音频输出,缓冲区大小为 16ms,以便它一次提供 128 字节的帧长度。
我通过在输入节点上安装一个水龙头来尝试这个 AVAudioEngine,但无法设置采样率和缓冲区大小。关于如何实现 128 字节输出的任何建议?
采样率可以不同,但我需要 128 字节和 16 毫秒。
谢谢
private func startRecording() throws {
checkPermission()
if !self.hasPermissionToRecord {
return
}
if engine == nil {
engine = AVAudioEngine()
}
let inputNode = engine.inputNode
let microphoneOutputFormat: AVAudioFormat = inputNode.outputFormat(forBus: 0)
let microphoneAudioStream = microphoneOutputFormat.formatDescription.audioStreamBasicDescription
let microphoneSampleRate = microphoneAudioStream!.mSampleRate
var mulawDescription = AudioStreamBasicDescription(
mSampleRate: 8000,
mFormatID: kAudioFormatULaw,
mFormatFlags: 0,
mBytesPerPacket: 1,
mFramesPerPacket: 1,
mBytesPerFrame: 1,
mChannelsPerFrame: 1,
mBitsPerChannel: 8,
mReserved: 0
)
let mulawFormat = AVAudioFormat(streamDescription: &mulawDescription)!
converter = AVAudioConverter(from: microphoneOutputFormat, to: mulawFormat)
inputNode.installTap(onBus: 0, bufferSize: defaultUlawBufferSize, format: microphoneOutputFormat) { [self] (buffer: AVAudioPCMBuffer!, time: AVAudioTime!) in
let secondsInBuffer:Float64 = Float64(buffer.frameLength) / Float64(microphoneSampleRate);
let ulawBufferSize = UInt32(8000 * secondsInBuffer) // 800
// conversion - downsample
guard let mulawBuffer = AVAudioPCMBuffer(pcmFormat: converter.outputFormat, frameCapacity: 800) else {
return
}
var outError: NSError? = nil
let microphoneInputBlock: AVAudioConverterInputBlock = { (inNumbPackets, outStatus) -> AVAudioBuffer? in
outStatus.pointee = AVAudioConverterInputStatus.haveData
return buffer
}
self.converter.convert(to: mulawBuffer, error: &outError, withInputFrom: microphoneInputBlock)
let mulawData = Data(buffer:mulawBuffer)
if (!(receivedAudioCallback?(mulawData) ?? false)) {
stop()
}
}
engine.prepare()
try engine.start()
}
我试过这段代码,在以 8khz 下采样后,它给了我 800bytes
答: 暂无答案
评论