-
-
Notifications
You must be signed in to change notification settings - Fork 98
Description
Hi, first of all congratulations for the library.
I'm doing some experiments with this library using some of the most common soundfonts linked on the MuseScore SF page.
Everything works quite well with simple soundfonts like TimGM6mb.sf2.
Unfortunately I've found strange behaviors with the rendering of some (piano) instruments from high quality soundfonts like MuseScore_General.sf2/3 and MS Basic.sf3.
For example, in MuseScore_General.sf2 the programs 0, 1, 3 are much quieter than the other presets, the volume is so low that it is barely audible without headphones.
(In my main software that uses JavaSound, and therefore the integrated Gervill synthesizer, the volume of these instruments is instead rendered correctly.)
I decided to investigate a bit. I have only a very vague understanding of the SF2 specs, so please bear with me and take my observations with a grain of salt.
I initially checked the raw WAV samples, but they seem to be fine.
Eventually I compared other features and found something interesting.
First, for each low volume preset the samples are stereophonic (a feature not supported in TSF as in most SF synths, more on that below).
sample: Piano MF Bv1(L) - sampleType 4 - sampleLink 1100
sample: Piano MF Bv1(R) - sampleType 2 - sampleLink 1099
sample: Piano MF D#0(L) - sampleType 4 - sampleLink 1102
sample: Piano MF D#0(R) - sampleType 2 - sampleLink 1101
...
sample: Electric Piano G2 - sampleType 1 - sampleLink 0
sample: Electric Piano C3 - sampleType 1 - sampleLink 0
...
Secondly, but much more importantly, looking at the generator list, the stereo presets are the only ones that define the initial attenuation (48) and the attack/release volume envelopes (34/38)
Piano
generators=[48:174, 34:-7973, 38:165, 44:18947]
generators=[48:174, 34:-7973, 38:1902, 44:18947, 30:702]
...
Electric piano
generators=[8:-2084, 44:32634]
generators=[36:-182, 8:-2204, 44:31092]
…
So I decided to do an experiment: first I reduced the attenuation by a factor of 0.4f, as most SF midi synthesizers do.
voice->noteGainDB = f->globalGainDB - (0.4f * region->attenuation) - tsf_gainToDecibels(1.0f / vel);
and then I tried to remove the ampenv.level factor completely
gainMono = noteGain; // * v->ampenv.level;
After these two simple changes, the volume levels are now quite good and comparable to other instruments.
Of course, removing the amplitude volume envelope cannot be the final solution, but I can't figure out the root cause of the problem (and therefore an elegant solution).
Any ideas?
Finally, a note about stereo samples: it's really hard to find a synth that implements this part of the specs, but I accidentally found this library (under MIT license) that seems to implement this functionality, although I haven't tested it myself:
https://github.com/AnonN10/sf2hpp/blob/master/sf2.hpp#L1901
The library is very similar to TSF in scope, as it is a header-only C++ file, but unlike TSF it seems more limited as it doesn't implement controller change events (apart from sustain) for example.
One interesting thing though is the care with which it manages memory safety via unique_ptr.