OSX CoreAudio:提前获取 inNumberFrames - 在初始化时?
OSX CoreAudio: Getting inNumberFrames in advance - on initialization?
我正在尝试用 C 语言编写一个简单的基于单 AU 播放的(几乎)无延迟 跟踪相位声码器 原型。它是一个独立的程序。我想知道单个渲染回调可以安全地承受多少处理负载,所以我更喜欢远离异步 DSP。
我的想法是只有一个预定值,即window step,或hop size or decimation factor文献来源)。这个数字等于 inNumberFrames
,这在某种程度上取决于 设备采样率 (还有什么?)。所有其他参数,例如 window size 和 FFT size 将根据 window 步骤设置。这似乎是将所有内容保留在一个回调中的最简单方法。
在实际渲染开始之前,即在调用 AudioOutputUnitStart()
之前,是否有一种安全的方法可以独立于机器安全地猜测或查询可能是 inNumberFrames
?
相位声码器算法大部分是标准的并且非常简单,使用 vDSP 函数进行 FFT,加上自定义相位积分,我没有遇到任何问题。
其他调试信息
此代码正在监视输入回调中的计时:
static Float64 prev_stime; //prev. sample time
static UInt64 prev_htime; //prev. host time
printf("inBus: %d\tframes: %d\tHtime: %lld\tStime: %7.2lf\n",
(unsigned int)inBusNumber,
(unsigned int)inNumberFrames,
inTimeStamp->mHostTime - prev_htime,
inTimeStamp->mSampleTime - prev_stime);
prev_htime = inTimeStamp->mHostTime;
prev_stime = inTimeStamp->mSampleTime;
奇怪的是,TimeStamp->mSampleTime 中的参数实际上显示了渲染帧的数量(参数名称似乎有些误导)。这个数字总是 512
,无论是否在运行时通过 AudioMIDISetup.app 重新设置了另一个采样率,就好像该值已经以编程方式硬编码一样.一方面,
inTimeStamp->mHostTime - prev_htime
间隔根据以数学上清晰的方式设置的采样率动态变化。只要采样率值匹配 44100Hz 的倍数,就会进行实际渲染。另一方面,48kHz 的倍数产生渲染 error -10863 ( =
kAudioUnitErr_CannotDoInCurrentContext )
。我一定错过了很重要的一点。
假设 audioUnit 是一个输入音频单元:
UInt32 inNumberFrames = 0;
UInt32 propSize = sizeof(UInt32);
AudioUnitGetProperty(audioUnit,
kAudioDevicePropertyBufferFrameSize,
kAudioUnitScope_Global,
0,
&inNumberFrames,
&propSize);
帧数通常是采样率乘以缓冲持续时间。有一个音频单元 API 请求采样率和首选缓冲持续时间(例如 44100 和 5.8 毫秒导致 256 帧),但并非所有 OS 版本上的所有硬件都支持所有请求的缓冲持续时间或采样率。
This number would equal inNumberFrames, which somehow depends on the device sampling rate (and what else?)
这取决于您尝试将其设置为什么。你可以设置它。
// attempt to set duration
NSTimeInterval _preferredDuration = ...
NSError* err;
[[AVAudioSession sharedInstance]setPreferredIOBufferDuration:_preferredDuration error:&err];
// now get the actual duration it uses
NSTimeInterval _actualBufferDuration;
_actualBufferDuration = [[AVAudioSession sharedInstance] IOBufferDuration];
它会使用一个大致在您设置的首选值附近的值。实际使用的值是基于2的幂和当前采样率的时间间隔。
如果您正在寻找跨设备的一致性,请选择 10 毫秒左右的值。性能最差的合理现代设备是 iOS 没有后置摄像头的 iPod touch 16gb。但是,此设备可以毫无问题地执行大约 10 毫秒的回调。在某些设备上,您 "can" 将持续时间设置得非常低并获得非常快的回调,但通常它会破裂,因为在下一次回调发生之前回调中的处理尚未完成。
我正在尝试用 C 语言编写一个简单的基于单 AU 播放的(几乎)无延迟 跟踪相位声码器 原型。它是一个独立的程序。我想知道单个渲染回调可以安全地承受多少处理负载,所以我更喜欢远离异步 DSP。
我的想法是只有一个预定值,即window step,或hop size or decimation factor文献来源)。这个数字等于 inNumberFrames
,这在某种程度上取决于 设备采样率 (还有什么?)。所有其他参数,例如 window size 和 FFT size 将根据 window 步骤设置。这似乎是将所有内容保留在一个回调中的最简单方法。
在实际渲染开始之前,即在调用 AudioOutputUnitStart()
之前,是否有一种安全的方法可以独立于机器安全地猜测或查询可能是 inNumberFrames
?
相位声码器算法大部分是标准的并且非常简单,使用 vDSP 函数进行 FFT,加上自定义相位积分,我没有遇到任何问题。
其他调试信息
此代码正在监视输入回调中的计时:
static Float64 prev_stime; //prev. sample time
static UInt64 prev_htime; //prev. host time
printf("inBus: %d\tframes: %d\tHtime: %lld\tStime: %7.2lf\n",
(unsigned int)inBusNumber,
(unsigned int)inNumberFrames,
inTimeStamp->mHostTime - prev_htime,
inTimeStamp->mSampleTime - prev_stime);
prev_htime = inTimeStamp->mHostTime;
prev_stime = inTimeStamp->mSampleTime;
奇怪的是,TimeStamp->mSampleTime 中的参数实际上显示了渲染帧的数量(参数名称似乎有些误导)。这个数字总是 512
,无论是否在运行时通过 AudioMIDISetup.app 重新设置了另一个采样率,就好像该值已经以编程方式硬编码一样.一方面,
inTimeStamp->mHostTime - prev_htime
间隔根据以数学上清晰的方式设置的采样率动态变化。只要采样率值匹配 44100Hz 的倍数,就会进行实际渲染。另一方面,48kHz 的倍数产生渲染 error -10863 ( =
kAudioUnitErr_CannotDoInCurrentContext )
。我一定错过了很重要的一点。
假设 audioUnit 是一个输入音频单元:
UInt32 inNumberFrames = 0;
UInt32 propSize = sizeof(UInt32);
AudioUnitGetProperty(audioUnit,
kAudioDevicePropertyBufferFrameSize,
kAudioUnitScope_Global,
0,
&inNumberFrames,
&propSize);
帧数通常是采样率乘以缓冲持续时间。有一个音频单元 API 请求采样率和首选缓冲持续时间(例如 44100 和 5.8 毫秒导致 256 帧),但并非所有 OS 版本上的所有硬件都支持所有请求的缓冲持续时间或采样率。
This number would equal inNumberFrames, which somehow depends on the device sampling rate (and what else?)
这取决于您尝试将其设置为什么。你可以设置它。
// attempt to set duration
NSTimeInterval _preferredDuration = ...
NSError* err;
[[AVAudioSession sharedInstance]setPreferredIOBufferDuration:_preferredDuration error:&err];
// now get the actual duration it uses
NSTimeInterval _actualBufferDuration;
_actualBufferDuration = [[AVAudioSession sharedInstance] IOBufferDuration];
它会使用一个大致在您设置的首选值附近的值。实际使用的值是基于2的幂和当前采样率的时间间隔。
如果您正在寻找跨设备的一致性,请选择 10 毫秒左右的值。性能最差的合理现代设备是 iOS 没有后置摄像头的 iPod touch 16gb。但是,此设备可以毫无问题地执行大约 10 毫秒的回调。在某些设备上,您 "can" 将持续时间设置得非常低并获得非常快的回调,但通常它会破裂,因为在下一次回调发生之前回调中的处理尚未完成。