Hello,
this is my first post in this list and I hope it is the appropriate place
to discuss the issue but in case it's not I express my apologies.

I will try to describe in detail the needs and current limitations of the
JDK in terms of public API.
A common scenario in GUI MIDI applications consists in let the user choose
some form of "resources" (e.g. soundfonts) to produce actual waveforms from
the symbolic MIDI representation with the goal of both playback and saving
to disk. While in the JDK the former is available, it seems that it lacks
the second possibility.
In my specific case the JavaFX application allows to load a (possibly high
quality) .sf2 soundfonds file and playback midi sequences graphically in a
pianoroll editor and common practice notation viewer. Unfortunately there
isn't yet a "Save as .wav" functionality since at the moment (but let me
know if I'm wrong) there is no way to render the midi sequence to audio
wave using other than the default emergency Soundbank. (a low quality, DSP
generated, sf2 )
github.com/openjdk/jdk/blob/master/src/java.desktop/share/classes/com/sun/media/sound/EmergencySoundbank.java

In my opinion this is a severe lack of functionality in these cases and
creates an inconsistent behaviour: what you actually hear during playback
is not what you save.

Currently, for what I know, the only way to render a midi sequence relies
on the method:
AudioSystem.getAudioInputStream
that for MIDI files chooses as provider the SoftMidiAudioFileReader that
creates an AudioSynthesizer (SoftSynthesizer) as the Receiver of
time-stamped MIDI events and exploits its openStream method.
github.com/openjdk/jdk/blob/master/src/java.desktop/share/classes/com/sun/media/sound/SoftMidiAudioFileReader.java#L64

Unfortunately to conform to the strict interface signature this
implementation doesn't provide a way to pass a Soundbank as a parameter.

Anyway in the original Gervill project there was also an illustrative
example named Midi2WavRender with the added ability to select a custom
Soundbank before processing the events. Now there is no way to circumvent
this mechanism since the "key point" of the process is the openStream
method of the AudioSynthesizer interface that surprisingly is not public.
I've found two RF almost identical in scope (respectively from 2010 and
2016) that propose to make the interface public:

Make the AudioSynthesizer interface public
bugs.openjdk.org/browse/JDK-8170518
make public new synthesizer (gervill) functionality
bugs.openjdk.org/browse/JDK-6938913

however since there is no real activities in more than a decade my
expectations they move forward are quite low.

The current architecture of java sound is nice to get resources based on
the current hardware at hand, but often the desire of the developer it's
just using the default software synthesizer implementation (present in all
the JDKs regardless of specific hardware) with all the benefits it has to
offer.

Is there any real chance that in future releases of the JDK the
AudioSynthesizer will finally find its way into the public API?

Thanks in advance,
Mirco

P.S. forgive me but let me further express some feelings regarding parts of
the java sound internal API.
The Gervill software synthesizer (even before the integration of its code
in the upstream branch of the JDK) has always had amazing capabilities.
Using it's API it is possible to create virtual MIDI instruments using DSP
(e.g. DoubleFM, Additive/Subtrative synthesis) with just few lines of code
(thanks to the ModelAbstractOscillator class) or create .sf2 soundfonts
files from scratch using only a bunch of wave files (using the classes
SF2Soundbank, SF2Layer, SF2LayerRegion, SF2Instrument, SF2InstrumentRegion,
SF2Sample). Not counting the usual utilities common in almost every audio
library like FFT, iFFT, etc...
Moreover most of these internal classes are pure software with no specific
hardware requirements, pure math (DSP) and implement well established and
stable standards (e.g. Soundfonts specification).
After the JPMS it is possible to use them only with the usual hack:
--add-exports=java.desktop/com.sun.media.sound=ALL-UNNAMED  // or
<MYMODULENAME>
but of course this workaround is not advisable since later versions of the
JDK could completely prevent their inclusion.
It is really sad that such precious gems are concealed and not part of the
public API. What a waste.

Reply via email to