tap_doubler.c 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738
  1. /* -*- linux-c -*-
  2. Copyright (C) 2004 Tom Szilagyi
  3. This program is free software; you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation; either version 2 of the License, or
  6. (at your option) any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program; if not, write to the Free Software
  13. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  14. $Id: tap_doubler.c,v 1.4 2004/08/13 18:34:31 tszilagyi Exp $
  15. */
  16. #include <stdio.h>
  17. #include <stdlib.h>
  18. #include <string.h>
  19. #include <math.h>
  20. #include <time.h>
  21. #include <ladspa.h>
  22. #include "tap_utils.h"
  23. /* The Unique ID of the plugin: */
  24. #define ID_STEREO 2156
  25. /* The port numbers for the plugin: */
  26. #define TIME 0
  27. #define PITCH 1
  28. #define DRYLEVEL 2
  29. #define DRYPOSL 3
  30. #define DRYPOSR 4
  31. #define WETLEVEL 5
  32. #define WETPOSL 6
  33. #define WETPOSR 7
  34. #define INPUT_L 8
  35. #define INPUT_R 9
  36. #define OUTPUT_L 10
  37. #define OUTPUT_R 11
  38. /* Total number of ports */
  39. #define PORTCOUNT_STEREO 12
  40. /* Number of pink noise samples to be generated at once */
  41. #define NOISE_LEN 1024
  42. /*
  43. * Largest buffer length needed (at 192 kHz).
  44. */
  45. #define BUFLEN 11520
  46. /* The structure used to hold port connection information and state */
  47. typedef struct {
  48. LADSPA_Data * time;
  49. LADSPA_Data * pitch;
  50. LADSPA_Data * drylevel;
  51. LADSPA_Data * dryposl;
  52. LADSPA_Data * dryposr;
  53. LADSPA_Data * wetlevel;
  54. LADSPA_Data * wetposl;
  55. LADSPA_Data * wetposr;
  56. LADSPA_Data * input_L;
  57. LADSPA_Data * input_R;
  58. LADSPA_Data * output_L;
  59. LADSPA_Data * output_R;
  60. LADSPA_Data old_time;
  61. LADSPA_Data old_pitch;
  62. LADSPA_Data * ring_L;
  63. unsigned long buflen_L;
  64. unsigned long pos_L;
  65. LADSPA_Data * ring_R;
  66. unsigned long buflen_R;
  67. unsigned long pos_R;
  68. LADSPA_Data * ring_pnoise;
  69. unsigned long buflen_pnoise;
  70. unsigned long pos_pnoise;
  71. LADSPA_Data * ring_dnoise;
  72. unsigned long buflen_dnoise;
  73. unsigned long pos_dnoise;
  74. float delay;
  75. float d_delay;
  76. float p_delay;
  77. unsigned long n_delay;
  78. float pitchmod;
  79. float d_pitch;
  80. float p_pitch;
  81. unsigned long n_pitch;
  82. unsigned long p_stretch;
  83. unsigned long d_stretch;
  84. unsigned long sample_rate;
  85. LADSPA_Data run_adding_gain;
  86. } Doubler;
  87. /* generate fractal pattern using Midpoint Displacement Method
  88. * v: buffer of floats to output fractal pattern to
  89. * N: length of v, MUST be integer power of 2 (ie 128, 256, ...)
  90. * H: Hurst constant, between 0 and 0.9999 (fractal dimension)
  91. */
  92. void
  93. fractal(LADSPA_Data * v, int N, float H) {
  94. int l = N;
  95. int k;
  96. float r = 1.0f;
  97. int c;
  98. v[0] = 0;
  99. while (l > 1) {
  100. k = N / l;
  101. for (c = 0; c < k; c++) {
  102. v[c*l + l/2] = (v[c*l] + v[((c+1) * l) % N]) / 2.0f +
  103. 2.0f * r * (rand() - (float)RAND_MAX/2.0f) / (float)RAND_MAX;
  104. v[c*l + l/2] = LIMIT(v[c*l + l/2], -1.0f, 1.0f);
  105. }
  106. l /= 2;
  107. r /= powf(2, H);
  108. }
  109. }
  110. /* Construct a new plugin instance. */
  111. LADSPA_Handle
  112. instantiate_Doubler(const LADSPA_Descriptor * Descriptor,
  113. unsigned long sample_rate) {
  114. LADSPA_Handle * ptr;
  115. if ((ptr = malloc(sizeof(Doubler))) != NULL) {
  116. ((Doubler *)ptr)->sample_rate = sample_rate;
  117. ((Doubler *)ptr)->run_adding_gain = 1.0f;
  118. if ((((Doubler *)ptr)->ring_L =
  119. calloc(BUFLEN * sample_rate / 192000, sizeof(LADSPA_Data))) == NULL)
  120. return NULL;
  121. ((Doubler *)ptr)->buflen_L = BUFLEN * sample_rate / 192000;
  122. ((Doubler *)ptr)->pos_L = 0;
  123. if ((((Doubler *)ptr)->ring_R =
  124. calloc(BUFLEN * sample_rate / 192000, sizeof(LADSPA_Data))) == NULL)
  125. return NULL;
  126. ((Doubler *)ptr)->buflen_R = BUFLEN * sample_rate / 192000;
  127. ((Doubler *)ptr)->pos_R = 0;
  128. if ((((Doubler *)ptr)->ring_pnoise =
  129. calloc(NOISE_LEN, sizeof(LADSPA_Data))) == NULL)
  130. return NULL;
  131. ((Doubler *)ptr)->buflen_pnoise = NOISE_LEN;
  132. ((Doubler *)ptr)->pos_pnoise = 0;
  133. if ((((Doubler *)ptr)->ring_dnoise =
  134. calloc(NOISE_LEN, sizeof(LADSPA_Data))) == NULL)
  135. return NULL;
  136. ((Doubler *)ptr)->buflen_dnoise = NOISE_LEN;
  137. ((Doubler *)ptr)->pos_dnoise = 0;
  138. ((Doubler *)ptr)->d_stretch = sample_rate / 10;
  139. ((Doubler *)ptr)->p_stretch = sample_rate / 1000;
  140. ((Doubler *)ptr)->delay = 0.0f;
  141. ((Doubler *)ptr)->d_delay = 0.0f;
  142. ((Doubler *)ptr)->p_delay = 0.0f;
  143. ((Doubler *)ptr)->n_delay = ((Doubler *)ptr)->d_stretch;
  144. ((Doubler *)ptr)->pitchmod = 0.0f;
  145. ((Doubler *)ptr)->d_pitch = 0.0f;
  146. ((Doubler *)ptr)->p_pitch = 0.0f;
  147. ((Doubler *)ptr)->n_pitch = ((Doubler *)ptr)->p_stretch;
  148. return ptr;
  149. }
  150. return NULL;
  151. }
  152. void
  153. activate_Doubler(LADSPA_Handle Instance) {
  154. Doubler * ptr = (Doubler *)Instance;
  155. unsigned long i;
  156. for (i = 0; i < BUFLEN * ptr->sample_rate / 192000; i++) {
  157. ptr->ring_L[i] = 0.0f;
  158. ptr->ring_R[i] = 0.0f;
  159. }
  160. ptr->old_time = -1.0f;
  161. ptr->old_pitch = -1.0f;
  162. }
  163. /* Connect a port to a data location. */
  164. void
  165. connect_port_Doubler(LADSPA_Handle Instance,
  166. unsigned long Port,
  167. LADSPA_Data * data) {
  168. Doubler * ptr = (Doubler *)Instance;
  169. switch (Port) {
  170. case TIME:
  171. ptr->time = data;
  172. break;
  173. case PITCH:
  174. ptr->pitch = data;
  175. break;
  176. case DRYLEVEL:
  177. ptr->drylevel = data;
  178. break;
  179. case DRYPOSL:
  180. ptr->dryposl = data;
  181. break;
  182. case DRYPOSR:
  183. ptr->dryposr = data;
  184. break;
  185. case WETLEVEL:
  186. ptr->wetlevel = data;
  187. break;
  188. case WETPOSL:
  189. ptr->wetposl = data;
  190. break;
  191. case WETPOSR:
  192. ptr->wetposr = data;
  193. break;
  194. case INPUT_L:
  195. ptr->input_L = data;
  196. break;
  197. case INPUT_R:
  198. ptr->input_R = data;
  199. break;
  200. case OUTPUT_L:
  201. ptr->output_L = data;
  202. break;
  203. case OUTPUT_R:
  204. ptr->output_R = data;
  205. break;
  206. }
  207. }
  208. void
  209. run_Doubler(LADSPA_Handle Instance,
  210. unsigned long SampleCount) {
  211. Doubler * ptr = (Doubler *)Instance;
  212. LADSPA_Data pitch = LIMIT(*(ptr->pitch),0.0f,1.0f) + 0.75f;
  213. LADSPA_Data depth = LIMIT(((1.0f - LIMIT(*(ptr->pitch),0.0f,1.0f)) * 1.75f + 0.25f) *
  214. ptr->sample_rate / 6000.0f / M_PI,
  215. 0, ptr->buflen_L / 2);
  216. LADSPA_Data time = LIMIT(*(ptr->time), 0.0f, 1.0f) + 0.5f;
  217. LADSPA_Data drylevel = db2lin(LIMIT(*(ptr->drylevel),-90.0f,20.0f));
  218. LADSPA_Data wetlevel = db2lin(LIMIT(*(ptr->wetlevel),-90.0f,20.0f));
  219. LADSPA_Data dryposl = 1.0f - LIMIT(*(ptr->dryposl), 0.0f, 1.0f);
  220. LADSPA_Data dryposr = LIMIT(*(ptr->dryposr), 0.0f, 1.0f);
  221. LADSPA_Data wetposl = 1.0f - LIMIT(*(ptr->wetposl), 0.0f, 1.0f);
  222. LADSPA_Data wetposr = LIMIT(*(ptr->wetposr), 0.0f, 1.0f);
  223. LADSPA_Data * input_L = ptr->input_L;
  224. LADSPA_Data * input_R = ptr->input_R;
  225. LADSPA_Data * output_L = ptr->output_L;
  226. LADSPA_Data * output_R = ptr->output_R;
  227. unsigned long sample_index;
  228. unsigned long sample_count = SampleCount;
  229. LADSPA_Data in_L = 0.0f;
  230. LADSPA_Data in_R = 0.0f;
  231. LADSPA_Data out_L = 0.0f;
  232. LADSPA_Data out_R = 0.0f;
  233. LADSPA_Data fpos = 0.0f;
  234. LADSPA_Data n = 0.0f;
  235. LADSPA_Data rem = 0.0f;
  236. LADSPA_Data s_a_L, s_a_R, s_b_L, s_b_R;
  237. LADSPA_Data prev_p_pitch = 0.0f;
  238. LADSPA_Data prev_p_delay = 0.0f;
  239. LADSPA_Data delay;
  240. LADSPA_Data drystream_L = 0.0f;
  241. LADSPA_Data drystream_R = 0.0f;
  242. LADSPA_Data wetstream_L = 0.0f;
  243. LADSPA_Data wetstream_R = 0.0f;
  244. if (ptr->old_pitch != pitch) {
  245. ptr->pitchmod = ptr->p_pitch;
  246. prev_p_pitch = ptr->p_pitch;
  247. fractal(ptr->ring_pnoise, NOISE_LEN, pitch);
  248. ptr->pos_pnoise = 0;
  249. ptr->p_pitch = push_buffer(0.0f, ptr->ring_pnoise,
  250. ptr->buflen_pnoise, &(ptr->pos_pnoise));
  251. ptr->d_pitch = (ptr->p_pitch - prev_p_pitch) / (float)(ptr->p_stretch);
  252. ptr->n_pitch = 0;
  253. ptr->old_pitch = pitch;
  254. }
  255. if (ptr->old_time != time) {
  256. ptr->delay = ptr->p_delay;
  257. prev_p_delay = ptr->p_delay;
  258. fractal(ptr->ring_dnoise, NOISE_LEN, time);
  259. ptr->pos_dnoise = 0;
  260. ptr->p_delay = push_buffer(0.0f, ptr->ring_dnoise,
  261. ptr->buflen_dnoise, &(ptr->pos_dnoise));
  262. ptr->d_delay = (ptr->p_delay - prev_p_delay) / (float)(ptr->d_stretch);
  263. ptr->n_delay = 0;
  264. ptr->old_time = time;
  265. }
  266. for (sample_index = 0; sample_index < sample_count; sample_index++) {
  267. in_L = *(input_L++);
  268. in_R = *(input_R++);
  269. push_buffer(in_L, ptr->ring_L, ptr->buflen_L, &(ptr->pos_L));
  270. push_buffer(in_R, ptr->ring_R, ptr->buflen_R, &(ptr->pos_R));
  271. if (ptr->n_pitch < ptr->p_stretch) {
  272. ptr->pitchmod += ptr->d_pitch;
  273. ptr->n_pitch++;
  274. } else {
  275. ptr->pitchmod = ptr->p_pitch;
  276. prev_p_pitch = ptr->p_pitch;
  277. if (!ptr->pos_pnoise) {
  278. fractal(ptr->ring_pnoise, NOISE_LEN, pitch);
  279. }
  280. ptr->p_pitch = push_buffer(0.0f, ptr->ring_pnoise,
  281. ptr->buflen_pnoise, &(ptr->pos_pnoise));
  282. ptr->d_pitch = (ptr->p_pitch - prev_p_pitch) / (float)(ptr->p_stretch);
  283. ptr->n_pitch = 0;
  284. }
  285. if (ptr->n_delay < ptr->d_stretch) {
  286. ptr->delay += ptr->d_delay;
  287. ptr->n_delay++;
  288. } else {
  289. ptr->delay = ptr->p_delay;
  290. prev_p_delay = ptr->p_delay;
  291. if (!ptr->pos_dnoise) {
  292. fractal(ptr->ring_dnoise, NOISE_LEN, time);
  293. }
  294. ptr->p_delay = push_buffer(0.0f, ptr->ring_dnoise,
  295. ptr->buflen_dnoise, &(ptr->pos_dnoise));
  296. ptr->d_delay = (ptr->p_delay - prev_p_delay) / (float)(ptr->d_stretch);
  297. ptr->n_delay = 0;
  298. }
  299. delay = (12.5f * ptr->delay + 37.5f) * ptr->sample_rate / 1000.0f;
  300. fpos = ptr->buflen_L - depth * (1.0f - ptr->pitchmod) - delay - 1.0f;
  301. n = floorf(fpos);
  302. rem = fpos - n;
  303. s_a_L = read_buffer(ptr->ring_L, ptr->buflen_L,
  304. ptr->pos_L, (unsigned long) n);
  305. s_b_L = read_buffer(ptr->ring_L, ptr->buflen_L,
  306. ptr->pos_L, (unsigned long) n + 1);
  307. s_a_R = read_buffer(ptr->ring_R, ptr->buflen_R,
  308. ptr->pos_R, (unsigned long) n);
  309. s_b_R = read_buffer(ptr->ring_R, ptr->buflen_R,
  310. ptr->pos_R, (unsigned long) n + 1);
  311. drystream_L = drylevel * in_L;
  312. drystream_R = drylevel * in_R;
  313. wetstream_L = wetlevel * ((1 - rem) * s_a_L + rem * s_b_L);
  314. wetstream_R = wetlevel * ((1 - rem) * s_a_R + rem * s_b_R);
  315. out_L = dryposl * drystream_L + (1.0f - dryposr) * drystream_R +
  316. wetposl * wetstream_L + (1.0f - wetposr) * wetstream_R;
  317. out_R = (1.0f - dryposl) * drystream_L + dryposr * drystream_R +
  318. (1.0f - wetposl) * wetstream_L + wetposr * wetstream_R;
  319. *(output_L++) = out_L;
  320. *(output_R++) = out_R;
  321. }
  322. }
  323. void
  324. set_run_adding_gain_Doubler(LADSPA_Handle Instance, LADSPA_Data gain) {
  325. Doubler * ptr = (Doubler *)Instance;
  326. ptr->run_adding_gain = gain;
  327. }
  328. void
  329. run_adding_Doubler(LADSPA_Handle Instance,
  330. unsigned long SampleCount) {
  331. Doubler * ptr = (Doubler *)Instance;
  332. LADSPA_Data pitch = LIMIT(*(ptr->pitch),0.0f,1.0f) + 0.75f;
  333. LADSPA_Data depth = LIMIT(((1.0f - LIMIT(*(ptr->pitch),0.0f,1.0f)) * 1.75f + 0.25f) *
  334. ptr->sample_rate / 6000.0f / M_PI,
  335. 0, ptr->buflen_L / 2);
  336. LADSPA_Data time = LIMIT(*(ptr->time), 0.0f, 1.0f) + 0.5f;
  337. LADSPA_Data drylevel = db2lin(LIMIT(*(ptr->drylevel),-90.0f,20.0f));
  338. LADSPA_Data wetlevel = db2lin(LIMIT(*(ptr->wetlevel),-90.0f,20.0f));
  339. LADSPA_Data dryposl = 1.0f - LIMIT(*(ptr->dryposl), 0.0f, 1.0f);
  340. LADSPA_Data dryposr = LIMIT(*(ptr->dryposr), 0.0f, 1.0f);
  341. LADSPA_Data wetposl = 1.0f - LIMIT(*(ptr->wetposl), 0.0f, 1.0f);
  342. LADSPA_Data wetposr = LIMIT(*(ptr->wetposr), 0.0f, 1.0f);
  343. LADSPA_Data * input_L = ptr->input_L;
  344. LADSPA_Data * input_R = ptr->input_R;
  345. LADSPA_Data * output_L = ptr->output_L;
  346. LADSPA_Data * output_R = ptr->output_R;
  347. unsigned long sample_index;
  348. unsigned long sample_count = SampleCount;
  349. LADSPA_Data in_L = 0.0f;
  350. LADSPA_Data in_R = 0.0f;
  351. LADSPA_Data out_L = 0.0f;
  352. LADSPA_Data out_R = 0.0f;
  353. LADSPA_Data fpos = 0.0f;
  354. LADSPA_Data n = 0.0f;
  355. LADSPA_Data rem = 0.0f;
  356. LADSPA_Data s_a_L, s_a_R, s_b_L, s_b_R;
  357. LADSPA_Data prev_p_pitch = 0.0f;
  358. LADSPA_Data prev_p_delay = 0.0f;
  359. LADSPA_Data delay;
  360. LADSPA_Data drystream_L = 0.0f;
  361. LADSPA_Data drystream_R = 0.0f;
  362. LADSPA_Data wetstream_L = 0.0f;
  363. LADSPA_Data wetstream_R = 0.0f;
  364. if (ptr->old_pitch != pitch) {
  365. ptr->pitchmod = ptr->p_pitch;
  366. prev_p_pitch = ptr->p_pitch;
  367. fractal(ptr->ring_pnoise, NOISE_LEN, pitch);
  368. ptr->pos_pnoise = 0;
  369. ptr->p_pitch = push_buffer(0.0f, ptr->ring_pnoise,
  370. ptr->buflen_pnoise, &(ptr->pos_pnoise));
  371. ptr->d_pitch = (ptr->p_pitch - prev_p_pitch) / (float)(ptr->p_stretch);
  372. ptr->n_pitch = 0;
  373. ptr->old_pitch = pitch;
  374. }
  375. if (ptr->old_time != time) {
  376. ptr->delay = ptr->p_delay;
  377. prev_p_delay = ptr->p_delay;
  378. fractal(ptr->ring_dnoise, NOISE_LEN, time);
  379. ptr->pos_dnoise = 0;
  380. ptr->p_delay = push_buffer(0.0f, ptr->ring_dnoise,
  381. ptr->buflen_dnoise, &(ptr->pos_dnoise));
  382. ptr->d_delay = (ptr->p_delay - prev_p_delay) / (float)(ptr->d_stretch);
  383. ptr->n_delay = 0;
  384. ptr->old_time = time;
  385. }
  386. for (sample_index = 0; sample_index < sample_count; sample_index++) {
  387. in_L = *(input_L++);
  388. in_R = *(input_R++);
  389. push_buffer(in_L, ptr->ring_L, ptr->buflen_L, &(ptr->pos_L));
  390. push_buffer(in_R, ptr->ring_R, ptr->buflen_R, &(ptr->pos_R));
  391. if (ptr->n_pitch < ptr->p_stretch) {
  392. ptr->pitchmod += ptr->d_pitch;
  393. ptr->n_pitch++;
  394. } else {
  395. ptr->pitchmod = ptr->p_pitch;
  396. prev_p_pitch = ptr->p_pitch;
  397. if (!ptr->pos_pnoise) {
  398. fractal(ptr->ring_pnoise, NOISE_LEN, pitch);
  399. }
  400. ptr->p_pitch = push_buffer(0.0f, ptr->ring_pnoise,
  401. ptr->buflen_pnoise, &(ptr->pos_pnoise));
  402. ptr->d_pitch = (ptr->p_pitch - prev_p_pitch) / (float)(ptr->p_stretch);
  403. ptr->n_pitch = 0;
  404. }
  405. if (ptr->n_delay < ptr->d_stretch) {
  406. ptr->delay += ptr->d_delay;
  407. ptr->n_delay++;
  408. } else {
  409. ptr->delay = ptr->p_delay;
  410. prev_p_delay = ptr->p_delay;
  411. if (!ptr->pos_dnoise) {
  412. fractal(ptr->ring_dnoise, NOISE_LEN, time);
  413. }
  414. ptr->p_delay = push_buffer(0.0f, ptr->ring_dnoise,
  415. ptr->buflen_dnoise, &(ptr->pos_dnoise));
  416. ptr->d_delay = (ptr->p_delay - prev_p_delay) / (float)(ptr->d_stretch);
  417. ptr->n_delay = 0;
  418. }
  419. delay = (12.5f * ptr->delay + 37.5f) * ptr->sample_rate / 1000.0f;
  420. fpos = ptr->buflen_L - depth * (1.0f - ptr->pitchmod) - delay - 1.0f;
  421. n = floorf(fpos);
  422. rem = fpos - n;
  423. s_a_L = read_buffer(ptr->ring_L, ptr->buflen_L,
  424. ptr->pos_L, (unsigned long) n);
  425. s_b_L = read_buffer(ptr->ring_L, ptr->buflen_L,
  426. ptr->pos_L, (unsigned long) n + 1);
  427. s_a_R = read_buffer(ptr->ring_R, ptr->buflen_R,
  428. ptr->pos_R, (unsigned long) n);
  429. s_b_R = read_buffer(ptr->ring_R, ptr->buflen_R,
  430. ptr->pos_R, (unsigned long) n + 1);
  431. drystream_L = drylevel * in_L;
  432. drystream_R = drylevel * in_R;
  433. wetstream_L = wetlevel * ((1 - rem) * s_a_L + rem * s_b_L);
  434. wetstream_R = wetlevel * ((1 - rem) * s_a_R + rem * s_b_R);
  435. out_L = dryposl * drystream_L + (1.0f - dryposr) * drystream_R +
  436. wetposl * wetstream_L + (1.0f - wetposr) * wetstream_R;
  437. out_R = (1.0f - dryposl) * drystream_L + dryposr * drystream_R +
  438. (1.0f - wetposl) * wetstream_L + wetposr * wetstream_R;
  439. *(output_L++) += ptr->run_adding_gain * out_L;
  440. *(output_R++) += ptr->run_adding_gain * out_R;
  441. }
  442. }
  443. /* Throw away a Doubler effect instance. */
  444. void
  445. cleanup_Doubler(LADSPA_Handle Instance) {
  446. Doubler * ptr = (Doubler *)Instance;
  447. free(ptr->ring_L);
  448. free(ptr->ring_R);
  449. free(ptr->ring_pnoise);
  450. free(ptr->ring_dnoise);
  451. free(Instance);
  452. }
  453. LADSPA_Descriptor * stereo_descriptor = NULL;
  454. /* __attribute__((constructor)) tap_init() is called automatically when the plugin library is first
  455. loaded. */
  456. void
  457. __attribute__((constructor)) tap_init() {
  458. char ** port_names;
  459. LADSPA_PortDescriptor * port_descriptors;
  460. LADSPA_PortRangeHint * port_range_hints;
  461. if ((stereo_descriptor =
  462. (LADSPA_Descriptor *)malloc(sizeof(LADSPA_Descriptor))) == NULL)
  463. exit(1);
  464. stereo_descriptor->UniqueID = ID_STEREO;
  465. stereo_descriptor->Label = strdup("tap_doubler");
  466. stereo_descriptor->Properties = 0;
  467. stereo_descriptor->Name = strdup("TAP Fractal Doubler");
  468. stereo_descriptor->Maker = strdup("Tom Szilagyi");
  469. stereo_descriptor->Copyright = strdup("GPL");
  470. stereo_descriptor->PortCount = PORTCOUNT_STEREO;
  471. if ((port_descriptors =
  472. (LADSPA_PortDescriptor *)calloc(PORTCOUNT_STEREO, sizeof(LADSPA_PortDescriptor))) == NULL)
  473. exit(1);
  474. stereo_descriptor->PortDescriptors = (const LADSPA_PortDescriptor *)port_descriptors;
  475. port_descriptors[TIME] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  476. port_descriptors[PITCH] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  477. port_descriptors[DRYLEVEL] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  478. port_descriptors[DRYPOSL] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  479. port_descriptors[DRYPOSR] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  480. port_descriptors[WETLEVEL] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  481. port_descriptors[WETPOSL] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  482. port_descriptors[WETPOSR] = LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL;
  483. port_descriptors[INPUT_L] = LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO;
  484. port_descriptors[INPUT_R] = LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO;
  485. port_descriptors[OUTPUT_L] = LADSPA_PORT_OUTPUT | LADSPA_PORT_AUDIO;
  486. port_descriptors[OUTPUT_R] = LADSPA_PORT_OUTPUT | LADSPA_PORT_AUDIO;
  487. if ((port_names =
  488. (char **)calloc(PORTCOUNT_STEREO, sizeof(char *))) == NULL)
  489. exit(1);
  490. stereo_descriptor->PortNames = (const char **)port_names;
  491. port_names[TIME] = strdup("Time Tracking");
  492. port_names[PITCH] = strdup("Pitch Tracking");
  493. port_names[DRYLEVEL] = strdup("Dry Level [dB]");
  494. port_names[DRYPOSL] = strdup("Dry Left Position");
  495. port_names[DRYPOSR] = strdup("Dry Right Position");
  496. port_names[WETLEVEL] = strdup("Wet Level [dB]");
  497. port_names[WETPOSL] = strdup("Wet Left Position");
  498. port_names[WETPOSR] = strdup("Wet Right Position");
  499. port_names[INPUT_L] = strdup("Input_L");
  500. port_names[INPUT_R] = strdup("Input_R");
  501. port_names[OUTPUT_L] = strdup("Output_L");
  502. port_names[OUTPUT_R] = strdup("Output_R");
  503. if ((port_range_hints =
  504. ((LADSPA_PortRangeHint *)calloc(PORTCOUNT_STEREO, sizeof(LADSPA_PortRangeHint)))) == NULL)
  505. exit(1);
  506. stereo_descriptor->PortRangeHints = (const LADSPA_PortRangeHint *)port_range_hints;
  507. port_range_hints[TIME].HintDescriptor =
  508. (LADSPA_HINT_BOUNDED_BELOW |
  509. LADSPA_HINT_BOUNDED_ABOVE |
  510. LADSPA_HINT_DEFAULT_MIDDLE);
  511. port_range_hints[PITCH].HintDescriptor =
  512. (LADSPA_HINT_BOUNDED_BELOW |
  513. LADSPA_HINT_BOUNDED_ABOVE |
  514. LADSPA_HINT_DEFAULT_MIDDLE);
  515. port_range_hints[DRYLEVEL].HintDescriptor =
  516. (LADSPA_HINT_BOUNDED_BELOW |
  517. LADSPA_HINT_BOUNDED_ABOVE |
  518. LADSPA_HINT_DEFAULT_0);
  519. port_range_hints[DRYPOSL].HintDescriptor =
  520. (LADSPA_HINT_BOUNDED_BELOW |
  521. LADSPA_HINT_BOUNDED_ABOVE |
  522. LADSPA_HINT_DEFAULT_MINIMUM);
  523. port_range_hints[DRYPOSR].HintDescriptor =
  524. (LADSPA_HINT_BOUNDED_BELOW |
  525. LADSPA_HINT_BOUNDED_ABOVE |
  526. LADSPA_HINT_DEFAULT_MAXIMUM);
  527. port_range_hints[WETLEVEL].HintDescriptor =
  528. (LADSPA_HINT_BOUNDED_BELOW |
  529. LADSPA_HINT_BOUNDED_ABOVE |
  530. LADSPA_HINT_DEFAULT_0);
  531. port_range_hints[WETPOSL].HintDescriptor =
  532. (LADSPA_HINT_BOUNDED_BELOW |
  533. LADSPA_HINT_BOUNDED_ABOVE |
  534. LADSPA_HINT_DEFAULT_MINIMUM);
  535. port_range_hints[WETPOSR].HintDescriptor =
  536. (LADSPA_HINT_BOUNDED_BELOW |
  537. LADSPA_HINT_BOUNDED_ABOVE |
  538. LADSPA_HINT_DEFAULT_MAXIMUM);
  539. port_range_hints[TIME].LowerBound = 0.0f;
  540. port_range_hints[TIME].UpperBound = 1.0f;
  541. port_range_hints[PITCH].LowerBound = 0.0f;
  542. port_range_hints[PITCH].UpperBound = 1.0f;
  543. port_range_hints[DRYLEVEL].LowerBound = -90.0f;
  544. port_range_hints[DRYLEVEL].UpperBound = +20.0f;
  545. port_range_hints[DRYPOSL].LowerBound = 0.0f;
  546. port_range_hints[DRYPOSL].UpperBound = 1.0f;
  547. port_range_hints[DRYPOSR].LowerBound = 0.0f;
  548. port_range_hints[DRYPOSR].UpperBound = 1.0f;
  549. port_range_hints[WETLEVEL].LowerBound = -90.0f;
  550. port_range_hints[WETLEVEL].UpperBound = +20.0f;
  551. port_range_hints[WETPOSL].LowerBound = 0.0f;
  552. port_range_hints[WETPOSL].UpperBound = 1.0f;
  553. port_range_hints[WETPOSR].LowerBound = 0.0f;
  554. port_range_hints[WETPOSR].UpperBound = 1.0f;
  555. port_range_hints[INPUT_L].HintDescriptor = 0;
  556. port_range_hints[INPUT_R].HintDescriptor = 0;
  557. port_range_hints[OUTPUT_L].HintDescriptor = 0;
  558. port_range_hints[OUTPUT_R].HintDescriptor = 0;
  559. stereo_descriptor->instantiate = instantiate_Doubler;
  560. stereo_descriptor->connect_port = connect_port_Doubler;
  561. stereo_descriptor->activate = activate_Doubler;
  562. stereo_descriptor->run = run_Doubler;
  563. stereo_descriptor->run_adding = run_adding_Doubler;
  564. stereo_descriptor->set_run_adding_gain = set_run_adding_gain_Doubler;
  565. stereo_descriptor->deactivate = NULL;
  566. stereo_descriptor->cleanup = cleanup_Doubler;
  567. }
  568. void
  569. delete_descriptor(LADSPA_Descriptor * descriptor) {
  570. unsigned long index;
  571. if (descriptor) {
  572. free((char *)descriptor->Label);
  573. free((char *)descriptor->Name);
  574. free((char *)descriptor->Maker);
  575. free((char *)descriptor->Copyright);
  576. free((LADSPA_PortDescriptor *)descriptor->PortDescriptors);
  577. for (index = 0; index < descriptor->PortCount; index++)
  578. free((char *)(descriptor->PortNames[index]));
  579. free((char **)descriptor->PortNames);
  580. free((LADSPA_PortRangeHint *)descriptor->PortRangeHints);
  581. free(descriptor);
  582. }
  583. }
  584. /* __attribute__((destructor)) tap_fini() is called automatically when the library is unloaded. */
  585. void
  586. __attribute__((destructor)) tap_fini() {
  587. delete_descriptor(stereo_descriptor);
  588. }
  589. /* Return a descriptor of the requested plugin type. */
  590. const LADSPA_Descriptor *
  591. ladspa_descriptor(unsigned long Index) {
  592. switch (Index) {
  593. case 0:
  594. return stereo_descriptor;
  595. default:
  596. return NULL;
  597. }
  598. }