我正在学习如何使用Steinberg VST 2.4 SDK(或者更确切地说,是3.6.0版本附带的2.x部分)。我创造了一个简单的合成器,用于在其生命周期内以恒定频率播放正弦波。这是这个合成器的代码:
static const float TAU = 3.14159f * 2;
AudioEffect* createEffectInstance(audioMasterCallback audioMaster) {
return new VSTTest(audioMaster);
}
VSTTest::VSTTest(audioMasterCallback audioMaster) : AudioEffectX(audioMaster, 0, NUM_PARAMS), //NUM_PARAMS is 0
fDeltaTime(1.0f / getSampleRate()), //time per sample (1.0 / 44100, presumably)
fFrequency(100.0f), //frequency of the wave (100 Hz)
fAmplitude(0.5f), //amplitude of the wave
fPos(0.0f) { //position of the wave in the x direction
setNumInputs(0);
setNumOutputs(2);
canProcessReplacing();
isSynth();
}
VSTTest::~VSTTest(void) {
}
void VSTTest::processReplacing(float** input, float** output, VstInt32 numFrames) {
for (VstInt32 i = 0; i < numFrames; i++) {
output[0][i] = fAmplitude * sin(fPos);
output[1][i] = fAmplitude * sin(fPos);
fPos += fFrequency * TAU * fDeltaTime;
if (fPos >= TAU) {
fPos = fmod(fPos, TAU);
}
}
}
void VSTTest::setSampleRate(float fSampleRate) {
fDeltaTime = 1.0f / fSampleRate;
}
问题在于,当VST作为FL Studio中的频道加载时,我可以听到(并看到)它在大约20秒内改变音高几次,直到它达到最终音高为止。甚至是正确的(偏离大约10赫兹)。为什么会这样?
答案 0 :(得分:0)
你正在向fPos添加一个巨大的数字,它应该加1。你正在寻找的公式是:
sinf(2.0 * M_PI * fPos++ * fFrequency / fSampleRate);
答案 1 :(得分:0)
这不是一个完整的答案,但这是通过计算resume()中的delta时间来解决的。
void VSTTest::resume(void) {
fDeltaTime = 1.0 / getSampleRate();
}
我不确定为什么需要这样做或者如何解决问题,但确实如此。另外,我应该注意fDeltaTime
不应该在构造函数中初始化,因为当时没有保证getSampleRate()
是正确的。