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.

151 lines
4.7KB

  1. //============================================================================================================
  2. //!
  3. //! \file Fade-G1.cpp
  4. //!
  5. //! \brief Fade-G1 is a two input six voice one-dimensional fader.
  6. //!
  7. //============================================================================================================
  8. #include "Gratrix.hpp"
  9. namespace rack_plugin_Gratrix {
  10. //============================================================================================================
  11. //! \brief The module.
  12. struct GtxModule_Fade_G1 : Module
  13. {
  14. enum ParamIds {
  15. BLEND12_PARAM,
  16. NUM_PARAMS
  17. };
  18. enum InputIds {
  19. BLEND12_INPUT,
  20. IN1_INPUT,
  21. IN2_INPUT,
  22. NUM_INPUTS,
  23. OFF_INPUTS = IN1_INPUT
  24. };
  25. enum OutputIds {
  26. OUT1_OUTPUT,
  27. OUT2_OUTPUT,
  28. NUM_OUTPUTS,
  29. OFF_OUTPUTS = OUT1_OUTPUT
  30. };
  31. enum LightIds {
  32. IN_1_GREEN, IN_1_RED,
  33. IN_2_GREEN, IN_2_RED,
  34. OUT_1_GREEN, OUT_1_RED,
  35. OUT_2_GREEN, OUT_2_RED,
  36. NUM_LIGHTS
  37. };
  38. GtxModule_Fade_G1()
  39. :
  40. Module(NUM_PARAMS,
  41. (GTX__N+1) * (NUM_INPUTS - OFF_INPUTS ) + OFF_INPUTS,
  42. (GTX__N ) * (NUM_OUTPUTS - OFF_OUTPUTS) + OFF_OUTPUTS,
  43. NUM_LIGHTS)
  44. {
  45. lights[IN_1_GREEN].value = 0.0f; lights[IN_1_RED].value = 1.0f;
  46. lights[IN_2_GREEN].value = 1.0f; lights[IN_2_RED].value = 0.0f;
  47. }
  48. static constexpr std::size_t imap(std::size_t port, std::size_t bank)
  49. {
  50. return (port < OFF_INPUTS) ? port : port + bank * (NUM_INPUTS - OFF_INPUTS);
  51. }
  52. static constexpr std::size_t omap(std::size_t port, std::size_t bank)
  53. {
  54. return port + bank * NUM_OUTPUTS;
  55. }
  56. void step() override
  57. {
  58. float blend12 = params[BLEND12_PARAM].value;
  59. if (inputs[BLEND12_INPUT].active) blend12 *= clamp(inputs[BLEND12_INPUT].normalize(10.0f) / 10.0f, 0.0f, 1.0f);
  60. for (std::size_t i=0; i<GTX__N; ++i)
  61. {
  62. float input1 = inputs[imap(IN1_INPUT, i)].active ? inputs[imap(IN1_INPUT, i)].value : inputs[imap(IN1_INPUT, GTX__N)].value;
  63. float input2 = inputs[imap(IN2_INPUT, i)].active ? inputs[imap(IN2_INPUT, i)].value : inputs[imap(IN2_INPUT, GTX__N)].value;
  64. float delta12 = blend12 * (input2 - input1);
  65. outputs[omap(OUT1_OUTPUT, i)].value = input1 + delta12;
  66. outputs[omap(OUT2_OUTPUT, i)].value = input2 - delta12;
  67. }
  68. lights[OUT_1_GREEN].value = lights[OUT_2_RED].value = blend12;
  69. lights[OUT_2_GREEN].value = lights[OUT_1_RED].value = 1.0f - blend12;
  70. }
  71. };
  72. //============================================================================================================
  73. //! \brief The widget.
  74. struct GtxWidget_Fade_G1 : ModuleWidget
  75. {
  76. GtxWidget_Fade_G1(GtxModule_Fade_G1 *module) : ModuleWidget(module)
  77. {
  78. GTX__WIDGET();
  79. box.size = Vec(12*15, 380);
  80. #if GTX__SAVE_SVG
  81. {
  82. PanelGen pg(assetPlugin(plugin, "build/res/Fade-G1.svg"), box.size, "FADE-G1");
  83. // ― is a horizontal bar see https://en.wikipedia.org/wiki/Dash#Horizontal_bar
  84. pg.prt_in2(0, 0, "CV 1―2"); pg.nob_big(1, 0, "1―2");
  85. pg.bus_in(0, 1, "IN 1"); pg.bus_out(1, 1, "OUT 1");
  86. pg.bus_in(0, 2, "IN 2"); pg.bus_out(1, 2, "OUT 2");
  87. }
  88. #endif
  89. setPanel(SVG::load(assetPlugin(plugin, "res/Fade-G1.svg")));
  90. addChild(Widget::create<ScrewSilver>(Vec(15, 0)));
  91. addChild(Widget::create<ScrewSilver>(Vec(box.size.x-30, 0)));
  92. addChild(Widget::create<ScrewSilver>(Vec(15, 365)));
  93. addChild(Widget::create<ScrewSilver>(Vec(box.size.x-30, 365)));
  94. addParam(createParamGTX<KnobFreeHug>(Vec(fx(1), fy(0)), module, GtxModule_Fade_G1::BLEND12_PARAM, 0.0f, 1.0f, 0.0f));
  95. addInput(createInputGTX<PortInMed>(Vec(fx(0), fy(0)), module, GtxModule_Fade_G1::BLEND12_INPUT));
  96. for (std::size_t i=0; i<GTX__N; ++i)
  97. {
  98. addInput(createInputGTX<PortInMed>(Vec(px(0, i), py(1, i)), module, GtxModule_Fade_G1::imap(GtxModule_Fade_G1::IN1_INPUT, i)));
  99. addInput(createInputGTX<PortInMed>(Vec(px(0, i), py(2, i)), module, GtxModule_Fade_G1::imap(GtxModule_Fade_G1::IN2_INPUT, i)));
  100. addOutput(createOutputGTX<PortOutMed>(Vec(px(1, i), py(1, i)), module, GtxModule_Fade_G1::omap(GtxModule_Fade_G1::OUT1_OUTPUT, i)));
  101. addOutput(createOutputGTX<PortOutMed>(Vec(px(1, i), py(2, i)), module, GtxModule_Fade_G1::omap(GtxModule_Fade_G1::OUT2_OUTPUT, i)));
  102. }
  103. addInput(createInputGTX<PortInMed>(Vec(gx(0), gy(1)), module, GtxModule_Fade_G1::imap(GtxModule_Fade_G1::IN1_INPUT, GTX__N)));
  104. addInput(createInputGTX<PortInMed>(Vec(gx(0), gy(2)), module, GtxModule_Fade_G1::imap(GtxModule_Fade_G1::IN2_INPUT, GTX__N)));
  105. for (std::size_t i=0, x=0; x<2; ++x)
  106. {
  107. for (std::size_t y=0; y<2; ++y)
  108. {
  109. addChild(ModuleLightWidget::create<SmallLight<GreenRedLight>>(l_s(gx(x)+28, gy(y+1)-47.5), module, i)); i+=2;
  110. }
  111. }
  112. }
  113. };
  114. } // namespace rack_plugin_Gratrix
  115. using namespace rack_plugin_Gratrix;
  116. RACK_PLUGIN_MODEL_INIT(Gratrix, Fade_G1) {
  117. Model *model = Model::create<GtxModule_Fade_G1, GtxWidget_Fade_G1>("Gratrix", "Fade-G1", "Fade-G1", MIXER_TAG); // right tag?
  118. return model;
  119. }