Web Audio API中实现无幅度调制的频率调制
问题:Web Audio API生成FM信号出现AM干扰
我正在用Web Audio API尝试生成一组简单的调频(FM)信号,但调制过程中出现了幅度调制(AM)干扰(可能是拍频现象?)。当前音频听感正常,但示波器显示存在幅度调制,需要生成无AM干扰的纯FM信号。以下是单通道振荡器的相关代码,求解决方案或建议!
oscMod[i] = audioCtx.createOscillator(); gainMod[i] = audioCtx.createGain(); oscCarrier[i] = audioCtx.createOscillator(); gainOsc[i] = audioCtx.createGain(); oscCarrier[i].frequency.value = initialHz; oscMod[i].frequency.value = 6;//rate of FM modulation gainMod[i].gain.value = 0; //10% modulation gainOsc[i].gain.value = 0; oscMod[i].connect(gainMod[i]); gainMod[i].connect(oscCarrier[i].frequency); oscCarrier[i].connect(gainOsc[i]); gainOsc[i].connect(audioCtx.destination) //10% modulation of the carrier frequency gainMod[channel].gain.setValueAtTime(oscCarrier[channel].frequency.value * .1, start) gainOsc[channel].gain.setValueAtTime(0, start); gainOsc[channel].gain.linearRampToValueAtTime(amp, start + rampTime)
示波器输出:
解决方案与建议
1. 同步振荡器起始相位
Web Audio振荡器默认起始相位可能存在随机偏移,会导致频率调制时引入不必要的幅度波动。强制设置两个振荡器的起始相位为0,保证相位同步:
oscMod[i].phase.value = 0; oscCarrier[i].phase.value = 0;
2. 调整参数设置时机
确保所有增益、频率参数的自动化设置在振荡器启动前完成,避免启动瞬间的参数突变引发幅度干扰:
// 先完成所有参数配置 const start = audioCtx.currentTime; oscCarrier[i].frequency.value = initialHz; oscMod[i].frequency.value = 6; gainMod[i].gain.setValueAtTime(oscCarrier[i].frequency.value * 0.1, start); gainOsc[i].gain.setValueAtTime(0, start); gainOsc[i].gain.linearRampToValueAtTime(amp, start + rampTime); // 再启动振荡器 oscMod[i].start(start); oscCarrier[i].start(start);
3. 优化调制参数与波形
纯FM信号的调制指数β = (调制频率偏移量) / 调制频率。若β值过大,信号频谱扩展可能超出预期,视觉上类似AM干扰。可适当降低调制深度(比如从10%降到5%)测试是否改善。
同时确认调制振荡器使用正弦波(Web Audio默认是正弦波,无需额外设置),避免使用方波、锯齿波等含谐波的波形,这类波形会引入额外幅度变化。
4. 排查示波器显示问题
有时候示波器触发设置不当会造成视觉假象:
- 切换到边缘触发模式,确保触发电平稳定在信号中间幅度
- 提高示波器采样率,至少达到载波频率的2倍以上,保证信号还原准确
内容的提问来源于stack exchange,提问作者shaedopotato
相关产品推荐
相关产品推荐

