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.

92 lines
2.3KB

  1. #include "Befaco.hpp"
  2. struct SlewLimiter : Module {
  3. enum ParamIds {
  4. SHAPE_PARAM,
  5. RISE_PARAM,
  6. FALL_PARAM,
  7. NUM_PARAMS
  8. };
  9. enum InputIds {
  10. RISE_INPUT,
  11. FALL_INPUT,
  12. IN_INPUT,
  13. NUM_INPUTS
  14. };
  15. enum OutputIds {
  16. OUT_OUTPUT,
  17. NUM_OUTPUTS
  18. };
  19. float output = 0.0;
  20. SlewLimiter();
  21. void step();
  22. };
  23. SlewLimiter::SlewLimiter() {
  24. params.resize(NUM_PARAMS);
  25. inputs.resize(NUM_INPUTS);
  26. outputs.resize(NUM_OUTPUTS);
  27. }
  28. void SlewLimiter::step() {
  29. float input = getf(inputs[IN_INPUT]);
  30. float shape = params[SHAPE_PARAM];
  31. // minimum and maximum slopes in volts per second
  32. const float slewMin = 0.1;
  33. const float slewMax = 40000.0;
  34. // Amount of extra slew per voltage difference
  35. const float shapeScale = 1/10.0;
  36. // Rise
  37. if (input > output) {
  38. float rise = getf(inputs[RISE_INPUT]) + params[RISE_PARAM];
  39. float slew = slewMax * powf(slewMin / slewMax, rise);
  40. output += slew * crossf(1.0, shapeScale * (input - output), shape) / gSampleRate;
  41. if (output > input)
  42. output = input;
  43. }
  44. // Fall
  45. else if (input < output) {
  46. float fall = getf(inputs[FALL_INPUT]) + params[FALL_PARAM];
  47. float slew = slewMax * powf(slewMin / slewMax, fall);
  48. output -= slew * crossf(1.0, shapeScale * (output - input), shape) / gSampleRate;
  49. if (output < input)
  50. output = input;
  51. }
  52. setf(outputs[OUT_OUTPUT], output);
  53. }
  54. SlewLimiterWidget::SlewLimiterWidget() {
  55. SlewLimiter *module = new SlewLimiter();
  56. setModule(module);
  57. box.size = Vec(15*6, 380);
  58. {
  59. Panel *panel = new DarkPanel();
  60. panel->box.size = box.size;
  61. panel->backgroundImage = Image::load("plugins/Befaco/res/Slew Limiter.png");
  62. addChild(panel);
  63. }
  64. addChild(createScrew<BlackScrew>(Vec(15, 0)));
  65. addChild(createScrew<BlackScrew>(Vec(15, 365)));
  66. addParam(createParam<Davies1900hWhiteKnob>(Vec(26, 39), module, SlewLimiter::SHAPE_PARAM, 0.0, 1.0, 0.0));
  67. addParam(createParam<BefacoSlidePot>(Vec(17, 100), module, SlewLimiter::RISE_PARAM, 0.0, 1.0, 0.0));
  68. addParam(createParam<BefacoSlidePot>(Vec(61, 100), module, SlewLimiter::FALL_PARAM, 0.0, 1.0, 0.0));
  69. addInput(createInput<PJ3410Port>(Vec(6, 270), module, SlewLimiter::RISE_INPUT));
  70. addInput(createInput<PJ3410Port>(Vec(52, 270), module, SlewLimiter::FALL_INPUT));
  71. addInput(createInput<PJ3410Port>(Vec(6, 320), module, SlewLimiter::IN_INPUT));
  72. addOutput(createOutput<PJ3410Port>(Vec(52, 320), module, SlewLimiter::OUT_OUTPUT));
  73. }