an engine sound generator written in JavaScript using the Web Audio API
Some attempts to implement an engine sound generator based on the ideas from this paper [1] and by using Three.js and the Web Audio API.
The Doppler effect is also implemented by using DelayNodes and setting the value of delayTime
.
http://antonio-r1.github.io/engine-sound-generator/src/engine_sound_generator/sounds.htm
The first attempt uses ‘AudioBufferSourceNode.start(when)’ for trying to generate the audio continuously. However, this does not seem to work correctly in some browsers.
http://antonio-r1.github.io/engine-sound-generator/src/engine_sound_generator/sounds_worklet.htm
The second attempt uses an AudioWorklet for generating the audio. Now, the volume for the intake, engine block vibrations and outlet sound can be set seperately and also the algorithm for the Doppler effect has been improved compared to the first attempt.
First of all, we have to import the modules:
import {SoundGeneratorAudioListener, SineWaveSoundGenerator, EngineSoundGenerator} from './sound_generator_worklet.js';
Then, the module used by the worklet needs to be loaded:
var loadingManager = new THREE.LoadingManager();
loadingManager.onLoad = function () {
moduleInit ();
};
listener = new SoundGeneratorAudioListener();
EngineSoundGenerator.load (loadingManager, listener);
In the moduleInit function add the listener to the camera and then create an EngineSoundGenerator object.
The EngineSoundGenerator object then needs to be added for example to a THREE.Object3d and then started with soundCarEngine.play()
.
The waveguide lengths are specified in samples.
soundCarEngine = new EngineSoundGenerator({listener: listener, parameters: {cylinders: 4,
intakeWaveguideLength: 100,
exhaustWaveguideLength: 100,
extractorWaveguideLength: 100,
intakeOpenReflectionFactor: 0.01,
intakeClosedReflectionFactor: 0.95,
exhaustOpenReflectionFactor: 0.01,
exhaustClosedReflectionFactor: 0.95,
ignitionTime: 0.016,
straightPipeWaveguideLength: 128,
straightPipeReflectionFactor: 0.01,
mufflerElementsLength: [10, 15, 20, 25],
action: 0.1,
outletWaveguideLength: 5,
outletReflectionFactor: 0.01}});
The value of the rpm paremeter can be set in the following way:
let rpmParam = soundCarEngine.worklet.parameters.get('rpm');
rpmParam.value = someValue;
The second attempt has also been ported to C++ and compiled with Emscripten to WebAssembly for making
the sound generator more efficient and removing the glitches. It can be built by activating the environment
variables of Emscripten and running make
in the sound_generator_wasm
folder.
This version can be used like the JavaScript version as described above, only the modules have to be imported from a different file:
import {SoundGeneratorAudioListener, SineWaveSoundGenerator, EngineSoundGenerator} from './sound_generator_worklet_wasm.js';