frontpanelState.cpp (3586B)
1 #include "frontpanelState.h" 2 3 #include "microcontrollerTypes.h" 4 5 #include "synthLib/midiTypes.h" 6 7 #include "dsp56kEmu/dsp.h" 8 #include "dsp56kEmu/peripherals.h" 9 10 namespace virusLib 11 { 12 static constexpr std::initializer_list<uint8_t> g_midiDumpHeader = {0xf0, 0x00, 0x20, 0x33, 0x01, OMNI_DEVICE_ID, DUMP_EMU_SYNTHSTATE}; 13 14 void FrontpanelState::updateLfoPhaseFromTimer(dsp56k::DSP& _dsp, const uint32_t _lfo, const uint32_t _timer, const float _minimumValue/* = 0.0f*/, float _maximumValue/* = 1.0f*/) 15 { 16 updatePhaseFromTimer(m_lfoPhases[_lfo], _dsp, _timer, _minimumValue, _maximumValue); 17 } 18 19 void FrontpanelState::updatePhaseFromTimer(float& _target, dsp56k::DSP& _dsp, const uint32_t _timer, float _minimumValue, float _maximumValue) 20 { 21 const auto* peripherals = _dsp.getPeriph(0); 22 23 if(const auto* p362 = dynamic_cast<const dsp56k::Peripherals56362*>(peripherals)) 24 { 25 const auto& t = p362->getTimers(); 26 updatePhaseFromTimer(_target, t, _timer, _minimumValue, _maximumValue); 27 } 28 else if(const auto* p303 = dynamic_cast<const dsp56k::Peripherals56303*>(peripherals)) 29 { 30 const auto& t = p303->getTimers(); 31 updatePhaseFromTimer(_target, t, _timer, _minimumValue, _maximumValue); 32 } 33 } 34 35 void FrontpanelState::updatePhaseFromTimer(float& _target, const dsp56k::Timers& _timers, uint32_t _timer, float _minimumValue, float _maximumValue) 36 { 37 const auto compare = _timers.readTCPR(static_cast<int>(_timer)); 38 const auto load = _timers.readTLR(static_cast<int>(_timer)); 39 40 const auto range = 0xffffff - load; 41 42 const auto normalized = static_cast<float>(compare - load) / static_cast<float>(range); 43 44 // the minimum PWM value is not always zero, we need to remap 45 const auto floatRange = _maximumValue - _minimumValue; 46 const auto floatRangeInv = 1.0f / floatRange; 47 48 _target = (normalized - _minimumValue) * floatRangeInv; 49 } 50 51 void writeFloat(std::vector<uint8_t>& _sysex, const float _v) 52 { 53 const auto* ptr = reinterpret_cast<const uint8_t*>(&_v); 54 for(size_t i=0; i<sizeof(_v); ++i) 55 _sysex.push_back(ptr[i]); 56 } 57 58 size_t readFloat(float& _dst, const uint8_t* _s) 59 { 60 auto* ptr = reinterpret_cast<uint8_t*>(&_dst); 61 for(size_t i=0; i<sizeof(_dst); ++i) 62 ptr[i] = _s[i]; 63 return sizeof(_dst); 64 } 65 66 void FrontpanelState::toMidiEvent(synthLib::SMidiEvent& _e) const 67 { 68 _e.sysex.assign(g_midiDumpHeader.begin(), g_midiDumpHeader.end()); 69 70 uint32_t midiEvents = 0; 71 72 for(size_t i=0; i<m_midiEventReceived.size(); ++i) 73 { 74 if(m_midiEventReceived[i]) 75 midiEvents |= (1<<i); 76 } 77 78 _e.sysex.push_back((midiEvents >> 14) & 0x7f); 79 _e.sysex.push_back((midiEvents >> 7) & 0x7f); 80 _e.sysex.push_back((midiEvents) & 0x7f); 81 82 for (const auto lfoPhase : m_lfoPhases) 83 writeFloat(_e.sysex, lfoPhase); 84 85 writeFloat(_e.sysex, m_logo); 86 writeFloat(_e.sysex, m_bpm); 87 88 _e.sysex.push_back(0xf7); 89 } 90 91 bool FrontpanelState::fromMidiEvent(const synthLib::SMidiEvent& _e) 92 { 93 return fromMidiEvent(_e.sysex); 94 } 95 96 bool FrontpanelState::fromMidiEvent(const std::vector<uint8_t>& _sysex) 97 { 98 if(_sysex.size() < g_midiDumpHeader.size()) 99 return false; 100 101 const auto* s = &_sysex[g_midiDumpHeader.size()]; 102 103 uint32_t midiEvents = 0; 104 midiEvents |= static_cast<uint32_t>(*s) << 14; ++s; 105 midiEvents |= static_cast<uint32_t>(*s) << 7; ++s; 106 midiEvents |= static_cast<uint32_t>(*s); ++s; 107 108 for(size_t i=0; i<m_midiEventReceived.size(); ++i) 109 m_midiEventReceived[i] = (midiEvents & (1<<i)) ? true : false; 110 111 for (auto& lfoPhase : m_lfoPhases) 112 s += readFloat(lfoPhase, s); 113 114 s += readFloat(m_logo, s); 115 readFloat(m_bpm, s); 116 117 return true; 118 } 119 }