Audio plugin host https://kx.studio/carla
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

FluidSynthPlugin.cpp 53KB

11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490
  1. /*
  2. * Carla FluidSynth Plugin
  3. * Copyright (C) 2011-2013 Filipe Coelho <falktx@falktx.com>
  4. *
  5. * This program is free software; you can redistribute it and/or
  6. * modify it under the terms of the GNU General Public License as
  7. * published by the Free Software Foundation; either version 2 of
  8. * the License, or any later version.
  9. *
  10. * This program is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU General Public License for more details.
  14. *
  15. * For a full copy of the GNU General Public License see the GPL.txt file
  16. */
  17. #include "CarlaPluginInternal.hpp"
  18. #ifdef WANT_FLUIDSYNTH
  19. #include <fluidsynth.h>
  20. #define FLUIDSYNTH_VERSION_NEW_API (FLUIDSYNTH_VERSION_MAJOR >= 1 && FLUIDSYNTH_VERSION_MINOR >= 1 && FLUIDSYNTH_VERSION_MICRO >= 4)
  21. CARLA_BACKEND_START_NAMESPACE
  22. class FluidSynthPlugin : public CarlaPlugin
  23. {
  24. public:
  25. FluidSynthPlugin(CarlaEngine* const engine, const unsigned int id, const bool use16Outs)
  26. : CarlaPlugin(engine, id),
  27. kUses16Outs(use16Outs),
  28. fSettings(nullptr),
  29. fSynth(nullptr),
  30. fSynthId(-1),
  31. fAudio16Buffers(nullptr)
  32. {
  33. carla_debug("FluidSynthPlugin::FluidSynthPlugin(%p, %i, %s)", engine, id, bool2str(use16Outs));
  34. // create settings
  35. fSettings = new_fluid_settings();
  36. // define settings
  37. fluid_settings_setint(fSettings, "synth.audio-channels", use16Outs ? 16 : 1);
  38. fluid_settings_setint(fSettings, "synth.audio-groups", use16Outs ? 16 : 1);
  39. fluid_settings_setnum(fSettings, "synth.sample-rate", kData->engine->getSampleRate());
  40. fluid_settings_setint(fSettings, "synth.threadsafe-api ", 0);
  41. // create synth
  42. fSynth = new_fluid_synth(fSettings);
  43. #ifdef FLUIDSYNTH_VERSION_NEW_API
  44. fluid_synth_set_sample_rate(fSynth, kData->engine->getSampleRate());
  45. #endif
  46. // set default values
  47. fluid_synth_set_reverb_on(fSynth, 0);
  48. fluid_synth_set_reverb(fSynth, FLUID_REVERB_DEFAULT_ROOMSIZE, FLUID_REVERB_DEFAULT_DAMP, FLUID_REVERB_DEFAULT_WIDTH, FLUID_REVERB_DEFAULT_LEVEL);
  49. fluid_synth_set_chorus_on(fSynth, 0);
  50. fluid_synth_set_chorus(fSynth, FLUID_CHORUS_DEFAULT_N, FLUID_CHORUS_DEFAULT_LEVEL, FLUID_CHORUS_DEFAULT_SPEED, FLUID_CHORUS_DEFAULT_DEPTH, FLUID_CHORUS_DEFAULT_TYPE);
  51. fluid_synth_set_polyphony(fSynth, 64);
  52. for (int i=0; i < 16; i++)
  53. fluid_synth_set_interp_method(fSynth, i, FLUID_INTERP_DEFAULT);
  54. }
  55. ~FluidSynthPlugin()
  56. {
  57. carla_debug("FluidSynthPlugin::~FluidSynthPlugin()");
  58. kData->singleMutex.lock();
  59. kData->masterMutex.lock();
  60. delete_fluid_synth(fSynth);
  61. delete_fluid_settings(fSettings);
  62. deleteBuffers();
  63. }
  64. // -------------------------------------------------------------------
  65. // Information (base)
  66. PluginType type() const
  67. {
  68. return PLUGIN_SF2;
  69. }
  70. PluginCategory category()
  71. {
  72. return PLUGIN_CATEGORY_SYNTH;
  73. }
  74. // -------------------------------------------------------------------
  75. // Information (count)
  76. uint32_t parameterScalePointCount(const uint32_t parameterId) const
  77. {
  78. CARLA_ASSERT(parameterId < kData->param.count);
  79. switch (parameterId)
  80. {
  81. case FluidSynthChorusType:
  82. return 2;
  83. case FluidSynthInterpolation:
  84. return 4;
  85. default:
  86. return 0;
  87. }
  88. }
  89. // -------------------------------------------------------------------
  90. // Information (per-plugin data)
  91. unsigned int availableOptions()
  92. {
  93. unsigned int options = 0x0;
  94. options |= PLUGIN_OPTION_MAP_PROGRAM_CHANGES;
  95. options |= PLUGIN_OPTION_SEND_CONTROL_CHANGES;
  96. options |= PLUGIN_OPTION_SEND_CHANNEL_PRESSURE;
  97. options |= PLUGIN_OPTION_SEND_PITCHBEND;
  98. options |= PLUGIN_OPTION_SEND_ALL_SOUND_OFF;
  99. return options;
  100. }
  101. float getParameterValue(const uint32_t parameterId)
  102. {
  103. CARLA_ASSERT(parameterId < kData->param.count);
  104. return fParamBuffers[parameterId];
  105. }
  106. float getParameterScalePointValue(const uint32_t parameterId, const uint32_t scalePointId)
  107. {
  108. CARLA_ASSERT(parameterId < kData->param.count);
  109. CARLA_ASSERT(scalePointId < parameterScalePointCount(parameterId));
  110. switch (parameterId)
  111. {
  112. case FluidSynthChorusType:
  113. switch (scalePointId)
  114. {
  115. case 0:
  116. return FLUID_CHORUS_MOD_SINE;
  117. case 1:
  118. return FLUID_CHORUS_MOD_TRIANGLE;
  119. default:
  120. return FLUID_CHORUS_DEFAULT_TYPE;
  121. }
  122. case FluidSynthInterpolation:
  123. switch (scalePointId)
  124. {
  125. case 0:
  126. return FLUID_INTERP_NONE;
  127. case 1:
  128. return FLUID_INTERP_LINEAR;
  129. case 2:
  130. return FLUID_INTERP_4THORDER;
  131. case 3:
  132. return FLUID_INTERP_7THORDER;
  133. default:
  134. return FLUID_INTERP_DEFAULT;
  135. }
  136. default:
  137. return 0.0f;
  138. }
  139. }
  140. void getLabel(char* const strBuf)
  141. {
  142. if (fLabel.isNotEmpty())
  143. std::strncpy(strBuf, (const char*)fLabel, STR_MAX);
  144. else
  145. CarlaPlugin::getLabel(strBuf);
  146. }
  147. void getMaker(char* const strBuf)
  148. {
  149. std::strncpy(strBuf, "FluidSynth SF2 engine", STR_MAX);
  150. }
  151. void getCopyright(char* const strBuf)
  152. {
  153. std::strncpy(strBuf, "GNU GPL v2+", STR_MAX);
  154. }
  155. void getRealName(char* const strBuf)
  156. {
  157. getLabel(strBuf);
  158. }
  159. void getParameterName(const uint32_t parameterId, char* const strBuf)
  160. {
  161. CARLA_ASSERT(parameterId < kData->param.count);
  162. switch (parameterId)
  163. {
  164. case FluidSynthReverbOnOff:
  165. std::strncpy(strBuf, "Reverb On/Off", STR_MAX);
  166. break;
  167. case FluidSynthReverbRoomSize:
  168. std::strncpy(strBuf, "Reverb Room Size", STR_MAX);
  169. break;
  170. case FluidSynthReverbDamp:
  171. std::strncpy(strBuf, "Reverb Damp", STR_MAX);
  172. break;
  173. case FluidSynthReverbLevel:
  174. std::strncpy(strBuf, "Reverb Level", STR_MAX);
  175. break;
  176. case FluidSynthReverbWidth:
  177. std::strncpy(strBuf, "Reverb Width", STR_MAX);
  178. break;
  179. case FluidSynthChorusOnOff:
  180. std::strncpy(strBuf, "Chorus On/Off", STR_MAX);
  181. break;
  182. case FluidSynthChorusNr:
  183. std::strncpy(strBuf, "Chorus Voice Count", STR_MAX);
  184. break;
  185. case FluidSynthChorusLevel:
  186. std::strncpy(strBuf, "Chorus Level", STR_MAX);
  187. break;
  188. case FluidSynthChorusSpeedHz:
  189. std::strncpy(strBuf, "Chorus Speed", STR_MAX);
  190. break;
  191. case FluidSynthChorusDepthMs:
  192. std::strncpy(strBuf, "Chorus Depth", STR_MAX);
  193. break;
  194. case FluidSynthChorusType:
  195. std::strncpy(strBuf, "Chorus Type", STR_MAX);
  196. break;
  197. case FluidSynthPolyphony:
  198. std::strncpy(strBuf, "Polyphony", STR_MAX);
  199. break;
  200. case FluidSynthInterpolation:
  201. std::strncpy(strBuf, "Interpolation", STR_MAX);
  202. break;
  203. case FluidSynthVoiceCount:
  204. std::strncpy(strBuf, "Voice Count", STR_MAX);
  205. break;
  206. default:
  207. CarlaPlugin::getParameterName(parameterId, strBuf);
  208. break;
  209. }
  210. }
  211. void getParameterUnit(const uint32_t parameterId, char* const strBuf)
  212. {
  213. CARLA_ASSERT(parameterId < kData->param.count);
  214. switch (parameterId)
  215. {
  216. case FluidSynthChorusSpeedHz:
  217. std::strncpy(strBuf, "Hz", STR_MAX);
  218. break;
  219. case FluidSynthChorusDepthMs:
  220. std::strncpy(strBuf, "ms", STR_MAX);
  221. break;
  222. default:
  223. CarlaPlugin::getParameterUnit(parameterId, strBuf);
  224. break;
  225. }
  226. }
  227. void getParameterScalePointLabel(const uint32_t parameterId, const uint32_t scalePointId, char* const strBuf)
  228. {
  229. CARLA_ASSERT(parameterId < kData->param.count);
  230. CARLA_ASSERT(scalePointId < parameterScalePointCount(parameterId));
  231. switch (parameterId)
  232. {
  233. case FluidSynthChorusType:
  234. switch (scalePointId)
  235. {
  236. case 0:
  237. std::strncpy(strBuf, "Sine wave", STR_MAX);
  238. return;
  239. case 1:
  240. std::strncpy(strBuf, "Triangle wave", STR_MAX);
  241. return;
  242. }
  243. case FluidSynthInterpolation:
  244. switch (scalePointId)
  245. {
  246. case 0:
  247. std::strncpy(strBuf, "None", STR_MAX);
  248. return;
  249. case 1:
  250. std::strncpy(strBuf, "Straight-line", STR_MAX);
  251. return;
  252. case 2:
  253. std::strncpy(strBuf, "Fourth-order", STR_MAX);
  254. return;
  255. case 3:
  256. std::strncpy(strBuf, "Seventh-order", STR_MAX);
  257. return;
  258. }
  259. }
  260. CarlaPlugin::getParameterScalePointLabel(parameterId, scalePointId, strBuf);
  261. }
  262. // -------------------------------------------------------------------
  263. // Set data (plugin-specific stuff)
  264. void setParameterValue(const uint32_t parameterId, const float value, const bool sendGui, const bool sendOsc, const bool sendCallback)
  265. {
  266. CARLA_ASSERT(parameterId < kData->param.count);
  267. const float fixedValue = kData->param.fixValue(parameterId, value);
  268. fParamBuffers[parameterId] = fixedValue;
  269. {
  270. const ScopedProcessLocker spl(this, (sendGui || sendOsc || sendCallback));
  271. switch (parameterId)
  272. {
  273. case FluidSynthReverbOnOff:
  274. fluid_synth_set_reverb_on(fSynth, (fixedValue > 0.5f) ? 1 : 0);
  275. break;
  276. case FluidSynthReverbRoomSize:
  277. case FluidSynthReverbDamp:
  278. case FluidSynthReverbLevel:
  279. case FluidSynthReverbWidth:
  280. fluid_synth_set_reverb(fSynth, fParamBuffers[FluidSynthReverbRoomSize], fParamBuffers[FluidSynthReverbDamp], fParamBuffers[FluidSynthReverbWidth], fParamBuffers[FluidSynthReverbLevel]);
  281. break;
  282. case FluidSynthChorusOnOff:
  283. fluid_synth_set_chorus_on(fSynth, (value > 0.5f) ? 1 : 0);
  284. break;
  285. case FluidSynthChorusNr:
  286. case FluidSynthChorusLevel:
  287. case FluidSynthChorusSpeedHz:
  288. case FluidSynthChorusDepthMs:
  289. case FluidSynthChorusType:
  290. fluid_synth_set_chorus(fSynth, fParamBuffers[FluidSynthChorusNr], fParamBuffers[FluidSynthChorusLevel], fParamBuffers[FluidSynthChorusSpeedHz], fParamBuffers[FluidSynthChorusDepthMs], fParamBuffers[FluidSynthChorusType]);
  291. break;
  292. case FluidSynthPolyphony:
  293. fluid_synth_set_polyphony(fSynth, value);
  294. break;
  295. case FluidSynthInterpolation:
  296. for (int i=0; i < 16; i++)
  297. fluid_synth_set_interp_method(fSynth, i, value);
  298. break;
  299. default:
  300. break;
  301. }
  302. }
  303. CarlaPlugin::setParameterValue(parameterId, value, sendGui, sendOsc, sendCallback);
  304. }
  305. void setMidiProgram(int32_t index, const bool sendGui, const bool sendOsc, const bool sendCallback)
  306. {
  307. CARLA_ASSERT(fSynth != nullptr);
  308. CARLA_ASSERT(index >= -1 && index < static_cast<int32_t>(kData->midiprog.count));
  309. if (index < -1)
  310. index = -1;
  311. else if (index > static_cast<int32_t>(kData->midiprog.count))
  312. return;
  313. if (kData->ctrlChannel < 0 || kData->ctrlChannel >= 16)
  314. return;
  315. if (index >= 0)
  316. {
  317. const uint32_t bank = kData->midiprog.data[index].bank;
  318. const uint32_t program = kData->midiprog.data[index].program;
  319. const ScopedProcessLocker spl(this, (sendGui || sendOsc || sendCallback));
  320. fluid_synth_program_select(fSynth, kData->ctrlChannel, fSynthId, bank, program);
  321. }
  322. CarlaPlugin::setMidiProgram(index, sendGui, sendOsc, sendCallback);
  323. }
  324. // -------------------------------------------------------------------
  325. // Plugin state
  326. void reload()
  327. {
  328. carla_debug("FluidSynthPlugin::reload() - start");
  329. CARLA_ASSERT(kData->engine != nullptr);
  330. CARLA_ASSERT(fSynth != nullptr);
  331. const ProcessMode processMode(kData->engine->getProccessMode());
  332. // Safely disable plugin for reload
  333. const ScopedDisabler sd(this);
  334. deleteBuffers();
  335. uint32_t aOuts, params, j;
  336. aOuts = kUses16Outs ? 32 : 2;
  337. params = FluidSynthParametersMax;
  338. kData->audioOut.createNew(aOuts);
  339. kData->param.createNew(params);
  340. const int portNameSize = kData->engine->maxPortNameSize();
  341. CarlaString portName;
  342. // ---------------------------------------
  343. // Audio Outputs
  344. if (kUses16Outs)
  345. {
  346. for (j=0; j < 32; j++)
  347. {
  348. portName.clear();
  349. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  350. {
  351. portName = fName;
  352. portName += ":";
  353. }
  354. portName += "out-";
  355. if ((j+2)/2 < 9)
  356. portName += "0";
  357. portName += CarlaString((j+2)/2);
  358. if (j % 2 == 0)
  359. portName += "L";
  360. else
  361. portName += "R";
  362. portName.truncate(portNameSize);
  363. kData->audioOut.ports[j].port = (CarlaEngineAudioPort*)kData->client->addPort(kEnginePortTypeAudio, portName, false);
  364. kData->audioOut.ports[j].rindex = j;
  365. }
  366. fAudio16Buffers = new float*[aOuts];
  367. for (j=0; j < aOuts; j++)
  368. fAudio16Buffers[j] = nullptr;
  369. }
  370. else
  371. {
  372. // out-left
  373. portName.clear();
  374. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  375. {
  376. portName = fName;
  377. portName += ":";
  378. }
  379. portName += "out-left";
  380. portName.truncate(portNameSize);
  381. kData->audioOut.ports[0].port = (CarlaEngineAudioPort*)kData->client->addPort(kEnginePortTypeAudio, portName, false);
  382. kData->audioOut.ports[0].rindex = 0;
  383. // out-right
  384. portName.clear();
  385. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  386. {
  387. portName = fName;
  388. portName += ":";
  389. }
  390. portName += "out-right";
  391. portName.truncate(portNameSize);
  392. kData->audioOut.ports[1].port = (CarlaEngineAudioPort*)kData->client->addPort(kEnginePortTypeAudio, portName, false);
  393. kData->audioOut.ports[1].rindex = 1;
  394. }
  395. // ---------------------------------------
  396. // Event Input
  397. {
  398. portName.clear();
  399. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  400. {
  401. portName = fName;
  402. portName += ":";
  403. }
  404. portName += "event-in";
  405. portName.truncate(portNameSize);
  406. kData->event.portIn = (CarlaEngineEventPort*)kData->client->addPort(kEnginePortTypeEvent, portName, true);
  407. }
  408. // ---------------------------------------
  409. // Event Output
  410. {
  411. portName.clear();
  412. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  413. {
  414. portName = fName;
  415. portName += ":";
  416. }
  417. portName += "event-out";
  418. portName.truncate(portNameSize);
  419. kData->event.portOut = (CarlaEngineEventPort*)kData->client->addPort(kEnginePortTypeEvent, portName, false);
  420. }
  421. // ----------------------
  422. j = FluidSynthReverbOnOff;
  423. kData->param.data[j].index = j;
  424. kData->param.data[j].rindex = j;
  425. kData->param.data[j].type = PARAMETER_INPUT;
  426. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_AUTOMABLE | PARAMETER_IS_BOOLEAN;
  427. kData->param.data[j].midiChannel = 0;
  428. kData->param.data[j].midiCC = -1;
  429. kData->param.ranges[j].min = 0.0f;
  430. kData->param.ranges[j].max = 1.0f;
  431. kData->param.ranges[j].def = 0.0f; // off
  432. kData->param.ranges[j].step = 1.0f;
  433. kData->param.ranges[j].stepSmall = 1.0f;
  434. kData->param.ranges[j].stepLarge = 1.0f;
  435. fParamBuffers[j] = kData->param.ranges[j].def;
  436. // ----------------------
  437. j = FluidSynthReverbRoomSize;
  438. kData->param.data[j].index = j;
  439. kData->param.data[j].rindex = j;
  440. kData->param.data[j].type = PARAMETER_INPUT;
  441. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_AUTOMABLE;
  442. kData->param.data[j].midiChannel = 0;
  443. kData->param.data[j].midiCC = -1;
  444. kData->param.ranges[j].min = 0.0f;
  445. kData->param.ranges[j].max = 1.2f;
  446. kData->param.ranges[j].def = FLUID_REVERB_DEFAULT_ROOMSIZE;
  447. kData->param.ranges[j].step = 0.01f;
  448. kData->param.ranges[j].stepSmall = 0.0001f;
  449. kData->param.ranges[j].stepLarge = 0.1f;
  450. fParamBuffers[j] = kData->param.ranges[j].def;
  451. // ----------------------
  452. j = FluidSynthReverbDamp;
  453. kData->param.data[j].index = j;
  454. kData->param.data[j].rindex = j;
  455. kData->param.data[j].type = PARAMETER_INPUT;
  456. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_AUTOMABLE;
  457. kData->param.data[j].midiChannel = 0;
  458. kData->param.data[j].midiCC = -1;
  459. kData->param.ranges[j].min = 0.0f;
  460. kData->param.ranges[j].max = 1.0f;
  461. kData->param.ranges[j].def = FLUID_REVERB_DEFAULT_DAMP;
  462. kData->param.ranges[j].step = 0.01f;
  463. kData->param.ranges[j].stepSmall = 0.0001f;
  464. kData->param.ranges[j].stepLarge = 0.1f;
  465. fParamBuffers[j] = kData->param.ranges[j].def;
  466. // ----------------------
  467. j = FluidSynthReverbLevel;
  468. kData->param.data[j].index = j;
  469. kData->param.data[j].rindex = j;
  470. kData->param.data[j].type = PARAMETER_INPUT;
  471. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_AUTOMABLE;
  472. kData->param.data[j].midiChannel = 0;
  473. kData->param.data[j].midiCC = MIDI_CONTROL_REVERB_SEND_LEVEL;
  474. kData->param.ranges[j].min = 0.0f;
  475. kData->param.ranges[j].max = 1.0f;
  476. kData->param.ranges[j].def = FLUID_REVERB_DEFAULT_LEVEL;
  477. kData->param.ranges[j].step = 0.01f;
  478. kData->param.ranges[j].stepSmall = 0.0001f;
  479. kData->param.ranges[j].stepLarge = 0.1f;
  480. fParamBuffers[j] = kData->param.ranges[j].def;
  481. // ----------------------
  482. j = FluidSynthReverbWidth;
  483. kData->param.data[j].index = j;
  484. kData->param.data[j].rindex = j;
  485. kData->param.data[j].type = PARAMETER_INPUT;
  486. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_AUTOMABLE;
  487. kData->param.data[j].midiChannel = 0;
  488. kData->param.data[j].midiCC = -1;
  489. kData->param.ranges[j].min = 0.0f;
  490. kData->param.ranges[j].max = 10.0f; // should be 100, but that sounds too much
  491. kData->param.ranges[j].def = FLUID_REVERB_DEFAULT_WIDTH;
  492. kData->param.ranges[j].step = 0.01f;
  493. kData->param.ranges[j].stepSmall = 0.0001f;
  494. kData->param.ranges[j].stepLarge = 0.1f;
  495. fParamBuffers[j] = kData->param.ranges[j].def;
  496. // ----------------------
  497. j = FluidSynthChorusOnOff;
  498. kData->param.data[j].index = j;
  499. kData->param.data[j].rindex = j;
  500. kData->param.data[j].type = PARAMETER_INPUT;
  501. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_BOOLEAN;
  502. kData->param.data[j].midiChannel = 0;
  503. kData->param.data[j].midiCC = -1;
  504. kData->param.ranges[j].min = 0.0f;
  505. kData->param.ranges[j].max = 1.0f;
  506. kData->param.ranges[j].def = 0.0f; // off
  507. kData->param.ranges[j].step = 1.0f;
  508. kData->param.ranges[j].stepSmall = 1.0f;
  509. kData->param.ranges[j].stepLarge = 1.0f;
  510. fParamBuffers[j] = kData->param.ranges[j].def;
  511. // ----------------------
  512. j = FluidSynthChorusNr;
  513. kData->param.data[j].index = j;
  514. kData->param.data[j].rindex = j;
  515. kData->param.data[j].type = PARAMETER_INPUT;
  516. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_INTEGER;
  517. kData->param.data[j].midiChannel = 0;
  518. kData->param.data[j].midiCC = -1;
  519. kData->param.ranges[j].min = 0.0f;
  520. kData->param.ranges[j].max = 99.0f;
  521. kData->param.ranges[j].def = FLUID_CHORUS_DEFAULT_N;
  522. kData->param.ranges[j].step = 1.0f;
  523. kData->param.ranges[j].stepSmall = 1.0f;
  524. kData->param.ranges[j].stepLarge = 10.0f;
  525. fParamBuffers[j] = kData->param.ranges[j].def;
  526. // ----------------------
  527. j = FluidSynthChorusLevel;
  528. kData->param.data[j].index = j;
  529. kData->param.data[j].rindex = j;
  530. kData->param.data[j].type = PARAMETER_INPUT;
  531. kData->param.data[j].hints = PARAMETER_IS_ENABLED;
  532. kData->param.data[j].midiChannel = 0;
  533. kData->param.data[j].midiCC = 0; //MIDI_CONTROL_CHORUS_SEND_LEVEL;
  534. kData->param.ranges[j].min = 0.0f;
  535. kData->param.ranges[j].max = 10.0f;
  536. kData->param.ranges[j].def = FLUID_CHORUS_DEFAULT_LEVEL;
  537. kData->param.ranges[j].step = 0.01f;
  538. kData->param.ranges[j].stepSmall = 0.0001f;
  539. kData->param.ranges[j].stepLarge = 0.1f;
  540. fParamBuffers[j] = kData->param.ranges[j].def;
  541. // ----------------------
  542. j = FluidSynthChorusSpeedHz;
  543. kData->param.data[j].index = j;
  544. kData->param.data[j].rindex = j;
  545. kData->param.data[j].type = PARAMETER_INPUT;
  546. kData->param.data[j].hints = PARAMETER_IS_ENABLED;
  547. kData->param.data[j].midiChannel = 0;
  548. kData->param.data[j].midiCC = -1;
  549. kData->param.ranges[j].min = 0.29f;
  550. kData->param.ranges[j].max = 5.0f;
  551. kData->param.ranges[j].def = FLUID_CHORUS_DEFAULT_SPEED;
  552. kData->param.ranges[j].step = 0.01f;
  553. kData->param.ranges[j].stepSmall = 0.0001f;
  554. kData->param.ranges[j].stepLarge = 0.1f;
  555. fParamBuffers[j] = kData->param.ranges[j].def;
  556. // ----------------------
  557. j = FluidSynthChorusDepthMs;
  558. kData->param.data[j].index = j;
  559. kData->param.data[j].rindex = j;
  560. kData->param.data[j].type = PARAMETER_INPUT;
  561. kData->param.data[j].hints = PARAMETER_IS_ENABLED;
  562. kData->param.data[j].midiChannel = 0;
  563. kData->param.data[j].midiCC = -1;
  564. kData->param.ranges[j].min = 0.0f;
  565. kData->param.ranges[j].max = 2048000.0 / kData->engine->getSampleRate();
  566. kData->param.ranges[j].def = FLUID_CHORUS_DEFAULT_DEPTH;
  567. kData->param.ranges[j].step = 0.01f;
  568. kData->param.ranges[j].stepSmall = 0.0001f;
  569. kData->param.ranges[j].stepLarge = 0.1f;
  570. fParamBuffers[j] = kData->param.ranges[j].def;
  571. // ----------------------
  572. j = FluidSynthChorusType;
  573. kData->param.data[j].index = j;
  574. kData->param.data[j].rindex = j;
  575. kData->param.data[j].type = PARAMETER_INPUT;
  576. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_INTEGER | PARAMETER_USES_SCALEPOINTS;
  577. kData->param.data[j].midiChannel = 0;
  578. kData->param.data[j].midiCC = -1;
  579. kData->param.ranges[j].min = FLUID_CHORUS_MOD_SINE;
  580. kData->param.ranges[j].max = FLUID_CHORUS_MOD_TRIANGLE;
  581. kData->param.ranges[j].def = FLUID_CHORUS_DEFAULT_TYPE;
  582. kData->param.ranges[j].step = 1.0f;
  583. kData->param.ranges[j].stepSmall = 1.0f;
  584. kData->param.ranges[j].stepLarge = 1.0f;
  585. fParamBuffers[j] = kData->param.ranges[j].def;
  586. // ----------------------
  587. j = FluidSynthPolyphony;
  588. kData->param.data[j].index = j;
  589. kData->param.data[j].rindex = j;
  590. kData->param.data[j].type = PARAMETER_INPUT;
  591. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_INTEGER;
  592. kData->param.data[j].midiChannel = 0;
  593. kData->param.data[j].midiCC = -1;
  594. kData->param.ranges[j].min = 1.0f;
  595. kData->param.ranges[j].max = 512.0f; // max theoric is 65535
  596. kData->param.ranges[j].def = fluid_synth_get_polyphony(fSynth);
  597. kData->param.ranges[j].step = 1.0f;
  598. kData->param.ranges[j].stepSmall = 1.0f;
  599. kData->param.ranges[j].stepLarge = 10.0f;
  600. fParamBuffers[j] = kData->param.ranges[j].def;
  601. // ----------------------
  602. j = FluidSynthInterpolation;
  603. kData->param.data[j].index = j;
  604. kData->param.data[j].rindex = j;
  605. kData->param.data[j].type = PARAMETER_INPUT;
  606. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_INTEGER | PARAMETER_USES_SCALEPOINTS;
  607. kData->param.data[j].midiChannel = 0;
  608. kData->param.data[j].midiCC = -1;
  609. kData->param.ranges[j].min = FLUID_INTERP_NONE;
  610. kData->param.ranges[j].max = FLUID_INTERP_HIGHEST;
  611. kData->param.ranges[j].def = FLUID_INTERP_DEFAULT;
  612. kData->param.ranges[j].step = 1.0f;
  613. kData->param.ranges[j].stepSmall = 1.0f;
  614. kData->param.ranges[j].stepLarge = 1.0f;
  615. fParamBuffers[j] = kData->param.ranges[j].def;
  616. // ----------------------
  617. j = FluidSynthVoiceCount;
  618. kData->param.data[j].index = j;
  619. kData->param.data[j].rindex = j;
  620. kData->param.data[j].type = PARAMETER_OUTPUT;
  621. kData->param.data[j].hints = PARAMETER_IS_ENABLED | PARAMETER_IS_AUTOMABLE | PARAMETER_IS_INTEGER;
  622. kData->param.data[j].midiChannel = 0;
  623. kData->param.data[j].midiCC = -1;
  624. kData->param.ranges[j].min = 0.0f;
  625. kData->param.ranges[j].max = 65535.0f;
  626. kData->param.ranges[j].def = 0.0f;
  627. kData->param.ranges[j].step = 1.0f;
  628. kData->param.ranges[j].stepSmall = 1.0f;
  629. kData->param.ranges[j].stepLarge = 1.0f;
  630. fParamBuffers[j] = kData->param.ranges[j].def;
  631. // ---------------------------------------
  632. // plugin hints
  633. fHints = 0x0;
  634. fHints |= PLUGIN_IS_RTSAFE;
  635. fHints |= PLUGIN_IS_SYNTH;
  636. fHints |= PLUGIN_CAN_VOLUME;
  637. fHints |= PLUGIN_CAN_BALANCE;
  638. // extra plugin hints
  639. kData->extraHints = 0x0;
  640. kData->extraHints |= PLUGIN_HINT_CAN_RUN_RACK;
  641. // plugin options
  642. fOptions = 0x0;
  643. fOptions |= PLUGIN_OPTION_MAP_PROGRAM_CHANGES;
  644. fOptions |= PLUGIN_OPTION_SEND_CONTROL_CHANGES;
  645. fOptions |= PLUGIN_OPTION_SEND_CHANNEL_PRESSURE;
  646. fOptions |= PLUGIN_OPTION_SEND_PITCHBEND;
  647. fOptions |= PLUGIN_OPTION_SEND_ALL_SOUND_OFF;
  648. bufferSizeChanged(kData->engine->getBufferSize());
  649. reloadPrograms(true);
  650. carla_debug("FluidSynthPlugin::reload() - end");
  651. }
  652. void reloadPrograms(const bool init)
  653. {
  654. carla_debug("FluidSynthPlugin::reloadPrograms(%s)", bool2str(init));
  655. // Delete old programs
  656. kData->midiprog.clear();
  657. // Query new programs
  658. uint32_t count = 0;
  659. fluid_sfont_t* f_sfont;
  660. fluid_preset_t f_preset;
  661. bool hasDrums = false;
  662. f_sfont = fluid_synth_get_sfont_by_id(fSynth, fSynthId);
  663. // initial check to know how much midi-programs we have
  664. f_sfont->iteration_start(f_sfont);
  665. while (f_sfont->iteration_next(f_sfont, &f_preset))
  666. count += 1;
  667. // soundfonts must always have at least 1 midi-program
  668. CARLA_ASSERT(count > 0);
  669. if (count == 0)
  670. return;
  671. kData->midiprog.createNew(count);
  672. // Update data
  673. uint32_t i = 0;
  674. f_sfont->iteration_start(f_sfont);
  675. while (f_sfont->iteration_next(f_sfont, &f_preset))
  676. {
  677. CARLA_ASSERT(i < kData->midiprog.count);
  678. kData->midiprog.data[i].bank = f_preset.get_banknum(&f_preset);
  679. kData->midiprog.data[i].program = f_preset.get_num(&f_preset);
  680. kData->midiprog.data[i].name = carla_strdup(f_preset.get_name(&f_preset));
  681. if (kData->midiprog.data[i].bank == 128)
  682. hasDrums = true;
  683. i++;
  684. }
  685. //f_sfont->free(f_sfont);
  686. #ifndef BUILD_BRIDGE
  687. // Update OSC Names
  688. if (kData->engine->isOscControlRegistered())
  689. {
  690. kData->engine->osc_send_control_set_midi_program_count(fId, count);
  691. for (i=0; i < count; i++)
  692. kData->engine->osc_send_control_set_midi_program_data(fId, i, kData->midiprog.data[i].bank, kData->midiprog.data[i].program, kData->midiprog.data[i].name);
  693. }
  694. #endif
  695. if (init)
  696. {
  697. fluid_synth_program_reset(fSynth);
  698. // select first program, or 128 for ch10
  699. for (i=0; i < 16 && i != 9; i++)
  700. {
  701. fluid_synth_program_select(fSynth, i, fSynthId, kData->midiprog.data[0].bank, kData->midiprog.data[0].program);
  702. #ifdef FLUIDSYNTH_VERSION_NEW_API
  703. fluid_synth_set_channel_type(fSynth, i, CHANNEL_TYPE_MELODIC);
  704. #endif
  705. }
  706. if (hasDrums)
  707. {
  708. fluid_synth_program_select(fSynth, 9, fSynthId, 128, 0);
  709. #ifdef FLUIDSYNTH_VERSION_NEW_API
  710. fluid_synth_set_channel_type(fSynth, 9, CHANNEL_TYPE_DRUM);
  711. #endif
  712. }
  713. else
  714. {
  715. fluid_synth_program_select(fSynth, 9, fSynthId, kData->midiprog.data[0].bank, kData->midiprog.data[0].program);
  716. #ifdef FLUIDSYNTH_VERSION_NEW_API
  717. fluid_synth_set_channel_type(fSynth, 9, CHANNEL_TYPE_MELODIC);
  718. #endif
  719. }
  720. setMidiProgram(0, false, false, false);
  721. }
  722. else
  723. {
  724. kData->engine->callback(CALLBACK_RELOAD_PROGRAMS, fId, 0, 0, 0.0f, nullptr);
  725. }
  726. }
  727. // -------------------------------------------------------------------
  728. // Plugin processing
  729. void process(float** const, float** const outBuffer, const uint32_t frames)
  730. {
  731. uint32_t i, k;
  732. // --------------------------------------------------------------------------------------------------------
  733. // Check if active
  734. if (! kData->active)
  735. {
  736. // disable any output sound
  737. for (i=0; i < kData->audioOut.count; i++)
  738. carla_zeroFloat(outBuffer[i], frames);
  739. kData->activeBefore = kData->active;
  740. return;
  741. }
  742. // --------------------------------------------------------------------------------------------------------
  743. // Check if not active before
  744. if (kData->needsReset || ! kData->activeBefore)
  745. {
  746. if (fOptions & PLUGIN_OPTION_SEND_ALL_SOUND_OFF)
  747. {
  748. for (int c=0; c < MAX_MIDI_CHANNELS; c++)
  749. {
  750. #ifdef FLUIDSYNTH_VERSION_NEW_API
  751. fluid_synth_all_notes_off(fSynth, c);
  752. fluid_synth_all_sounds_off(fSynth, c);
  753. #else
  754. fluid_synth_cc(f_synth, c, MIDI_CONTROL_ALL_SOUND_OFF, 0);
  755. fluid_synth_cc(f_synth, c, MIDI_CONTROL_ALL_NOTES_OFF, 0);
  756. #endif
  757. }
  758. }
  759. kData->needsReset = false;
  760. }
  761. // --------------------------------------------------------------------------------------------------------
  762. // Event Input and Processing
  763. if (kData->activeBefore)
  764. {
  765. // ----------------------------------------------------------------------------------------------------
  766. // MIDI Input (External)
  767. if (kData->extNotes.mutex.tryLock())
  768. {
  769. while (! kData->extNotes.data.isEmpty())
  770. {
  771. const ExternalMidiNote& note = kData->extNotes.data.getFirst(true);
  772. CARLA_ASSERT(note.channel >= 0);
  773. if (note.velo > 0)
  774. fluid_synth_noteon(fSynth, note.channel, note.note, note.velo);
  775. else
  776. fluid_synth_noteoff(fSynth,note.channel, note.note);
  777. }
  778. kData->extNotes.mutex.unlock();
  779. } // End of MIDI Input (External)
  780. // ----------------------------------------------------------------------------------------------------
  781. // Event Input (System)
  782. bool allNotesOffSent = false;
  783. uint32_t time, nEvents = kData->event.portIn->getEventCount();
  784. uint32_t timeOffset = 0;
  785. uint32_t nextBankIds[16] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 0, 0, 0, 0, 0, 0 };
  786. if (kData->midiprog.current >= 0 && kData->midiprog.count > 0 && kData->ctrlChannel >= 0 && kData->ctrlChannel < 16)
  787. nextBankIds[kData->ctrlChannel] = kData->midiprog.data[kData->midiprog.current].bank;
  788. for (i=0; i < nEvents; i++)
  789. {
  790. const EngineEvent& event = kData->event.portIn->getEvent(i);
  791. time = event.time;
  792. if (time >= frames)
  793. continue;
  794. CARLA_ASSERT_INT2(time >= timeOffset, time, timeOffset);
  795. if (time > timeOffset)
  796. {
  797. if (processSingle(outBuffer, time - timeOffset, timeOffset))
  798. {
  799. timeOffset = time;
  800. if (kData->midiprog.current >= 0 && kData->midiprog.count > 0 && kData->ctrlChannel >= 0 && kData->ctrlChannel < 16)
  801. nextBankIds[kData->ctrlChannel] = kData->midiprog.data[kData->midiprog.current].bank;
  802. }
  803. }
  804. // Control change
  805. switch (event.type)
  806. {
  807. case kEngineEventTypeNull:
  808. break;
  809. case kEngineEventTypeControl:
  810. {
  811. const EngineControlEvent& ctrlEvent = event.ctrl;
  812. switch (ctrlEvent.type)
  813. {
  814. case kEngineControlEventTypeNull:
  815. break;
  816. case kEngineControlEventTypeParameter:
  817. {
  818. // Control backend stuff
  819. if (event.channel == kData->ctrlChannel)
  820. {
  821. float value;
  822. if (MIDI_IS_CONTROL_BREATH_CONTROLLER(ctrlEvent.param) && (fHints & PLUGIN_CAN_DRYWET) > 0)
  823. {
  824. value = ctrlEvent.value;
  825. setDryWet(value, false, false);
  826. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_DRYWET, 0, value);
  827. continue;
  828. }
  829. if (MIDI_IS_CONTROL_CHANNEL_VOLUME(ctrlEvent.param) && (fHints & PLUGIN_CAN_VOLUME) > 0)
  830. {
  831. value = ctrlEvent.value*127.0f/100.0f;
  832. setVolume(value, false, false);
  833. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_VOLUME, 0, value);
  834. continue;
  835. }
  836. if (MIDI_IS_CONTROL_BALANCE(ctrlEvent.param) && (fHints & PLUGIN_CAN_BALANCE) > 0)
  837. {
  838. float left, right;
  839. value = ctrlEvent.value/0.5f - 1.0f;
  840. if (value < 0.0f)
  841. {
  842. left = -1.0f;
  843. right = (value*2.0f)+1.0f;
  844. }
  845. else if (value > 0.0f)
  846. {
  847. left = (value*2.0f)-1.0f;
  848. right = 1.0f;
  849. }
  850. else
  851. {
  852. left = -1.0f;
  853. right = 1.0f;
  854. }
  855. setBalanceLeft(left, false, false);
  856. setBalanceRight(right, false, false);
  857. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_BALANCE_LEFT, 0, left);
  858. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_BALANCE_RIGHT, 0, right);
  859. continue;
  860. }
  861. }
  862. // Control plugin parameters
  863. for (k=0; k < kData->param.count; k++)
  864. {
  865. if (kData->param.data[k].midiChannel != event.channel)
  866. continue;
  867. if (kData->param.data[k].midiCC != ctrlEvent.param)
  868. continue;
  869. if (kData->param.data[k].type != PARAMETER_INPUT)
  870. continue;
  871. if ((kData->param.data[k].hints & PARAMETER_IS_AUTOMABLE) == 0)
  872. continue;
  873. float value;
  874. if (kData->param.data[k].hints & PARAMETER_IS_BOOLEAN)
  875. {
  876. value = (ctrlEvent.value < 0.5f) ? kData->param.ranges[k].min : kData->param.ranges[k].max;
  877. }
  878. else
  879. {
  880. value = kData->param.ranges[i].unnormalizeValue(ctrlEvent.value);
  881. if (kData->param.data[k].hints & PARAMETER_IS_INTEGER)
  882. value = std::rint(value);
  883. }
  884. setParameterValue(k, value, false, false, false);
  885. postponeRtEvent(kPluginPostRtEventParameterChange, static_cast<int32_t>(k), 0, value);
  886. }
  887. break;
  888. }
  889. case kEngineControlEventTypeMidiBank:
  890. if (event.channel < 16)
  891. nextBankIds[event.channel] = ctrlEvent.param;
  892. break;
  893. case kEngineControlEventTypeMidiProgram:
  894. if (event.channel < 16)
  895. {
  896. const uint32_t bankId = nextBankIds[event.channel];
  897. const uint32_t progId = ctrlEvent.param;
  898. for (k=0; k < kData->midiprog.count; k++)
  899. {
  900. if (kData->midiprog.data[k].bank == bankId && kData->midiprog.data[k].program == progId)
  901. {
  902. if (event.channel == kData->ctrlChannel)
  903. {
  904. setMidiProgram(k, false, false, false);
  905. postponeRtEvent(kPluginPostRtEventMidiProgramChange, k, 0, 0.0f);
  906. }
  907. else
  908. fluid_synth_program_select(fSynth, event.channel, fSynthId, bankId, progId);
  909. break;
  910. }
  911. }
  912. }
  913. break;
  914. case kEngineControlEventTypeAllSoundOff:
  915. if (event.channel == kData->ctrlChannel)
  916. {
  917. if (! allNotesOffSent)
  918. {
  919. allNotesOffSent = true;
  920. sendMidiAllNotesOff();
  921. }
  922. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_ACTIVE, 0, 0.0f);
  923. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_ACTIVE, 0, 1.0f);
  924. if (fOptions & PLUGIN_OPTION_SEND_ALL_SOUND_OFF)
  925. {
  926. #ifdef FLUIDSYNTH_VERSION_NEW_API
  927. fluid_synth_all_sounds_off(fSynth, event.channel);
  928. #else
  929. fluid_synth_cc(f_synth, event.channel, MIDI_CONTROL_ALL_SOUND_OFF, 0);
  930. #endif
  931. }
  932. }
  933. break;
  934. case kEngineControlEventTypeAllNotesOff:
  935. if (event.channel == kData->ctrlChannel)
  936. {
  937. if (! allNotesOffSent)
  938. {
  939. allNotesOffSent = true;
  940. sendMidiAllNotesOff();
  941. }
  942. if (fOptions & PLUGIN_OPTION_SEND_ALL_SOUND_OFF)
  943. {
  944. #ifdef FLUIDSYNTH_VERSION_NEW_API
  945. fluid_synth_all_notes_off(fSynth, event.channel);
  946. #else
  947. fluid_synth_cc(f_synth, event.channel, MIDI_CONTROL_ALL_NOTES_OFF, 0);
  948. #endif
  949. }
  950. }
  951. break;
  952. }
  953. break;
  954. }
  955. case kEngineEventTypeMidi:
  956. {
  957. const EngineMidiEvent& midiEvent = event.midi;
  958. uint8_t status = MIDI_GET_STATUS_FROM_DATA(midiEvent.data);
  959. uint8_t channel = event.channel;
  960. // Fix bad note-off
  961. if (MIDI_IS_STATUS_NOTE_ON(status) && midiEvent.data[2] == 0)
  962. status -= 0x10;
  963. if (MIDI_IS_STATUS_NOTE_OFF(status))
  964. {
  965. const uint8_t note = midiEvent.data[1];
  966. fluid_synth_noteoff(fSynth, channel, note);
  967. postponeRtEvent(kPluginPostRtEventNoteOff, channel, note, 0.0f);
  968. }
  969. else if (MIDI_IS_STATUS_NOTE_ON(status))
  970. {
  971. const uint8_t note = midiEvent.data[1];
  972. const uint8_t velo = midiEvent.data[2];
  973. fluid_synth_noteon(fSynth, channel, note, velo);
  974. postponeRtEvent(kPluginPostRtEventNoteOn, channel, note, velo);
  975. }
  976. else if (MIDI_IS_STATUS_POLYPHONIC_AFTERTOUCH(status) && (fOptions & PLUGIN_OPTION_SEND_NOTE_AFTERTOUCH) != 0)
  977. {
  978. //const uint8_t note = midiEvent.data[1];
  979. //const uint8_t pressure = midiEvent.data[2];
  980. // TODO, not in fluidsynth API
  981. }
  982. else if (MIDI_IS_STATUS_CONTROL_CHANGE(status) && (fOptions & PLUGIN_OPTION_SEND_CONTROL_CHANGES) != 0)
  983. {
  984. const uint8_t control = midiEvent.data[1];
  985. const uint8_t value = midiEvent.data[2];
  986. fluid_synth_cc(fSynth, channel, control, value);
  987. }
  988. else if (MIDI_IS_STATUS_AFTERTOUCH(status) && (fOptions & PLUGIN_OPTION_SEND_CHANNEL_PRESSURE) != 0)
  989. {
  990. const uint8_t pressure = midiEvent.data[1];
  991. fluid_synth_channel_pressure(fSynth, channel, pressure);;
  992. }
  993. else if (MIDI_IS_STATUS_PITCH_WHEEL_CONTROL(status) && (fOptions & PLUGIN_OPTION_SEND_PITCHBEND) != 0)
  994. {
  995. const uint8_t lsb = midiEvent.data[1];
  996. const uint8_t msb = midiEvent.data[2];
  997. fluid_synth_pitch_bend(fSynth, channel, (msb << 7) | lsb);
  998. }
  999. break;
  1000. }
  1001. }
  1002. }
  1003. kData->postRtEvents.trySplice();
  1004. if (frames > timeOffset)
  1005. processSingle(outBuffer, frames - timeOffset, timeOffset);
  1006. } // End of Event Input and Processing
  1007. CARLA_PROCESS_CONTINUE_CHECK;
  1008. // --------------------------------------------------------------------------------------------------------
  1009. // Control Output
  1010. {
  1011. k = FluidSynthVoiceCount;
  1012. fParamBuffers[k] = fluid_synth_get_active_voice_count(fSynth);
  1013. kData->param.ranges[k].fixValue(fParamBuffers[k]);
  1014. if (kData->param.data[k].midiCC > 0)
  1015. {
  1016. double value = kData->param.ranges[k].normalizeValue(fParamBuffers[k]);
  1017. kData->event.portOut->writeControlEvent(0, kData->param.data[k].midiChannel, kEngineControlEventTypeParameter, kData->param.data[k].midiCC, value);
  1018. }
  1019. } // End of Control Output
  1020. // --------------------------------------------------------------------------------------------------------
  1021. kData->activeBefore = kData->active;
  1022. }
  1023. bool processSingle(float** const outBuffer, const uint32_t frames, const uint32_t timeOffset)
  1024. {
  1025. uint32_t i, k;
  1026. // --------------------------------------------------------------------------------------------------------
  1027. // Try lock, silence otherwise
  1028. if (kData->engine->isOffline())
  1029. {
  1030. kData->singleMutex.lock();
  1031. }
  1032. else if (! kData->singleMutex.tryLock())
  1033. {
  1034. for (i=0; i < kData->audioOut.count; i++)
  1035. {
  1036. for (k=0; k < frames; k++)
  1037. outBuffer[i][k+timeOffset] = 0.0f;
  1038. }
  1039. return false;
  1040. }
  1041. // --------------------------------------------------------------------------------------------------------
  1042. // Fill plugin buffers and Run plugin
  1043. if (kUses16Outs)
  1044. {
  1045. for (i=0; i < kData->audioOut.count; i++)
  1046. carla_zeroFloat(fAudio16Buffers[i], frames);
  1047. fluid_synth_process(fSynth, frames, 0, nullptr, kData->audioOut.count, fAudio16Buffers);
  1048. }
  1049. else
  1050. fluid_synth_write_float(fSynth, frames, outBuffer[0] + timeOffset, 0, 1, outBuffer[1] + timeOffset, 0, 1);
  1051. // --------------------------------------------------------------------------------------------------------
  1052. // Post-processing (volume and balance)
  1053. {
  1054. // note - balance not possible with kUses16Outs, so we can safely skip fAudioOutBuffers
  1055. const bool doVolume = (fHints & PLUGIN_CAN_VOLUME) > 0 && kData->postProc.volume != 1.0f;
  1056. const bool doBalance = (fHints & PLUGIN_CAN_BALANCE) > 0 && (kData->postProc.balanceLeft != -1.0f || kData->postProc.balanceRight != 1.0f);
  1057. float oldBufLeft[doBalance ? frames : 1];
  1058. for (i=0; i < kData->audioOut.count; i++)
  1059. {
  1060. // Balance
  1061. if (doBalance)
  1062. {
  1063. if (i % 2 == 0)
  1064. carla_copyFloat(oldBufLeft, outBuffer[i]+timeOffset, frames);
  1065. float balRangeL = (kData->postProc.balanceLeft + 1.0f)/2.0f;
  1066. float balRangeR = (kData->postProc.balanceRight + 1.0f)/2.0f;
  1067. for (k=0; k < frames; k++)
  1068. {
  1069. if (i % 2 == 0)
  1070. {
  1071. // left
  1072. outBuffer[i][k+timeOffset] = oldBufLeft[k] * (1.0f - balRangeL);
  1073. outBuffer[i][k+timeOffset] += outBuffer[i+1][k+timeOffset] * (1.0f - balRangeR);
  1074. }
  1075. else
  1076. {
  1077. // right
  1078. outBuffer[i][k+timeOffset] = outBuffer[i][k+timeOffset] * balRangeR;
  1079. outBuffer[i][k+timeOffset] += oldBufLeft[k] * balRangeL;
  1080. }
  1081. }
  1082. }
  1083. // Volume
  1084. if (kUses16Outs)
  1085. {
  1086. for (k=0; k < frames; k++)
  1087. outBuffer[i][k+timeOffset] = fAudio16Buffers[i][k] * kData->postProc.volume;
  1088. }
  1089. else if (doVolume)
  1090. {
  1091. for (k=0; k < frames; k++)
  1092. outBuffer[i][k+timeOffset] *= kData->postProc.volume;
  1093. }
  1094. }
  1095. } // End of Post-processing
  1096. // --------------------------------------------------------------------------------------------------------
  1097. kData->singleMutex.unlock();
  1098. return true;
  1099. }
  1100. void bufferSizeChanged(const uint32_t newBufferSize)
  1101. {
  1102. if (! kUses16Outs)
  1103. return;
  1104. for (uint32_t i=0; i < kData->audioOut.count; i++)
  1105. {
  1106. if (fAudio16Buffers[i] != nullptr)
  1107. delete[] fAudio16Buffers[i];
  1108. fAudio16Buffers[i] = new float[newBufferSize];
  1109. }
  1110. }
  1111. // -------------------------------------------------------------------
  1112. // Cleanup
  1113. void deleteBuffers()
  1114. {
  1115. carla_debug("FluidSynthPlugin::deleteBuffers() - start");
  1116. if (fAudio16Buffers != nullptr)
  1117. {
  1118. for (uint32_t i=0; i < kData->audioOut.count; i++)
  1119. {
  1120. if (fAudio16Buffers[i] != nullptr)
  1121. {
  1122. delete[] fAudio16Buffers[i];
  1123. fAudio16Buffers[i] = nullptr;
  1124. }
  1125. }
  1126. delete[] fAudio16Buffers;
  1127. fAudio16Buffers = nullptr;
  1128. }
  1129. CarlaPlugin::deleteBuffers();
  1130. carla_debug("FluidSynthPlugin::deleteBuffers() - end");
  1131. }
  1132. // -------------------------------------------------------------------
  1133. bool init(const char* const filename, const char* const name, const char* const label)
  1134. {
  1135. CARLA_ASSERT(fSynth != nullptr);
  1136. CARLA_ASSERT(filename != nullptr);
  1137. CARLA_ASSERT(label != nullptr);
  1138. // ---------------------------------------------------------------
  1139. // open soundfont
  1140. fSynthId = fluid_synth_sfload(fSynth, filename, 0);
  1141. if (fSynthId < 0)
  1142. {
  1143. kData->engine->setLastError("Failed to load SoundFont file");
  1144. return false;
  1145. }
  1146. // ---------------------------------------------------------------
  1147. // get info
  1148. fFilename = filename;
  1149. fLabel = label;
  1150. if (name != nullptr)
  1151. fName = kData->engine->getNewUniquePluginName(name);
  1152. else
  1153. fName = kData->engine->getNewUniquePluginName(label);
  1154. // ---------------------------------------------------------------
  1155. // register client
  1156. kData->client = kData->engine->addClient(this);
  1157. if (kData->client == nullptr || ! kData->client->isOk())
  1158. {
  1159. kData->engine->setLastError("Failed to register plugin client");
  1160. return false;
  1161. }
  1162. return true;
  1163. }
  1164. private:
  1165. enum FluidSynthInputParameters {
  1166. FluidSynthReverbOnOff = 0,
  1167. FluidSynthReverbRoomSize = 1,
  1168. FluidSynthReverbDamp = 2,
  1169. FluidSynthReverbLevel = 3,
  1170. FluidSynthReverbWidth = 4,
  1171. FluidSynthChorusOnOff = 5,
  1172. FluidSynthChorusNr = 6,
  1173. FluidSynthChorusLevel = 7,
  1174. FluidSynthChorusSpeedHz = 8,
  1175. FluidSynthChorusDepthMs = 9,
  1176. FluidSynthChorusType = 10,
  1177. FluidSynthPolyphony = 11,
  1178. FluidSynthInterpolation = 12,
  1179. FluidSynthVoiceCount = 13,
  1180. FluidSynthParametersMax = 14
  1181. };
  1182. const bool kUses16Outs;
  1183. CarlaString fLabel;
  1184. fluid_settings_t* fSettings;
  1185. fluid_synth_t* fSynth;
  1186. int fSynthId;
  1187. float** fAudio16Buffers;
  1188. double fParamBuffers[FluidSynthParametersMax];
  1189. CARLA_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(FluidSynthPlugin)
  1190. };
  1191. CARLA_BACKEND_END_NAMESPACE
  1192. #else // WANT_FLUIDSYNTH
  1193. # warning fluidsynth not available (no SF2 support)
  1194. #endif
  1195. CARLA_BACKEND_START_NAMESPACE
  1196. CarlaPlugin* CarlaPlugin::newSF2(const Initializer& init, const bool use16Outs)
  1197. {
  1198. carla_debug("CarlaPlugin::newSF2({%p, \"%s\", \"%s\", \"%s\"}, %s)", init.engine, init.filename, init.name, init.label, bool2str(use16Outs));
  1199. #ifdef WANT_FLUIDSYNTH
  1200. if (! fluid_is_soundfont(init.filename))
  1201. {
  1202. init.engine->setLastError("Requested file is not a valid SoundFont");
  1203. return nullptr;
  1204. }
  1205. if (init.engine->getProccessMode() == PROCESS_MODE_CONTINUOUS_RACK && use16Outs)
  1206. {
  1207. init.engine->setLastError("Carla's rack mode can only work with Stereo modules, please choose the 2-channel only SoundFont version");
  1208. return nullptr;
  1209. }
  1210. FluidSynthPlugin* const plugin = new FluidSynthPlugin(init.engine, init.id, use16Outs);
  1211. if (! plugin->init(init.filename, init.name, init.label))
  1212. {
  1213. delete plugin;
  1214. return nullptr;
  1215. }
  1216. plugin->reload();
  1217. return plugin;
  1218. #else
  1219. init.engine->setLastError("fluidsynth support not available");
  1220. return nullptr;
  1221. // unused
  1222. (void)use16Outs;
  1223. #endif
  1224. }
  1225. CARLA_BACKEND_END_NAMESPACE