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.

WobbleJuicePlugin.cpp 6.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243
  1. /*
  2. * Wobble Juice Plugin
  3. * Copyright (C) 2014 Andre Sklenar <andre.sklenar@gmail.com>, www.juicelab.cz
  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 doc/GPL.txt file.
  16. */
  17. #include "WobbleJuicePlugin.hpp"
  18. START_NAMESPACE_DISTRHO
  19. // -----------------------------------------------------------------------
  20. WobbleJuicePlugin::WobbleJuicePlugin()
  21. : Plugin(paramCount, 1, 0) // 1 program, 0 states
  22. {
  23. // set default values
  24. d_setProgram(0);
  25. }
  26. // -----------------------------------------------------------------------
  27. // Init
  28. void WobbleJuicePlugin::d_initParameter(uint32_t index, Parameter& parameter)
  29. {
  30. switch (index)
  31. {
  32. case paramDivision:
  33. parameter.hints = PARAMETER_IS_AUTOMABLE|PARAMETER_IS_INTEGER;
  34. parameter.name = "Division";
  35. parameter.symbol = "div";
  36. parameter.unit = "x";
  37. parameter.ranges.def = 4.0f;
  38. parameter.ranges.min = 1.0f;
  39. parameter.ranges.max = 16.0f;
  40. break;
  41. case paramReso:
  42. parameter.hints = PARAMETER_IS_AUTOMABLE;
  43. parameter.name = "Resonance";
  44. parameter.symbol = "reso";
  45. parameter.unit = "";
  46. parameter.ranges.def = 0.1f;
  47. parameter.ranges.min = 0.0f;
  48. parameter.ranges.max = 0.2f;
  49. break;
  50. case paramRange:
  51. parameter.hints = PARAMETER_IS_AUTOMABLE;
  52. parameter.name = "Range";
  53. parameter.symbol = "rng";
  54. parameter.unit = "Hz";
  55. parameter.ranges.def = 16000.0f;
  56. parameter.ranges.min = 500.0f;
  57. parameter.ranges.max = 16000.0f;
  58. break;
  59. case paramPhase:
  60. parameter.hints = PARAMETER_IS_AUTOMABLE;
  61. parameter.name = "Phase";
  62. parameter.symbol = "phs";
  63. parameter.unit = "Deg";
  64. parameter.ranges.def = 0.0f;
  65. parameter.ranges.min = -1.0f;
  66. parameter.ranges.max = 1.0f;
  67. break;
  68. case paramWave:
  69. parameter.hints = PARAMETER_IS_AUTOMABLE;
  70. parameter.name = "Wave";
  71. parameter.symbol = "wav";
  72. parameter.unit = "";
  73. parameter.ranges.def = 2.0f;
  74. parameter.ranges.min = 1.0f;
  75. parameter.ranges.max = 4.0f;
  76. break;
  77. case paramDrive:
  78. parameter.hints = PARAMETER_IS_AUTOMABLE;
  79. parameter.name = "Drive";
  80. parameter.symbol = "drv";
  81. parameter.unit = "";
  82. parameter.ranges.def = 0.5f;
  83. parameter.ranges.min = 0.0f;
  84. parameter.ranges.max = 1.0f;
  85. break;
  86. }
  87. }
  88. void WobbleJuicePlugin::d_initProgramName(uint32_t index, d_string& programName)
  89. {
  90. if (index != 0)
  91. return;
  92. programName = "Default";
  93. }
  94. // -----------------------------------------------------------------------
  95. // Internal data
  96. float WobbleJuicePlugin::d_getParameterValue(uint32_t index) const
  97. {
  98. switch (index)
  99. {
  100. case paramDivision:
  101. return division;
  102. case paramReso:
  103. return reso;
  104. case paramRange:
  105. return range;
  106. case paramPhase:
  107. return phase;
  108. case paramWave:
  109. return wave;
  110. case paramDrive:
  111. return drive;
  112. default:
  113. return 0.0f;
  114. }
  115. }
  116. void WobbleJuicePlugin::d_setParameterValue(uint32_t index, float value)
  117. {
  118. switch (index)
  119. {
  120. case paramDivision:
  121. division = value;
  122. break;
  123. case paramReso:
  124. reso = value;
  125. break;
  126. case paramRange:
  127. range = value;
  128. break;
  129. case paramPhase:
  130. phase = value;
  131. break;
  132. case paramWave:
  133. wave = value;
  134. break;
  135. case paramDrive:
  136. drive = value;
  137. break;
  138. }
  139. }
  140. void WobbleJuicePlugin::d_setProgram(uint32_t index)
  141. {
  142. if (index != 0)
  143. return;
  144. /* Default parameter values */
  145. division = 4.0f;
  146. reso = 0.1f;
  147. range = 16000.0f;
  148. phase = 0.0f;
  149. wave = 2.0f;
  150. drive = 0.5f;
  151. /* Default variable values */
  152. bar=tick=tickOffset=percentage=phaseOffset=currentPhaseL=0.0f;
  153. currentPhaseR=posL=posR=cutoffL=cutoffR=0.0f;
  154. waveType=2.0f;
  155. /* reset filter values */
  156. d_activate();
  157. }
  158. // -----------------------------------------------------------------------
  159. // Process
  160. void WobbleJuicePlugin::d_activate()
  161. {
  162. sinePos = 0.0;
  163. }
  164. void WobbleJuicePlugin::d_run(const float** inputs, float** outputs, uint32_t frames)
  165. {
  166. //fetch the timepos struct from host;
  167. const TimePos& time(d_getTimePos());
  168. /* sample count for one bar */
  169. bar = ((120.0/(time.bbt.valid ? time.bbt.beatsPerMinute : 120.0))*(d_getSampleRate())); //ONE, two, three, four
  170. tick = bar/(std::round(division)); //size of one target wob
  171. phaseOffset = phase*M_PI; //2pi = 1 whole cycle
  172. /* if rolling then sync to timepos */
  173. if (time.playing)
  174. {
  175. tickOffset = time.frame-std::floor(time.frame/tick)*tick; //how much after last tick
  176. if (tickOffset!=0) {
  177. //TODO: why do we need this??
  178. percentage = tickOffset/tick;
  179. } else {
  180. percentage = 0;
  181. }
  182. sinePos = (M_PI*2)*percentage;
  183. if (sinePos>2*M_PI) {
  184. //TODO: can this ever happen??
  185. sinePos = 0;
  186. }
  187. }
  188. /* else just keep on wobblin' */
  189. else
  190. {
  191. sinePos += (M_PI)/(tick/2000); //wtf, but works
  192. if (sinePos>2*M_PI) {
  193. sinePos = 0;
  194. }
  195. }
  196. /* phase of 0..1 filter = 500..16k */
  197. currentPhaseL = getBlendedPhase(sinePos+phaseOffset, wave);
  198. currentPhaseR = getBlendedPhase(sinePos-phaseOffset, wave);
  199. /* logarithmic */
  200. cutoffL = std::exp((std::log(range)-std::log(500))*currentPhaseL+std::log(500));
  201. cutoffR = std::exp((std::log(range)-std::log(500))*currentPhaseR+std::log(500));
  202. //output filtered signal
  203. filterL.recalc(cutoffL, reso*4, d_getSampleRate(), drive);
  204. filterR.recalc(cutoffR, reso*4, d_getSampleRate(), drive);
  205. filterL.process(frames, inputs[0], outputs[0]);
  206. filterR.process(frames, inputs[1], outputs[1]);
  207. }
  208. // -----------------------------------------------------------------------
  209. Plugin* createPlugin()
  210. {
  211. return new WobbleJuicePlugin();
  212. }
  213. // -----------------------------------------------------------------------
  214. END_NAMESPACE_DISTRHO