BogaudioModules

BogaudioModules for VCV Rack
Log | Files | Refs | README | LICENSE

commit 738f563a921bc47317c2616f14853f810bbff45e
parent cd12f5f743a7df5d167b6a0d6fb2265b1554fc67
Author: Matt Demanett <matt@demanett.net>
Date:   Mon, 30 Sep 2019 23:57:18 -0400

Poly: optional poly channel spread from input 1 on MIX8/MIX4. #66

Diffstat:
Msrc/Mix1.cpp | 2+-
Msrc/Mix1.hpp | 1-
Msrc/Mix4.cpp | 108+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++------------------
Msrc/Mix4.hpp | 23+++++++++++------------
Msrc/Mix8.cpp | 136++++++++++++++++++++++++++++++++++++++++++++++++++-----------------------------
Msrc/Mix8.hpp | 39+++++++++++++++------------------------
Msrc/mixer.cpp | 9++-------
Msrc/mixer.hpp | 5+----
8 files changed, 201 insertions(+), 122 deletions(-)

diff --git a/src/Mix1.cpp b/src/Mix1.cpp @@ -6,7 +6,7 @@ void Mix1::sampleRateChange() { } void Mix1::processChannel(const ProcessArgs& args, int _c) { - _channel->next(false, false); + _channel->next(inputs[IN_INPUT].getVoltageSum(), false, false); outputs[OUT_OUTPUT].setVoltage(_channel->out); } diff --git a/src/Mix1.hpp b/src/Mix1.hpp @@ -44,7 +44,6 @@ struct Mix1 : BGModule { params[LEVEL_PARAM], params[LEVEL_PARAM], // not used params[MUTE_PARAM], - inputs[IN_INPUT], inputs[LEVEL_INPUT], inputs[LEVEL_INPUT], // not used 1000.0f, diff --git a/src/Mix4.cpp b/src/Mix4.cpp @@ -1,12 +1,26 @@ #include "Mix4.hpp" +#define POLY_OFFSET "poly_channel_offset" + +json_t* Mix4::dataToJson() { + json_t* root = json_object(); + json_object_set_new(root, POLY_OFFSET, json_integer(_polyChannelOffset)); + return root; +} + +void Mix4::dataFromJson(json_t* root) { + json_t* o = json_object_get(root, POLY_OFFSET); + if (o) { + _polyChannelOffset = json_integer_value(o); + } +} + void Mix4::sampleRateChange() { float sr = APP->engine->getSampleRate(); - _channel1->setSampleRate(sr); - _channel2->setSampleRate(sr); - _channel3->setSampleRate(sr); - _channel4->setSampleRate(sr); + for (int i = 0; i < 4; ++i) { + _channels[i]->setSampleRate(sr); + } _slewLimiter.setParams(sr, MixerChannel::levelSlewTimeMS, MixerChannel::maxDecibels - MixerChannel::minDecibels); _rms.setSampleRate(sr); } @@ -18,10 +32,27 @@ void Mix4::processChannel(const ProcessArgs& args, int _c) { params[MUTE2_PARAM].getValue() > 1.5f || params[MUTE3_PARAM].getValue() > 1.5f || params[MUTE4_PARAM].getValue() > 1.5f; - _channel1->next(stereo, solo); - _channel2->next(stereo, solo); - _channel3->next(stereo, solo); - _channel4->next(stereo, solo); + + { + float sample = 0.0f; + if (_polyChannelOffset >= 0) { + sample = inputs[IN1_INPUT].getPolyVoltage(_polyChannelOffset); + } else { + sample = inputs[IN1_INPUT].getVoltageSum(); + } + _channels[0]->next(sample, stereo, solo); + + for (int i = 1; i < 4; ++i) { + float sample = 0.0f; + if (inputs[IN1_INPUT + 3 * i].isConnected()) { + sample = inputs[IN1_INPUT + 3 * i].getVoltageSum(); + } + else if (_polyChannelOffset >= 0) { + sample = inputs[IN1_INPUT].getPolyVoltage(_polyChannelOffset + i); + } + _channels[i]->next(sample, stereo, solo); + } + } float level = Amplifier::minDecibels; if (params[MIX_MUTE_PARAM].getValue() < 0.5f) { @@ -35,29 +66,26 @@ void Mix4::processChannel(const ProcessArgs& args, int _c) { _amplifier.setLevel(_slewLimiter.next(level)); float mono = 0.0f; - mono += _channel1->out; - mono += _channel2->out; - mono += _channel3->out; - mono += _channel4->out; + for (int i = 0; i < 4; ++i) { + mono += _channels[i]->out; + } mono = _amplifier.next(mono); mono = _saturator.next(mono); _rmsLevel = _rms.next(mono) / 5.0f; if (stereo) { float left = 0.0f; - left += _channel1->left; - left += _channel2->left; - left += _channel3->left; - left += _channel4->left; + for (int i = 0; i < 4; ++i) { + left += _channels[i]->left; + } left = _amplifier.next(left); left = _saturator.next(left); outputs[L_OUTPUT].setVoltage(left); float right = 0.0f; - right += _channel1->right; - right += _channel2->right; - right += _channel3->right; - right += _channel4->right; + for (int i = 0; i < 4; ++i) { + right += _channels[i]->right; + } right = _amplifier.next(right); right = _saturator.next(right); outputs[R_OUTPUT].setVoltage(right); @@ -121,16 +149,16 @@ struct Mix4Widget : ModuleWidget { auto rOutputPosition = Vec(186.5, 325.0); // end generated by svg_widgets.rb - addSlider(level1ParamPosition, module, Mix4::LEVEL1_PARAM, module ? &module->_channel1->rms : NULL); + addSlider(level1ParamPosition, module, Mix4::LEVEL1_PARAM, module ? &module->_channels[0]->rms : NULL); addParam(createParam<Knob16>(pan1ParamPosition, module, Mix4::PAN1_PARAM)); addParam(createParam<SoloMuteButton>(mute1ParamPosition, module, Mix4::MUTE1_PARAM)); - addSlider(level2ParamPosition, module, Mix4::LEVEL2_PARAM, module ? &module->_channel2->rms : NULL); + addSlider(level2ParamPosition, module, Mix4::LEVEL2_PARAM, module ? &module->_channels[1]->rms : NULL); addParam(createParam<Knob16>(pan2ParamPosition, module, Mix4::PAN2_PARAM)); addParam(createParam<SoloMuteButton>(mute2ParamPosition, module, Mix4::MUTE2_PARAM)); - addSlider(level3ParamPosition, module, Mix4::LEVEL3_PARAM, module ? &module->_channel3->rms : NULL); + addSlider(level3ParamPosition, module, Mix4::LEVEL3_PARAM, module ? &module->_channels[2]->rms : NULL); addParam(createParam<Knob16>(pan3ParamPosition, module, Mix4::PAN3_PARAM)); addParam(createParam<SoloMuteButton>(mute3ParamPosition, module, Mix4::MUTE3_PARAM)); - addSlider(level4ParamPosition, module, Mix4::LEVEL4_PARAM, module ? &module->_channel4->rms : NULL); + addSlider(level4ParamPosition, module, Mix4::LEVEL4_PARAM, module ? &module->_channels[3]->rms : NULL); addParam(createParam<Knob16>(pan4ParamPosition, module, Mix4::PAN4_PARAM)); addParam(createParam<SoloMuteButton>(mute4ParamPosition, module, Mix4::MUTE4_PARAM)); addSlider(mixParamPosition, module, Mix4::MIX_PARAM, module ? &module->_rmsLevel : NULL); @@ -161,6 +189,38 @@ struct Mix4Widget : ModuleWidget { } addParam(slider); } + + struct PolySpreadMenuItem : MenuItem { + Mix4* _module; + int _offset; + + PolySpreadMenuItem(Mix4* module, const char* label, int offset) + : _module(module) + , _offset(offset) + { + this->text = label; + } + + void onAction(const event::Action& e) override { + _module->_polyChannelOffset = _offset; + } + + void step() override { + MenuItem::step(); + rightText = _module->_polyChannelOffset == _offset ? "✔" : ""; + } + }; + + void appendContextMenu(Menu* menu) override { + Mix4* m = dynamic_cast<Mix4*>(module); + assert(m); + menu->addChild(new MenuLabel()); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: none", -1)); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: channels 1-4", 0)); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: channels 5-8", 4)); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: channels 9-12", 4)); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: channels 13-16", 4)); + } }; Model* modelMix4 = bogaudio::createModel<Mix4, Mix4Widget>("Bogaudio-Mix4", "Mix4", "4-channel mixer and panner", "Mixer", "Panning"); diff --git a/src/Mix4.hpp b/src/Mix4.hpp @@ -56,10 +56,8 @@ struct Mix4 : BGModule { NUM_LIGHTS }; - MixerChannel* _channel1; - MixerChannel* _channel2; - MixerChannel* _channel3; - MixerChannel* _channel4; + int _polyChannelOffset = -1; + MixerChannel* _channels[4] {}; Amplifier _amplifier; bogaudio::dsp::SlewLimiter _slewLimiter; Saturator _saturator; @@ -84,20 +82,21 @@ struct Mix4 : BGModule { configParam(MIX_PARAM, 0.0f, 1.0f, levelDefault, "Master level", " dB", 0.0f, MixerChannel::maxDecibels - MixerChannel::minDecibels, MixerChannel::minDecibels); configParam(MIX_MUTE_PARAM, 0.0f, 1.0f, 0.0f, "Master mute"); - _channel1 = new MixerChannel(params[LEVEL1_PARAM], params[PAN1_PARAM], params[MUTE1_PARAM], inputs[IN1_INPUT], inputs[CV1_INPUT], inputs[PAN1_INPUT]); - _channel2 = new MixerChannel(params[LEVEL2_PARAM], params[PAN2_PARAM], params[MUTE2_PARAM], inputs[IN2_INPUT], inputs[CV2_INPUT], inputs[PAN2_INPUT]); - _channel3 = new MixerChannel(params[LEVEL3_PARAM], params[PAN3_PARAM], params[MUTE3_PARAM], inputs[IN3_INPUT], inputs[CV3_INPUT], inputs[PAN3_INPUT]); - _channel4 = new MixerChannel(params[LEVEL4_PARAM], params[PAN4_PARAM], params[MUTE4_PARAM], inputs[IN4_INPUT], inputs[CV4_INPUT], inputs[PAN4_INPUT]); + _channels[0] = new MixerChannel(params[LEVEL1_PARAM], params[PAN1_PARAM], params[MUTE1_PARAM], inputs[CV1_INPUT], inputs[PAN1_INPUT]); + _channels[1] = new MixerChannel(params[LEVEL2_PARAM], params[PAN2_PARAM], params[MUTE2_PARAM], inputs[CV2_INPUT], inputs[PAN2_INPUT]); + _channels[2] = new MixerChannel(params[LEVEL3_PARAM], params[PAN3_PARAM], params[MUTE3_PARAM], inputs[CV3_INPUT], inputs[PAN3_INPUT]); + _channels[3] = new MixerChannel(params[LEVEL4_PARAM], params[PAN4_PARAM], params[MUTE4_PARAM], inputs[CV4_INPUT], inputs[PAN4_INPUT]); sampleRateChange(); _rms.setSensitivity(0.05f); } virtual ~Mix4() { - delete _channel1; - delete _channel2; - delete _channel3; - delete _channel4; + for (int i = 0; i < 4; ++i) { + delete _channels[i]; + } } + json_t* dataToJson() override; + void dataFromJson(json_t* root) override; void sampleRateChange() override; void processChannel(const ProcessArgs& args, int _c) override; }; diff --git a/src/Mix8.cpp b/src/Mix8.cpp @@ -1,18 +1,28 @@ #include "Mix8.hpp" +#define POLY_OFFSET "poly_channel_offset" + +json_t* Mix8::dataToJson() { + json_t* root = json_object(); + json_object_set_new(root, POLY_OFFSET, json_integer(_polyChannelOffset)); + return root; +} + +void Mix8::dataFromJson(json_t* root) { + json_t* o = json_object_get(root, POLY_OFFSET); + if (o) { + _polyChannelOffset = json_integer_value(o); + } +} + void Mix8::sampleRateChange() { float sr = APP->engine->getSampleRate(); - _channel1->setSampleRate(sr); - _channel2->setSampleRate(sr); - _channel3->setSampleRate(sr); - _channel4->setSampleRate(sr); - _channel5->setSampleRate(sr); - _channel6->setSampleRate(sr); - _channel7->setSampleRate(sr); - _channel8->setSampleRate(sr); + for (int i = 0; i < 8; ++i) { + _channels[i]->setSampleRate(sr); + } _slewLimiter.setParams(sr, MixerChannel::levelSlewTimeMS, MixerChannel::maxDecibels - MixerChannel::minDecibels); -_rms.setSampleRate(sr); + _rms.setSampleRate(sr); } void Mix8::processChannel(const ProcessArgs& args, int _c) { @@ -26,14 +36,27 @@ void Mix8::processChannel(const ProcessArgs& args, int _c) { params[MUTE6_PARAM].getValue() > 1.5f || params[MUTE7_PARAM].getValue() > 1.5f || params[MUTE8_PARAM].getValue() > 1.5f; - _channel1->next(stereo, solo); - _channel2->next(stereo, solo); - _channel3->next(stereo, solo); - _channel4->next(stereo, solo); - _channel5->next(stereo, solo); - _channel6->next(stereo, solo); - _channel7->next(stereo, solo); - _channel8->next(stereo, solo); + + { + float sample = 0.0f; + if (_polyChannelOffset >= 0) { + sample = inputs[IN1_INPUT].getPolyVoltage(_polyChannelOffset); + } else { + sample = inputs[IN1_INPUT].getVoltageSum(); + } + _channels[0]->next(sample, stereo, solo); + + for (int i = 1; i < 8; ++i) { + float sample = 0.0f; + if (inputs[IN1_INPUT + 3 * i].isConnected()) { + sample = inputs[IN1_INPUT + 3 * i].getVoltageSum(); + } + else if (_polyChannelOffset >= 0) { + sample = inputs[IN1_INPUT].getPolyVoltage(_polyChannelOffset + i); + } + _channels[i]->next(sample, stereo, solo); + } + } float level = Amplifier::minDecibels; if (params[MIX_MUTE_PARAM].getValue() < 0.5f) { @@ -47,41 +70,26 @@ void Mix8::processChannel(const ProcessArgs& args, int _c) { _amplifier.setLevel(_slewLimiter.next(level)); float mono = 0.0f; - mono += _channel1->out; - mono += _channel2->out; - mono += _channel3->out; - mono += _channel4->out; - mono += _channel5->out; - mono += _channel6->out; - mono += _channel7->out; - mono += _channel8->out; + for (int i = 0; i < 8; ++i) { + mono += _channels[i]->out; + } mono = _amplifier.next(mono); mono = _saturator.next(mono); _rmsLevel = _rms.next(mono) / 5.0f; if (stereo) { float left = 0.0f; - left += _channel1->left; - left += _channel2->left; - left += _channel3->left; - left += _channel4->left; - left += _channel5->left; - left += _channel6->left; - left += _channel7->left; - left += _channel8->left; + for (int i = 0; i < 8; ++i) { + left += _channels[i]->left; + } left = _amplifier.next(left); left = _saturator.next(left); outputs[L_OUTPUT].setVoltage(left); float right = 0.0f; - right += _channel1->right; - right += _channel2->right; - right += _channel3->right; - right += _channel4->right; - right += _channel5->right; - right += _channel6->right; - right += _channel7->right; - right += _channel8->right; + for (int i = 0; i < 8; ++i) { + right += _channels[i]->right; + } right = _amplifier.next(right); right = _saturator.next(right); outputs[R_OUTPUT].setVoltage(right); @@ -169,28 +177,28 @@ struct Mix8Widget : ModuleWidget { auto rOutputPosition = Vec(366.5, 325.0); // end generated by svg_widgets.rb - addSlider(level1ParamPosition, module, Mix8::LEVEL1_PARAM, module ? &module->_channel1->rms : NULL); + addSlider(level1ParamPosition, module, Mix8::LEVEL1_PARAM, module ? &module->_channels[0]->rms : NULL); addParam(createParam<SoloMuteButton>(mute1ParamPosition, module, Mix8::MUTE1_PARAM)); addParam(createParam<Knob16>(pan1ParamPosition, module, Mix8::PAN1_PARAM)); - addSlider(level2ParamPosition, module, Mix8::LEVEL2_PARAM, module ? &module->_channel2->rms : NULL); + addSlider(level2ParamPosition, module, Mix8::LEVEL2_PARAM, module ? &module->_channels[1]->rms : NULL); addParam(createParam<SoloMuteButton>(mute2ParamPosition, module, Mix8::MUTE2_PARAM)); addParam(createParam<Knob16>(pan2ParamPosition, module, Mix8::PAN2_PARAM)); - addSlider(level3ParamPosition, module, Mix8::LEVEL3_PARAM, module ? &module->_channel3->rms : NULL); + addSlider(level3ParamPosition, module, Mix8::LEVEL3_PARAM, module ? &module->_channels[2]->rms : NULL); addParam(createParam<SoloMuteButton>(mute3ParamPosition, module, Mix8::MUTE3_PARAM)); addParam(createParam<Knob16>(pan3ParamPosition, module, Mix8::PAN3_PARAM)); - addSlider(level4ParamPosition, module, Mix8::LEVEL4_PARAM, module ? &module->_channel4->rms : NULL); + addSlider(level4ParamPosition, module, Mix8::LEVEL4_PARAM, module ? &module->_channels[3]->rms : NULL); addParam(createParam<SoloMuteButton>(mute4ParamPosition, module, Mix8::MUTE4_PARAM)); addParam(createParam<Knob16>(pan4ParamPosition, module, Mix8::PAN4_PARAM)); - addSlider(level5ParamPosition, module, Mix8::LEVEL5_PARAM, module ? &module->_channel5->rms : NULL); + addSlider(level5ParamPosition, module, Mix8::LEVEL5_PARAM, module ? &module->_channels[4]->rms : NULL); addParam(createParam<SoloMuteButton>(mute5ParamPosition, module, Mix8::MUTE5_PARAM)); addParam(createParam<Knob16>(pan5ParamPosition, module, Mix8::PAN5_PARAM)); - addSlider(level6ParamPosition, module, Mix8::LEVEL6_PARAM, module ? &module->_channel6->rms : NULL); + addSlider(level6ParamPosition, module, Mix8::LEVEL6_PARAM, module ? &module->_channels[5]->rms : NULL); addParam(createParam<SoloMuteButton>(mute6ParamPosition, module, Mix8::MUTE6_PARAM)); addParam(createParam<Knob16>(pan6ParamPosition, module, Mix8::PAN6_PARAM)); - addSlider(level7ParamPosition, module, Mix8::LEVEL7_PARAM, module ? &module->_channel7->rms : NULL); + addSlider(level7ParamPosition, module, Mix8::LEVEL7_PARAM, module ? &module->_channels[6]->rms : NULL); addParam(createParam<SoloMuteButton>(mute7ParamPosition, module, Mix8::MUTE7_PARAM)); addParam(createParam<Knob16>(pan7ParamPosition, module, Mix8::PAN7_PARAM)); - addSlider(level8ParamPosition, module, Mix8::LEVEL8_PARAM, module ? &module->_channel8->rms : NULL); + addSlider(level8ParamPosition, module, Mix8::LEVEL8_PARAM, module ? &module->_channels[7]->rms : NULL); addParam(createParam<SoloMuteButton>(mute8ParamPosition, module, Mix8::MUTE8_PARAM)); addParam(createParam<Knob16>(pan8ParamPosition, module, Mix8::PAN8_PARAM)); addSlider(mixParamPosition, module, Mix8::MIX_PARAM, module ? &module->_rmsLevel : NULL); @@ -233,6 +241,36 @@ struct Mix8Widget : ModuleWidget { } addParam(slider); } + + struct PolySpreadMenuItem : MenuItem { + Mix8* _module; + int _offset; + + PolySpreadMenuItem(Mix8* module, const char* label, int offset) + : _module(module) + , _offset(offset) + { + this->text = label; + } + + void onAction(const event::Action& e) override { + _module->_polyChannelOffset = _offset; + } + + void step() override { + MenuItem::step(); + rightText = _module->_polyChannelOffset == _offset ? "✔" : ""; + } + }; + + void appendContextMenu(Menu* menu) override { + Mix8* m = dynamic_cast<Mix8*>(module); + assert(m); + menu->addChild(new MenuLabel()); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: none", -1)); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: channels 1-8", 0)); + menu->addChild(new PolySpreadMenuItem(m, "Input 1 poly spread: channels 9-16", 8)); + } }; Model* modelMix8 = bogaudio::createModel<Mix8, Mix8Widget>("Bogaudio-Mix8", "Mix8", "8-channel mixer and panner", "Mixer", "Panning"); diff --git a/src/Mix8.hpp b/src/Mix8.hpp @@ -80,14 +80,8 @@ struct Mix8 : BGModule { NUM_LIGHTS }; - MixerChannel* _channel1; - MixerChannel* _channel2; - MixerChannel* _channel3; - MixerChannel* _channel4; - MixerChannel* _channel5; - MixerChannel* _channel6; - MixerChannel* _channel7; - MixerChannel* _channel8; + int _polyChannelOffset = -1; + MixerChannel* _channels[8] {}; Amplifier _amplifier; bogaudio::dsp::SlewLimiter _slewLimiter; Saturator _saturator; @@ -124,28 +118,25 @@ struct Mix8 : BGModule { configParam(MIX_PARAM, 0.0f, 1.0f, levelDefault, "Master level", " dB", 0.0f, MixerChannel::maxDecibels - MixerChannel::minDecibels, MixerChannel::minDecibels); configParam(MIX_MUTE_PARAM, 0.0f, 1.0f, 0.0f, "Master mute"); - _channel1 = new MixerChannel(params[LEVEL1_PARAM], params[PAN1_PARAM], params[MUTE1_PARAM], inputs[IN1_INPUT], inputs[CV1_INPUT], inputs[PAN1_INPUT]); - _channel2 = new MixerChannel(params[LEVEL2_PARAM], params[PAN2_PARAM], params[MUTE2_PARAM], inputs[IN2_INPUT], inputs[CV2_INPUT], inputs[PAN2_INPUT]); - _channel3 = new MixerChannel(params[LEVEL3_PARAM], params[PAN3_PARAM], params[MUTE3_PARAM], inputs[IN3_INPUT], inputs[CV3_INPUT], inputs[PAN3_INPUT]); - _channel4 = new MixerChannel(params[LEVEL4_PARAM], params[PAN4_PARAM], params[MUTE4_PARAM], inputs[IN4_INPUT], inputs[CV4_INPUT], inputs[PAN4_INPUT]); - _channel5 = new MixerChannel(params[LEVEL5_PARAM], params[PAN5_PARAM], params[MUTE5_PARAM], inputs[IN5_INPUT], inputs[CV5_INPUT], inputs[PAN5_INPUT]); - _channel6 = new MixerChannel(params[LEVEL6_PARAM], params[PAN6_PARAM], params[MUTE6_PARAM], inputs[IN6_INPUT], inputs[CV6_INPUT], inputs[PAN6_INPUT]); - _channel7 = new MixerChannel(params[LEVEL7_PARAM], params[PAN7_PARAM], params[MUTE7_PARAM], inputs[IN7_INPUT], inputs[CV7_INPUT], inputs[PAN7_INPUT]); - _channel8 = new MixerChannel(params[LEVEL8_PARAM], params[PAN8_PARAM], params[MUTE8_PARAM], inputs[IN8_INPUT], inputs[CV8_INPUT], inputs[PAN8_INPUT]); + _channels[0] = new MixerChannel(params[LEVEL1_PARAM], params[PAN1_PARAM], params[MUTE1_PARAM], inputs[CV1_INPUT], inputs[PAN1_INPUT]); + _channels[1] = new MixerChannel(params[LEVEL2_PARAM], params[PAN2_PARAM], params[MUTE2_PARAM], inputs[CV2_INPUT], inputs[PAN2_INPUT]); + _channels[2] = new MixerChannel(params[LEVEL3_PARAM], params[PAN3_PARAM], params[MUTE3_PARAM], inputs[CV3_INPUT], inputs[PAN3_INPUT]); + _channels[3] = new MixerChannel(params[LEVEL4_PARAM], params[PAN4_PARAM], params[MUTE4_PARAM], inputs[CV4_INPUT], inputs[PAN4_INPUT]); + _channels[4] = new MixerChannel(params[LEVEL5_PARAM], params[PAN5_PARAM], params[MUTE5_PARAM], inputs[CV5_INPUT], inputs[PAN5_INPUT]); + _channels[5] = new MixerChannel(params[LEVEL6_PARAM], params[PAN6_PARAM], params[MUTE6_PARAM], inputs[CV6_INPUT], inputs[PAN6_INPUT]); + _channels[6] = new MixerChannel(params[LEVEL7_PARAM], params[PAN7_PARAM], params[MUTE7_PARAM], inputs[CV7_INPUT], inputs[PAN7_INPUT]); + _channels[7] = new MixerChannel(params[LEVEL8_PARAM], params[PAN8_PARAM], params[MUTE8_PARAM], inputs[CV8_INPUT], inputs[PAN8_INPUT]); sampleRateChange(); _rms.setSensitivity(0.05f); } virtual ~Mix8() { - delete _channel1; - delete _channel2; - delete _channel3; - delete _channel4; - delete _channel5; - delete _channel6; - delete _channel7; - delete _channel8; + for (int i = 0; i < 8; ++i) { + delete _channels[i]; + } } + json_t* dataToJson() override; + void dataFromJson(json_t* root) override; void sampleRateChange() override; void processChannel(const ProcessArgs& args, int _c) override; }; diff --git a/src/mixer.cpp b/src/mixer.cpp @@ -12,12 +12,7 @@ void MixerChannel::setSampleRate(float sampleRate) { _rms.setSampleRate(sampleRate); } -void MixerChannel::next(bool stereo, bool solo) { - if (!_inInput.isConnected()) { - rms = out = left = right = 0.0f; - return; - } - +void MixerChannel::next(float sample, bool stereo, bool solo) { float mute = _muteParam.getValue(); if (_muteInput) { mute += clamp(_muteInput->getVoltage(), 0.0f, 10.0f); @@ -36,7 +31,7 @@ void MixerChannel::next(bool stereo, bool solo) { _amplifier.setLevel(_levelSL.next(level)); } - out = _amplifier.next(_inInput.getVoltageSum()); + left = right = out = _amplifier.next(sample); rms = _rms.next(out / 5.0f); if (stereo) { float pan = clamp(_panParam.getValue(), -1.0f, 1.0f); diff --git a/src/mixer.hpp b/src/mixer.hpp @@ -22,7 +22,6 @@ struct MixerChannel { Param& _levelParam; Param& _panParam; Param& _muteParam; - Input& _inInput; Input& _levelInput; Input& _panInput; Input* _muteInput; @@ -36,7 +35,6 @@ struct MixerChannel { Param& level, Param& pan, Param& mute, - Input& in, Input& levelCv, Input& panCv, float sampleRate = 1000.0f, @@ -45,7 +43,6 @@ struct MixerChannel { : _levelParam(level) , _panParam(pan) , _muteParam(mute) - , _inInput(in) , _levelInput(levelCv) , _panInput(panCv) , _muteInput(muteCv) @@ -55,7 +52,7 @@ struct MixerChannel { } void setSampleRate(float sampleRate); - void next(bool stereo, bool solo); // input from _in; outputs on out, left, right, rms. + void next(float sample, bool stereo, bool solo); // outputs on out, left, right, rms. }; struct MuteButton : ToggleButton {