Reply 840 of 965, by sergm
Hi, there
wrote:The 2 functions give different results regarding volume level. The floating point one results in twice the volume.
Whereas I completely agree with the Facts, I'm not sure if this statement is true. This is so relative. It may look straightforward to deal with the signal volume in the 16-bit integer format but float samples are NOT native for the original hardware units. Even with integer samples there are quite interesting things to consider.
Indeed, we took quite some time to ensure the correct output volume when it comes to integer samples. It closely corresponds to what we get using the digital sampling right at the DAC entrance when the analogue output emulation is turned off. You may consider the volume to be nearly bit-accurate. On the other hand, analogue output emulation does make the output signal volume differ (depending on the frequency), so even with integer samples there is not much to compare with. And I even don't mention that virtually every analogue capture taken from a real device may have arbitrary volume 😀
OK, speaking of this particular question, it depends on how you measure the volume of float samples. The mt32emu routine that does the sample format conversion actually divides an integer sample by 16384 to produce a float one, and correspondingly a float sample is multiplied by 16384 to return an integer sample. This is mainly intended to adapt to the common rule of having float samples normalised. So, if you say you get the output volume doubled, then it seems your audio processing path expects a different multiplier, i.e. 32768.
However, all is not that simple. Real units are famous of suffering from digital overflows. When we started the float rendering engine, the main goal was to get rid of that sort of things completely. So, the output signal you get with float samples is not actually normalised. It may exceed unity in absolute value, so you have a possibility to normalise the whole recording further.
Another thing to consider is the output from mt32emu is usually too low compared with SFX in most games. So, making it reliably never-ever overdriven is not an option as it'll be difficult to mix nicely. That is why we don't map float 1.0 to integer 32768. Actually, the float renderer internally maps unity to 8192 in the integer renderer. This is the natural full volume of a single playing partial in the engine. It leaves some room for mixing more partials though, but as I said, it's easy to overdrive. The multiplier 16384 used in the sample format converter just takes into account the DAC bit shift that real units feature.
In the conclusion, I'd want to note that it's quite easy to change the output volume with almost no effect on the emulation. Use functions mt32emu_set_output_gain and mt32emu_set_reverb_output_gain for this. By default, the gain is set to 1.0, so supplying a value of 0.5 makes the output twice lower.
PS: Though, I also agree that now, when mt32emu has two rendering engines side-by-side and provides sample format conversion in-flight, this stuff is rather confusing. I'll consider making the volume of float renderer such as to have smoother float <-> integer conversion.