制定振荡器波形代码并创建新的波形
我想编写一些在我的音调生成器应用程序中生成振荡器波形类型的代码。本例中的波是正弦波,有人可以告诉我代码是如何工作的吗,因为我想在将来制作自定义波类型以及方形、锯齿和三角形类型。
OSStatus RenderTone(
void *inRefCon,
AudioUnitRenderActionFlags *ioActionFlags,
const AudioTimeStamp *inTimeStamp,
UInt32 inBusNumber,
UInt32 inNumberFrames,
AudioBufferList *ioData)
{
// Fixed amplitude is good enough for our purposes
const double amplitude = 0.25;
// Get the tone parameters out of the view controller
ToneGeneratorViewController *viewController =
(ToneGeneratorViewController *)inRefCon;
double theta = viewController->theta;
double theta_increment = 2.0 * M_PI * viewController->frequency / viewController->sampleRate;
// This is a mono tone generator so we only need the first buffer
const int channel = 0;
Float32 *buffer = (Float32 *)ioData->mBuffers[channel].mData;
// Generate the samples
for (UInt32 frame = 0; frame < inNumberFrames; frame++)
{
buffer[frame] = sin(theta) * amplitude;
theta += theta_increment;
if (theta > 2.0 * M_PI)
{
theta -= 2.0 * M_PI;
}
}
// Store the theta back in the view controller
viewController->theta = theta;
return noErr;
}
I want to work out a bit of code that generates the oscillator wave-type in my tone generator app. The one in this example is a sine-wave, can someone tell me how the code works, as i want to in the future make custom wave-types and square, sawtooth and triangle types.
OSStatus RenderTone(
void *inRefCon,
AudioUnitRenderActionFlags *ioActionFlags,
const AudioTimeStamp *inTimeStamp,
UInt32 inBusNumber,
UInt32 inNumberFrames,
AudioBufferList *ioData)
{
// Fixed amplitude is good enough for our purposes
const double amplitude = 0.25;
// Get the tone parameters out of the view controller
ToneGeneratorViewController *viewController =
(ToneGeneratorViewController *)inRefCon;
double theta = viewController->theta;
double theta_increment = 2.0 * M_PI * viewController->frequency / viewController->sampleRate;
// This is a mono tone generator so we only need the first buffer
const int channel = 0;
Float32 *buffer = (Float32 *)ioData->mBuffers[channel].mData;
// Generate the samples
for (UInt32 frame = 0; frame < inNumberFrames; frame++)
{
buffer[frame] = sin(theta) * amplitude;
theta += theta_increment;
if (theta > 2.0 * M_PI)
{
theta -= 2.0 * M_PI;
}
}
// Store the theta back in the view controller
viewController->theta = theta;
return noErr;
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
正在生成实际的正弦波样本,并填充下面代码片段中的缓冲区
在分配 buffer[frame] 的行中,您正在调用 sin(theta) * 振幅code>,并且对于
for
循环的每次迭代,您都会根据频率和采样率将theta
增加一些有限的步长,通过这本质上是除以
>2.0 * PI * 频率
by你的采样率。在循环
for
循环时增加theta
变量基本上是一次推进一个样本的时间步,直到缓冲区已满(即frame == iNumberFrames< /代码>)。
如果您想生成除正弦波之外的其他波,只需将以下行替换为其他函数:
也就是说,例如,您想要收敛为三角波的无限傅里叶级数中的前三项;然后你可能会得到以下内容......
The actual sine wave samples are being generated and are populating the buffer in the snippet below
In the line where
buffer[frame]
is being assigned, you are callingsin(theta) * amplitude
, and for each iteration of thefor
loop, you are incrementingtheta
by some finite step size based on your frequency and sample rate, viaWhich is essentially dividing
2.0 * PI * frequency
by your sample rate.Incrementing the
theta
variable while looping through thefor
loop is basically advancing the time step one sample at a time until your buffer is full (i.e.frame == iNumberFrames
).If you wanted to generate something other than a sine wave, you would simply replace the following line with some other function:
I.e. let's say, for example, you wanted the first three terms in the infinite Fourier series that converges to a triangle wave; you might then have the following instead...
要产生所需的波形,您需要将 sin() 函数替换为产生所需波形的函数。
您也许能够在带有图形示例的函数表中找到此函数,或者您可能必须创建自己的函数。创建函数近似的方法有很多,包括多项式、傅立叶级数、带或不带插值的查表、递归等。但这本身就是一个大主题(许多教科书等)
To produce your desired waveform, you need to replace the sin() function with a function that produces your desired wave shape.
You might be able to find this function in a table of functions with graphical examples, or you might have to create your function. The are lots of ways to create a functional approximation, including polynomial, Fourier series, table lookup with or without interpolation, recursions, and etc. But that is a big subject on its own (many textbooks, etc.)