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.

124 lines
4.1KB

  1. #include "plugin.hpp"
  2. struct DualAtenuverter : Module {
  3. enum ParamIds {
  4. ATEN1_PARAM,
  5. OFFSET1_PARAM,
  6. ATEN2_PARAM,
  7. OFFSET2_PARAM,
  8. NUM_PARAMS
  9. };
  10. enum InputIds {
  11. IN1_INPUT,
  12. IN2_INPUT,
  13. NUM_INPUTS
  14. };
  15. enum OutputIds {
  16. OUT1_OUTPUT,
  17. OUT2_OUTPUT,
  18. NUM_OUTPUTS
  19. };
  20. enum LightIds {
  21. ENUMS(OUT1_LIGHT, 3),
  22. ENUMS(OUT2_LIGHT, 3),
  23. NUM_LIGHTS
  24. };
  25. DualAtenuverter() {
  26. config(NUM_PARAMS, NUM_INPUTS, NUM_OUTPUTS, NUM_LIGHTS);
  27. configParam(ATEN1_PARAM, -1.0, 1.0, 0.0, "Ch 1 gain");
  28. configParam(OFFSET1_PARAM, -10.0, 10.0, 0.0, "Ch 1 offset", " V");
  29. configParam(ATEN2_PARAM, -1.0, 1.0, 0.0, "Ch 2 gain");
  30. configParam(OFFSET2_PARAM, -10.0, 10.0, 0.0, "Ch 2 offset", " V");
  31. configBypass(IN1_INPUT, OUT1_OUTPUT);
  32. configBypass(IN2_INPUT, OUT2_OUTPUT);
  33. }
  34. void process(const ProcessArgs& args) override {
  35. using simd::float_4;
  36. float_4 out1[4] = {};
  37. float_4 out2[4] = {};
  38. int channels1 = inputs[IN1_INPUT].getChannels();
  39. channels1 = channels1 > 0 ? channels1 : 1;
  40. int channels2 = inputs[IN2_INPUT].getChannels();
  41. channels2 = channels2 > 0 ? channels2 : 1;
  42. float att1 = params[ATEN1_PARAM].getValue();
  43. float att2 = params[ATEN2_PARAM].getValue();
  44. float offset1 = params[OFFSET1_PARAM].getValue();
  45. float offset2 = params[OFFSET2_PARAM].getValue();
  46. for (int c = 0; c < channels1; c += 4) {
  47. out1[c / 4] = clamp(inputs[IN1_INPUT].getVoltageSimd<float_4>(c) * att1 + offset1, -10.f, 10.f);
  48. }
  49. for (int c = 0; c < channels2; c += 4) {
  50. out2[c / 4] = clamp(inputs[IN2_INPUT].getVoltageSimd<float_4>(c) * att2 + offset2, -10.f, 10.f);
  51. }
  52. outputs[OUT1_OUTPUT].setChannels(channels1);
  53. outputs[OUT2_OUTPUT].setChannels(channels2);
  54. for (int c = 0; c < channels1; c += 4) {
  55. outputs[OUT1_OUTPUT].setVoltageSimd(out1[c / 4], c);
  56. }
  57. for (int c = 0; c < channels2; c += 4) {
  58. outputs[OUT2_OUTPUT].setVoltageSimd(out2[c / 4], c);
  59. }
  60. float light1 = outputs[OUT1_OUTPUT].getVoltageSum() / channels1;
  61. float light2 = outputs[OUT2_OUTPUT].getVoltageSum() / channels2;
  62. if (channels1 == 1) {
  63. lights[OUT1_LIGHT + 0].setSmoothBrightness(light1 / 5.f, args.sampleTime);
  64. lights[OUT1_LIGHT + 1].setSmoothBrightness(-light1 / 5.f, args.sampleTime);
  65. lights[OUT1_LIGHT + 2].setBrightness(0.0f);
  66. }
  67. else {
  68. lights[OUT1_LIGHT + 0].setBrightness(0.0f);
  69. lights[OUT1_LIGHT + 1].setBrightness(0.0f);
  70. lights[OUT1_LIGHT + 2].setBrightness(10.0f);
  71. }
  72. if (channels2 == 1) {
  73. lights[OUT2_LIGHT + 0].setSmoothBrightness(light2 / 5.f, args.sampleTime);
  74. lights[OUT2_LIGHT + 1].setSmoothBrightness(-light2 / 5.f, args.sampleTime);
  75. lights[OUT2_LIGHT + 2].setBrightness(0.0f);
  76. }
  77. else {
  78. lights[OUT2_LIGHT + 0].setBrightness(0.0f);
  79. lights[OUT2_LIGHT + 1].setBrightness(0.0f);
  80. lights[OUT2_LIGHT + 2].setBrightness(10.0f);
  81. }
  82. }
  83. };
  84. struct DualAtenuverterWidget : ModuleWidget {
  85. DualAtenuverterWidget(DualAtenuverter* module) {
  86. setModule(module);
  87. setPanel(APP->window->loadSvg(asset::plugin(pluginInstance, "res/DualAtenuverter.svg")));
  88. addChild(createWidget<Knurlie>(Vec(15, 0)));
  89. addChild(createWidget<Knurlie>(Vec(15, 365)));
  90. addParam(createParam<Davies1900hWhiteKnob>(Vec(20, 33), module, DualAtenuverter::ATEN1_PARAM));
  91. addParam(createParam<Davies1900hRedKnob>(Vec(20, 91), module, DualAtenuverter::OFFSET1_PARAM));
  92. addParam(createParam<Davies1900hWhiteKnob>(Vec(20, 201), module, DualAtenuverter::ATEN2_PARAM));
  93. addParam(createParam<Davies1900hRedKnob>(Vec(20, 260), module, DualAtenuverter::OFFSET2_PARAM));
  94. addInput(createInput<BefacoInputPort>(Vec(7, 152), module, DualAtenuverter::IN1_INPUT));
  95. addOutput(createOutput<BefacoOutputPort>(Vec(43, 152), module, DualAtenuverter::OUT1_OUTPUT));
  96. addInput(createInput<BefacoInputPort>(Vec(7, 319), module, DualAtenuverter::IN2_INPUT));
  97. addOutput(createOutput<BefacoOutputPort>(Vec(43, 319), module, DualAtenuverter::OUT2_OUTPUT));
  98. addChild(createLight<MediumLight<RedGreenBlueLight>>(Vec(33, 143), module, DualAtenuverter::OUT1_LIGHT));
  99. addChild(createLight<MediumLight<RedGreenBlueLight>>(Vec(33, 311), module, DualAtenuverter::OUT2_LIGHT));
  100. }
  101. };
  102. Model* modelDualAtenuverter = createModel<DualAtenuverter, DualAtenuverterWidget>("DualAtenuverter");