diff --git a/headers/os/midi/Synth.h b/headers/os/midi/Synth.h index 4fbf49b384..aad46f2039 100644 --- a/headers/os/midi/Synth.h +++ b/headers/os/midi/Synth.h @@ -34,8 +34,7 @@ class BMidiSynthFile; namespace BPrivate { class BSoftSynth; } -class BSynth -{ +class BSynth { public: BSynth(); diff --git a/src/kits/midi/SoftSynth.cpp b/src/kits/midi/SoftSynth.cpp index 2c45368837..f2ca29c3e0 100644 --- a/src/kits/midi/SoftSynth.cpp +++ b/src/kits/midi/SoftSynth.cpp @@ -43,7 +43,10 @@ BSoftSynth::BSoftSynth() : fInitCheck(false), fSynth(NULL), fSettings(NULL), - fSoundPlayer(NULL) + fSoundPlayer(NULL), + fMonitor(NULL), + fMonitorSize(0), + fMonitorChans(-1) { fInstrumentsFile = NULL; SetDefaultInstrumentsFile(); @@ -65,6 +68,7 @@ BSoftSynth::~BSoftSynth() // a big deal, but the Midi Kit will complain (on stdout) that we // didn't release our endpoints. + delete[] fMonitor; Unload(); } @@ -527,13 +531,23 @@ BSoftSynth::PlayBuffer(void* cookie, void* data, size_t size, { BSoftSynth* synth = (BSoftSynth*)cookie; + if (synth->fMonitor != NULL) { + delete[] synth->fMonitor; + synth->fMonitor = NULL; + } // we use float samples - if (synth->fSynth) { fluid_synth_write_float( synth->fSynth, size / sizeof(float) / format.channel_count, data, 0, format.channel_count, data, 1, format.channel_count); + + synth->fMonitor = new float[size]; + synth->fMonitorSize = size; + synth->fMonitorChans = format.channel_count; + memcpy(synth->fMonitor, data, size); } + + } diff --git a/src/kits/midi/SoftSynth.h b/src/kits/midi/SoftSynth.h index 58b1f0b5ed..ccd7cb4b9d 100644 --- a/src/kits/midi/SoftSynth.h +++ b/src/kits/midi/SoftSynth.h @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2014, Haiku. * * Copyright (c) 2004-2005 Matthijs Hollemans * Copyright (c) 2003 Jerome Leveque @@ -9,6 +9,7 @@ * Jérôme Duval * Jérôme Leveque * Matthijs Hollemans + * Pete Goodeve */ #ifndef _SOFT_SYNTH_H @@ -107,6 +108,10 @@ private: fluid_settings_t* fSettings; BSoundPlayer* fSoundPlayer; + + float* fMonitor; + size_t fMonitorSize; + int16 fMonitorChans; }; } // namespace BPrivate diff --git a/src/kits/midi/Synth.cpp b/src/kits/midi/Synth.cpp index 8f64d9f855..7777d1cab7 100644 --- a/src/kits/midi/Synth.cpp +++ b/src/kits/midi/Synth.cpp @@ -220,11 +220,23 @@ BSynth::GetAudio(int16* pLeft, int16* pRight, int32 max_samples) const { // We don't print a "not supported" message here. That would cause // significant slowdowns because applications ask for this many times. + + if (fSynth->fMonitorSize <= 0) { + memset(pLeft, 0, max_samples * sizeof(int16)); + memset(pRight, 0, max_samples * sizeof(int16)); + return max_samples; + } - memset(pLeft, 0, max_samples * sizeof(int16)); - memset(pRight, 0, max_samples * sizeof(int16)); - - return max_samples; + int32 nSamples = fSynth->fMonitorSize / sizeof(float) + / fSynth->fMonitorChans; + if (nSamples > max_samples) + nSamples = max_samples; + float* sPtr = fSynth->fMonitor; + for (int32 i = 0; i < nSamples; i++, sPtr += fSynth->fMonitorChans) { + *pLeft++ = (int16)(*sPtr * 32768); + *pRight++ = (int16)(*(sPtr + 1) * 32768); + } + return nSamples; }