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.

617 lines
18KB

  1. /*
  2. ZynAddSubFX - a software synthesizer
  3. SUBnote.cpp - The "subtractive" synthesizer
  4. Copyright (C) 2002-2005 Nasca Octavian Paul
  5. Author: Nasca Octavian Paul
  6. This program is free software; you can redistribute it and/or
  7. modify it under the terms of the GNU General Public License
  8. as published by the Free Software Foundation; either version 2
  9. of the License, or (at your option) any later version.
  10. */
  11. #include <cmath>
  12. #include <cstdlib>
  13. #include <cstdio>
  14. #include <cassert>
  15. #include <iostream>
  16. #include "../globals.h"
  17. #include "SUBnote.h"
  18. #include "Envelope.h"
  19. #include "ModFilter.h"
  20. #include "../Containers/ScratchString.h"
  21. #include "../Params/Controller.h"
  22. #include "../Params/SUBnoteParameters.h"
  23. #include "../Params/FilterParams.h"
  24. #include "../Misc/Time.h"
  25. #include "../Misc/Util.h"
  26. #include "../Misc/Allocator.h"
  27. SUBnote::SUBnote(const SUBnoteParameters *parameters, SynthParams &spars)
  28. :SynthNote(spars), pars(*parameters),
  29. AmpEnvelope(nullptr),
  30. FreqEnvelope(nullptr),
  31. BandWidthEnvelope(nullptr),
  32. GlobalFilter(nullptr),
  33. GlobalFilterEnvelope(nullptr),
  34. NoteEnabled(true),
  35. lfilter(nullptr), rfilter(nullptr),
  36. wm(nullptr)
  37. {
  38. setup(spars.frequency, spars.velocity, spars.portamento, spars.note);
  39. }
  40. float SUBnote::setupFilters(int *pos, bool automation)
  41. {
  42. //how much the amplitude is normalised (because the harmonics)
  43. float reduceamp = 0.0f;
  44. for(int n = 0; n < numharmonics; ++n) {
  45. const float freq = basefreq * pars.POvertoneFreqMult[pos[n]];
  46. overtone_freq[n] = freq;
  47. overtone_rolloff[n] = computerolloff(freq);
  48. //the bandwidth is not absolute(Hz); it is relative to frequency
  49. const float bw = SUBnoteParameters::convertBandwidth(pars.Pbandwidth,
  50. numstages, freq, pars.Pbwscale, pars.Phrelbw[pos[n]]);
  51. //try to keep same amplitude on all freqs and bw. (empirically)
  52. const float hgain = SUBnoteParameters::convertHarmonicMag(pars.Phmag[pos[n]],
  53. pars.Phmagtype);
  54. const float gain = hgain * sqrt(1500.0f / (bw * freq));
  55. reduceamp += hgain;
  56. for(int nph = 0; nph < numstages; ++nph) {
  57. float amp = 1.0f;
  58. if(nph == 0)
  59. amp = gain;
  60. initfilter(lfilter[nph + n * numstages], freq + OffsetHz, bw,
  61. amp, hgain, automation);
  62. if(stereo)
  63. initfilter(rfilter[nph + n * numstages], freq + OffsetHz, bw,
  64. amp, hgain, automation);
  65. }
  66. }
  67. if(reduceamp < 0.001f)
  68. reduceamp = 1.0f;
  69. return reduceamp;
  70. }
  71. void SUBnote::setup(float freq,
  72. float velocity,
  73. int portamento_,
  74. int midinote,
  75. bool legato)
  76. {
  77. this->velocity = velocity;
  78. portamento = portamento_;
  79. NoteEnabled = ON;
  80. volume = powf(0.1f, 3.0f * (1.0f - pars.PVolume / 96.0f)); //-60 dB .. 0 dB
  81. volume *= VelF(velocity, pars.PAmpVelocityScaleFunction);
  82. if(pars.PPanning != 0)
  83. panning = pars.PPanning / 127.0f;
  84. else
  85. panning = RND;
  86. if(!legato) { //normal note
  87. numstages = pars.Pnumstages;
  88. stereo = pars.Pstereo;
  89. start = pars.Pstart;
  90. firsttick = 1;
  91. }
  92. if(pars.Pfixedfreq == 0)
  93. basefreq = freq;
  94. else {
  95. basefreq = 440.0f;
  96. int fixedfreqET = pars.PfixedfreqET;
  97. if(fixedfreqET) { //if the frequency varies according the keyboard note
  98. float tmp = (midinote - 69.0f) / 12.0f
  99. * (powf(2.0f, (fixedfreqET - 1) / 63.0f) - 1.0f);
  100. if(fixedfreqET <= 64)
  101. basefreq *= powf(2.0f, tmp);
  102. else
  103. basefreq *= powf(3.0f, tmp);
  104. }
  105. }
  106. int BendAdj = pars.PBendAdjust - 64;
  107. if (BendAdj % 24 == 0)
  108. BendAdjust = BendAdj / 24;
  109. else
  110. BendAdjust = BendAdj / 24.0f;
  111. float offset_val = (pars.POffsetHz - 64)/64.0f;
  112. OffsetHz = 15.0f*(offset_val * sqrtf(fabsf(offset_val)));
  113. float detune = getdetune(pars.PDetuneType,
  114. pars.PCoarseDetune,
  115. pars.PDetune);
  116. basefreq *= powf(2.0f, detune / 1200.0f); //detune
  117. // basefreq*=ctl.pitchwheel.relfreq;//pitch wheel
  118. int pos[MAX_SUB_HARMONICS];
  119. int harmonics;
  120. pars.activeHarmonics(pos, harmonics);
  121. if(!legato) //normal note
  122. firstnumharmonics = numharmonics = harmonics;
  123. else {
  124. if(harmonics > firstnumharmonics)
  125. numharmonics = firstnumharmonics;
  126. else
  127. numharmonics = harmonics;
  128. }
  129. if(numharmonics == 0) {
  130. NoteEnabled = false;
  131. return;
  132. }
  133. if(!legato) { //normal note
  134. lfilter = memory.valloc<bpfilter>(numstages * numharmonics);
  135. if(stereo)
  136. rfilter = memory.valloc<bpfilter>(numstages * numharmonics);
  137. }
  138. //how much the amplitude is normalised (because the harmonics)
  139. float reduceamp = setupFilters(pos, false);
  140. oldreduceamp = reduceamp;
  141. volume /= reduceamp;
  142. oldpitchwheel = 0;
  143. oldbandwidth = 64;
  144. if(!legato) { //normal note
  145. if(pars.Pfixedfreq == 0)
  146. initparameters(basefreq, wm);
  147. else
  148. initparameters(basefreq / 440.0f * freq, wm);
  149. }
  150. else {
  151. if(pars.Pfixedfreq == 0)
  152. freq = basefreq;
  153. else
  154. freq *= basefreq / 440.0f;
  155. if(GlobalFilter)
  156. GlobalFilter->updateNoteFreq(basefreq);
  157. }
  158. oldamplitude = newamplitude;
  159. }
  160. SynthNote *SUBnote::cloneLegato(void)
  161. {
  162. SynthParams sp{memory, ctl, synth, time, legato.param.freq, velocity,
  163. portamento, legato.param.midinote, true};
  164. return memory.alloc<SUBnote>(&pars, sp);
  165. }
  166. void SUBnote::legatonote(LegatoParams pars)
  167. {
  168. // Manage legato stuff
  169. if(legato.update(pars))
  170. return;
  171. try {
  172. setup(pars.frequency, pars.velocity, pars.portamento, pars.midinote,
  173. true);
  174. } catch (std::bad_alloc &ba) {
  175. std::cerr << "failed to set legato note parameter in SUBnote: " << ba.what() << std::endl;
  176. }
  177. }
  178. SUBnote::~SUBnote()
  179. {
  180. if(NoteEnabled)
  181. KillNote();
  182. }
  183. /*
  184. * Kill the note
  185. */
  186. void SUBnote::KillNote()
  187. {
  188. if(NoteEnabled) {
  189. memory.devalloc(numstages * numharmonics, lfilter);
  190. if(stereo)
  191. memory.devalloc(numstages * numharmonics, rfilter);
  192. memory.dealloc(AmpEnvelope);
  193. memory.dealloc(FreqEnvelope);
  194. memory.dealloc(BandWidthEnvelope);
  195. memory.dealloc(GlobalFilter);
  196. memory.dealloc(GlobalFilterEnvelope);
  197. NoteEnabled = false;
  198. }
  199. }
  200. /*
  201. * Compute the filters coefficients
  202. */
  203. void SUBnote::computefiltercoefs(bpfilter &filter,
  204. float freq,
  205. float bw,
  206. float gain)
  207. {
  208. if(freq > synth.samplerate_f / 2.0f - 200.0f)
  209. freq = synth.samplerate_f / 2.0f - 200.0f;
  210. float omega = 2.0f * PI * freq / synth.samplerate_f;
  211. float sn = sinf(omega);
  212. float cs = cosf(omega);
  213. float alpha = sn * sinh(LOG_2 / 2.0f * bw * omega / sn);
  214. if(alpha > 1)
  215. alpha = 1;
  216. if(alpha > bw)
  217. alpha = bw;
  218. filter.b0 = alpha / (1.0f + alpha) * filter.amp * gain;
  219. filter.b2 = -alpha / (1.0f + alpha) * filter.amp * gain;
  220. filter.a1 = -2.0f * cs / (1.0f + alpha);
  221. filter.a2 = (1.0f - alpha) / (1.0f + alpha);
  222. }
  223. /*
  224. * Initialise the filters
  225. */
  226. void SUBnote::initfilter(bpfilter &filter,
  227. float freq,
  228. float bw,
  229. float amp,
  230. float mag,
  231. bool automation)
  232. {
  233. if(!automation) {
  234. filter.xn1 = 0.0f;
  235. filter.xn2 = 0.0f;
  236. if(start == 0) {
  237. filter.yn1 = 0.0f;
  238. filter.yn2 = 0.0f;
  239. }
  240. else {
  241. float a = 0.1f * mag; //empirically
  242. float p = RND * 2.0f * PI;
  243. if(start == 1)
  244. a *= RND;
  245. filter.yn1 = a * cosf(p);
  246. filter.yn2 = a * cosf(p + freq * 2.0f * PI / synth.samplerate_f);
  247. //correct the error of computation the start amplitude
  248. //at very high frequencies
  249. if(freq > synth.samplerate_f * 0.96f) {
  250. filter.yn1 = 0.0f;
  251. filter.yn2 = 0.0f;
  252. }
  253. }
  254. }
  255. filter.amp = amp;
  256. filter.freq = freq;
  257. filter.bw = bw;
  258. computefiltercoefs(filter, freq, bw, 1.0f);
  259. }
  260. /*
  261. * Do the filtering
  262. */
  263. inline void SubFilterA(const float coeff[4], float &src, float work[4])
  264. {
  265. work[3] = src*coeff[0]+work[1]*coeff[1]+work[2]*coeff[2]+work[3]*coeff[3];
  266. work[1] = src;
  267. src = work[3];
  268. }
  269. inline void SubFilterB(const float coeff[4], float &src, float work[4])
  270. {
  271. work[2] = src*coeff[0]+work[0]*coeff[1]+work[3]*coeff[2]+work[2]*coeff[3];
  272. work[0] = src;
  273. src = work[2];
  274. }
  275. //This dance is designed to minimize unneeded memory operations which can result
  276. //in quite a bit of wasted time
  277. void SUBnote::filter(bpfilter &filter, float *smps)
  278. {
  279. assert(synth.buffersize % 8 == 0);
  280. float coeff[4] = {filter.b0, filter.b2, -filter.a1, -filter.a2};
  281. float work[4] = {filter.xn1, filter.xn2, filter.yn1, filter.yn2};
  282. for(int i = 0; i < synth.buffersize; i += 8) {
  283. SubFilterA(coeff, smps[i + 0], work);
  284. SubFilterB(coeff, smps[i + 1], work);
  285. SubFilterA(coeff, smps[i + 2], work);
  286. SubFilterB(coeff, smps[i + 3], work);
  287. SubFilterA(coeff, smps[i + 4], work);
  288. SubFilterB(coeff, smps[i + 5], work);
  289. SubFilterA(coeff, smps[i + 6], work);
  290. SubFilterB(coeff, smps[i + 7], work);
  291. }
  292. filter.xn1 = work[0];
  293. filter.xn2 = work[1];
  294. filter.yn1 = work[2];
  295. filter.yn2 = work[3];
  296. }
  297. /*
  298. * Init Parameters
  299. */
  300. void SUBnote::initparameters(float freq, WatchManager *wm)
  301. {
  302. //TODO populate this base string
  303. ScratchString pre;
  304. AmpEnvelope = memory.alloc<Envelope>(*pars.AmpEnvelope, freq,
  305. synth.dt(), wm, (pre+"AmpEnvelope/").c_str);
  306. if(pars.PFreqEnvelopeEnabled)
  307. FreqEnvelope = memory.alloc<Envelope>(*pars.FreqEnvelope, freq,
  308. synth.dt(), wm, (pre+"FreqEnvelope/").c_str);
  309. if(pars.PBandWidthEnvelopeEnabled)
  310. BandWidthEnvelope = memory.alloc<Envelope>(*pars.BandWidthEnvelope,
  311. freq, synth.dt(), wm, (pre+"BandWidthEnvelope/").c_str);
  312. if(pars.PGlobalFilterEnabled) {
  313. GlobalFilterEnvelope =
  314. memory.alloc<Envelope>(*pars.GlobalFilterEnvelope, freq,
  315. synth.dt(), wm, (pre+"GlobalFilterEnvelope/").c_str);
  316. GlobalFilter = memory.alloc<ModFilter>(*pars.GlobalFilter, synth, time, memory, stereo, freq);
  317. GlobalFilter->updateSense(velocity, pars.PGlobalFilterVelocityScale,
  318. pars.PGlobalFilterVelocityScaleFunction);
  319. GlobalFilter->addMod(*GlobalFilterEnvelope);
  320. }
  321. computecurrentparameters();
  322. }
  323. /*
  324. * Compute how much to reduce amplitude near nyquist or subaudible frequencies.
  325. */
  326. float SUBnote::computerolloff(float freq)
  327. {
  328. const float lower_limit = 10.0f;
  329. const float lower_width = 10.0f;
  330. const float upper_width = 200.0f;
  331. float upper_limit = synth.samplerate / 2.0f;
  332. if (freq > lower_limit + lower_width &&
  333. freq < upper_limit - upper_width)
  334. return 1.0f;
  335. if (freq <= lower_limit || freq >= upper_limit)
  336. return 0.0f;
  337. if (freq <= lower_limit + lower_width)
  338. return (1.0f - cosf(M_PI * (freq - lower_limit) / lower_width)) / 2.0f;
  339. return (1.0f - cosf(M_PI * (freq - upper_limit) / upper_width)) / 2.0f;
  340. }
  341. /*
  342. * Compute Parameters of SUBnote for each tick
  343. */
  344. void SUBnote::computecurrentparameters()
  345. {
  346. //Recompute parameters for realtime automation
  347. if(pars.time && pars.last_update_timestamp == pars.time->time()) {
  348. //A little bit of copy/paste for now
  349. int pos[MAX_SUB_HARMONICS];
  350. int harmonics;
  351. pars.activeHarmonics(pos, harmonics);
  352. bool delta_harmonics = (harmonics != numharmonics);
  353. if(delta_harmonics) {
  354. memory.devalloc(lfilter);
  355. memory.devalloc(rfilter);
  356. firstnumharmonics = numharmonics = harmonics;
  357. lfilter = memory.valloc<bpfilter>(numstages * numharmonics);
  358. if(stereo)
  359. rfilter = memory.valloc<bpfilter>(numstages * numharmonics);
  360. }
  361. float reduceamp = setupFilters(pos, !delta_harmonics);
  362. volume = volume*oldreduceamp/reduceamp;
  363. oldreduceamp = reduceamp;
  364. }
  365. if(FreqEnvelope || BandWidthEnvelope
  366. || (oldpitchwheel != ctl.pitchwheel.data)
  367. || (oldbandwidth != ctl.bandwidth.data)
  368. || portamento) {
  369. float envfreq = 1.0f;
  370. float envbw = 1.0f;
  371. if(FreqEnvelope) {
  372. envfreq = FreqEnvelope->envout() / 1200;
  373. envfreq = powf(2.0f, envfreq);
  374. }
  375. envfreq *=
  376. powf(ctl.pitchwheel.relfreq, BendAdjust); //pitch wheel
  377. //Update frequency while portamento is converging
  378. if(portamento) {
  379. envfreq *= ctl.portamento.freqrap;
  380. if(!ctl.portamento.used) //the portamento has finished
  381. portamento = false;
  382. }
  383. if(BandWidthEnvelope) {
  384. envbw = BandWidthEnvelope->envout();
  385. envbw = powf(2, envbw);
  386. }
  387. envbw *= ctl.bandwidth.relbw; //bandwidth controller
  388. //Recompute High Frequency Dampening Terms
  389. for(int n = 0; n < numharmonics; ++n)
  390. overtone_rolloff[n] = computerolloff(overtone_freq[n] * envfreq);
  391. //Recompute Filter Coefficients
  392. float tmpgain = 1.0f / sqrt(envbw * envfreq);
  393. computeallfiltercoefs(lfilter, envfreq, envbw, tmpgain);
  394. if(stereo)
  395. computeallfiltercoefs(rfilter, envfreq, envbw, tmpgain);
  396. oldbandwidth = ctl.bandwidth.data;
  397. oldpitchwheel = ctl.pitchwheel.data;
  398. }
  399. newamplitude = volume * AmpEnvelope->envout_dB() * 2.0f;
  400. //Filter
  401. if(GlobalFilter)
  402. GlobalFilter->update(ctl.filtercutoff.relfreq,
  403. ctl.filterq.relq);
  404. }
  405. void SUBnote::computeallfiltercoefs(bpfilter *filters, float envfreq,
  406. float envbw, float gain)
  407. {
  408. for(int n = 0; n < numharmonics; ++n)
  409. for(int nph = 0; nph < numstages; ++nph)
  410. computefiltercoefs(filters[nph + n * numstages],
  411. filters[nph + n * numstages].freq * envfreq,
  412. filters[nph + n * numstages].bw * envbw,
  413. nph == 0 ? gain : 1.0);
  414. }
  415. void SUBnote::chanOutput(float *out, bpfilter *bp, int buffer_size)
  416. {
  417. float tmprnd[buffer_size];
  418. float tmpsmp[buffer_size];
  419. //Initialize Random Input
  420. for(int i = 0; i < buffer_size; ++i)
  421. tmprnd[i] = RND * 2.0f - 1.0f;
  422. //For each harmonic apply the filter on the random input stream
  423. //Sum the filter outputs to obtain the output signal
  424. for(int n = 0; n < numharmonics; ++n) {
  425. float rolloff = overtone_rolloff[n];
  426. memcpy(tmpsmp, tmprnd, synth.bufferbytes);
  427. for(int nph = 0; nph < numstages; ++nph)
  428. filter(bp[nph + n * numstages], tmpsmp);
  429. for(int i = 0; i < synth.buffersize; ++i)
  430. out[i] += tmpsmp[i] * rolloff;
  431. }
  432. }
  433. /*
  434. * Note Output
  435. */
  436. int SUBnote::noteout(float *outl, float *outr)
  437. {
  438. memcpy(outl, synth.denormalkillbuf, synth.bufferbytes);
  439. memcpy(outr, synth.denormalkillbuf, synth.bufferbytes);
  440. if(!NoteEnabled)
  441. return 0;
  442. if(stereo) {
  443. chanOutput(outl, lfilter, synth.buffersize);
  444. chanOutput(outr, rfilter, synth.buffersize);
  445. if(GlobalFilter)
  446. GlobalFilter->filter(outl, outr);
  447. } else {
  448. chanOutput(outl, lfilter, synth.buffersize);
  449. if(GlobalFilter)
  450. GlobalFilter->filter(outl, 0);
  451. memcpy(outr, outl, synth.bufferbytes);
  452. }
  453. if(firsttick) {
  454. int n = 10;
  455. if(n > synth.buffersize)
  456. n = synth.buffersize;
  457. for(int i = 0; i < n; ++i) {
  458. float ampfadein = 0.5f - 0.5f * cosf(
  459. (float) i / (float) n * PI);
  460. outl[i] *= ampfadein;
  461. outr[i] *= ampfadein;
  462. }
  463. firsttick = false;
  464. }
  465. if(ABOVE_AMPLITUDE_THRESHOLD(oldamplitude, newamplitude))
  466. // Amplitude interpolation
  467. for(int i = 0; i < synth.buffersize; ++i) {
  468. float tmpvol = INTERPOLATE_AMPLITUDE(oldamplitude,
  469. newamplitude,
  470. i,
  471. synth.buffersize);
  472. outl[i] *= tmpvol * panning;
  473. outr[i] *= tmpvol * (1.0f - panning);
  474. }
  475. else
  476. for(int i = 0; i < synth.buffersize; ++i) {
  477. outl[i] *= newamplitude * panning;
  478. outr[i] *= newamplitude * (1.0f - panning);
  479. }
  480. oldamplitude = newamplitude;
  481. computecurrentparameters();
  482. // Apply legato-specific sound signal modifications
  483. legato.apply(*this, outl, outr);
  484. // Check if the note needs to be computed more
  485. if(AmpEnvelope->finished() != 0) {
  486. for(int i = 0; i < synth.buffersize; ++i) { //fade-out
  487. float tmp = 1.0f - (float)i / synth.buffersize_f;
  488. outl[i] *= tmp;
  489. outr[i] *= tmp;
  490. }
  491. KillNote();
  492. }
  493. return 1;
  494. }
  495. /*
  496. * Release Key (Note Off)
  497. */
  498. void SUBnote::releasekey()
  499. {
  500. AmpEnvelope->releasekey();
  501. if(FreqEnvelope)
  502. FreqEnvelope->releasekey();
  503. if(BandWidthEnvelope)
  504. BandWidthEnvelope->releasekey();
  505. if(GlobalFilterEnvelope)
  506. GlobalFilterEnvelope->releasekey();
  507. }
  508. /*
  509. * Check if the note is finished
  510. */
  511. bool SUBnote::finished() const
  512. {
  513. return !NoteEnabled;
  514. }
  515. void SUBnote::entomb(void)
  516. {
  517. AmpEnvelope->forceFinish();
  518. }