//
// minidexed.h
//
// MiniDexed - Dexed FM synthesizer for bare metal Raspberry Pi
// Copyright (C) 2022 The MiniDexed Team
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
//
# ifndef _minidexed_h
# define _minidexed_h
# include "extra_features.h"
# include "dexedadapter.h"
# include "config.h"
# include "userinterface.h"
# include "sysexfileloader.h"
# include "performanceconfig.h"
# include "midikeyboard.h"
# include "pckeyboard.h"
# include "serialmididevice.h"
# include "perftimer.h"
# include <fatfs/ff.h>
# include <stdint.h>
# include <string>
# include <circle/types.h>
# include <circle/interrupt.h>
# include <circle/gpiomanager.h>
# include <circle/i2cmaster.h>
# include <circle/multicore.h>
# include <circle/soundbasedevice.h>
# include <circle/spinlock.h>
# include "common.h"
# include "effect_mixer.hpp"
# include "effect_platervbstereo.h"
# include "effect_compressor.h"
# ifdef MIXING_CONSOLE_ENABLE
# include "mixing_console.h"
typedef MixingConsole < CConfig : : ToneGenerators > Mixer ;
# endif
class CMiniDexed
# ifdef ARM_ALLOW_MULTI_CORE
: public CMultiCoreSupport
# endif
{
public :
CMiniDexed ( CConfig * pConfig , CInterruptSystem * pInterrupt ,
CGPIOManager * pGPIOManager , CI2CMaster * pI2CMaster , FATFS * pFileSystem ) ;
bool Initialize ( void ) ;
void Process ( bool bPlugAndPlayUpdated ) ;
# ifdef ARM_ALLOW_MULTI_CORE
void Run ( unsigned nCore ) ;
# endif
CSysExFileLoader * GetSysExFileLoader ( void ) ;
void BankSelectLSB ( unsigned nBankLSB , unsigned nTG ) ;
void ProgramChange ( unsigned nProgram , unsigned nTG ) ;
void SetVolume ( unsigned nVolume , unsigned nTG ) ;
void SetPan ( unsigned nPan , unsigned nTG ) ; // 0 .. 127
void SetMasterTune ( int nMasterTune , unsigned nTG ) ; // -99 .. 99
void SetCutoff ( int nCutoff , unsigned nTG ) ; // 0 .. 99
void SetResonance ( int nResonance , unsigned nTG ) ; // 0 .. 99
void SetMIDIChannel ( uint8_t uchChannel , unsigned nTG ) ;
void keyup ( int16_t pitch , unsigned nTG ) ;
void keydown ( int16_t pitch , uint8_t velocity , unsigned nTG ) ;
void setSustain ( bool sustain , unsigned nTG ) ;
void panic ( uint8_t value , unsigned nTG ) ;
void notesOff ( uint8_t value , unsigned nTG ) ;
void setModWheel ( uint8_t value , unsigned nTG ) ;
void setPitchbend ( int16_t value , unsigned nTG ) ;
void ControllersRefresh ( unsigned nTG ) ;
void setFootController ( uint8_t value , unsigned nTG ) ;
void setBreathController ( uint8_t value , unsigned nTG ) ;
void setAftertouch ( uint8_t value , unsigned nTG ) ;
# ifdef MIXING_CONSOLE_ENABLE
void setMixingConsoleSendLevel ( unsigned nTG , MixerOutput fx , unsigned nFXSend ) ;
void setMixingConsoleReturnLevel ( MixerOutput ret , MixerOutput fx , unsigned nFXReturn ) ;
# else
void SetReverbSend ( unsigned nReverbSend , unsigned nTG ) ; // 0 .. 127
# endif
void setMonoMode ( uint8_t mono , uint8_t nTG ) ;
void setPitchbendRange ( uint8_t range , uint8_t nTG ) ;
void setPitchbendStep ( uint8_t step , uint8_t nTG ) ;
void setPortamentoMode ( uint8_t mode , uint8_t nTG ) ;
void setPortamentoGlissando ( uint8_t glissando , uint8_t nTG ) ;
void setPortamentoTime ( uint8_t time , uint8_t nTG ) ;
void setModWheelRange ( uint8_t range , uint8_t nTG ) ;
void setModWheelTarget ( uint8_t target , uint8_t nTG ) ;
void setFootControllerRange ( uint8_t range , uint8_t nTG ) ;
void setFootControllerTarget ( uint8_t target , uint8_t nTG ) ;
void setBreathControllerRange ( uint8_t range , uint8_t nTG ) ;
void setBreathControllerTarget ( uint8_t target , uint8_t nTG ) ;
void setAftertouchRange ( uint8_t range , uint8_t nTG ) ;
void setAftertouchTarget ( uint8_t target , uint8_t nTG ) ;
void loadVoiceParameters ( const uint8_t * data , uint8_t nTG ) ;
void setVoiceDataElement ( uint8_t data , uint8_t number , uint8_t nTG ) ;
void getSysExVoiceDump ( uint8_t * dest , uint8_t nTG ) ;
void setModController ( unsigned controller , unsigned parameter , uint8_t value , uint8_t nTG ) ;
unsigned getModController ( unsigned controller , unsigned parameter , uint8_t nTG ) ;
int16_t checkSystemExclusive ( const uint8_t * pMessage , const uint16_t nLength , uint8_t nTG ) ;
std : : string GetPerformanceFileName ( unsigned nID ) ;
std : : string GetPerformanceName ( unsigned nID ) ;
unsigned GetLastPerformance ( ) ;
unsigned GetActualPerformanceID ( ) ;
void SetActualPerformanceID ( unsigned nID ) ;
bool SetNewPerformance ( unsigned nID ) ;
bool SavePerformanceNewFile ( ) ;
bool DoSavePerformanceNewFile ( void ) ;
bool DoSetNewPerformance ( void ) ;
bool GetPerformanceSelectToLoad ( void ) ;
bool SavePerformance ( bool bSaveAsDeault ) ;
enum TParameter
{
ParameterCompressorEnable ,
# if defined(PLATE_REVERB_ENABLE) || defined(MIXING_CONSOLE_ENABLE)
// Plate Reverb parameters
ParameterReverbEnable ,
ParameterReverbSize ,
ParameterReverbHighDamp ,
ParameterReverbLowDamp ,
ParameterReverbLowPass ,
ParameterReverbDiffusion ,
ParameterReverbLevel ,
# endif
# ifdef MIXING_CONSOLE_ENABLE
// BEGIN FX global parameters definition
// Tube parameters
ParameterFXTubeEnable ,
ParameterFXTubeOverdrive ,
// Chorus parameters
ParameterFXChorusEnable ,
ParameterFXChorusRate ,
ParameterFXChorusDepth ,
// Flanger parameters
ParameterFXFlangerEnable ,
ParameterFXFlangerRate ,
ParameterFXFlangerDepth ,
ParameterFXFlangerFeedback ,
// Orbitone parameters
ParameterFXOrbitoneEnable ,
ParameterFXOrbitoneRate ,
ParameterFXOrbitoneDepth ,
// Phaser parameters
ParameterFXPhaserEnable ,
ParameterFXPhaserRate ,
ParameterFXPhaserDepth ,
ParameterFXPhaserFeedback ,
ParameterFXPhaserNbStages ,
// Delay parameters
ParameterFXDelayEnable ,
ParameterFXDelayLeftDelayTime ,
ParameterFXDelayRightDelayTime ,
ParameterFXDelayFeedback ,
ParameterFXDelayFlutterRate ,
ParameterFXDelayFlutterAmount ,
// ShimmerReverb parameters
ParameterFXShimmerReverbEnable ,
ParameterFXShimmerReverbInputGain ,
ParameterFXShimmerReverbTime ,
ParameterFXShimmerReverbDiffusion ,
ParameterFXShimmerReverbLP ,
// Tube Return parameters
ParameterFXTube_ChorusReturn ,
ParameterFXTube_FlangerReturn ,
ParameterFXTube_OrbitoneReturn ,
ParameterFXTube_PhaserReturn ,
ParameterFXTube_DelayReturn ,
ParameterFXTube_ReverbReturn ,
ParameterFXTube_ShimmerReturn ,
ParameterFXTube_MainOutput ,
// Chorus Return parameters
ParameterFXChorus_TubeReturn ,
ParameterFXChorus_FlangerReturn ,
ParameterFXChorus_OrbitoneReturn ,
ParameterFXChorus_PhaserReturn ,
ParameterFXChorus_DelayReturn ,
ParameterFXChorus_ReverbReturn ,
ParameterFXChorus_ShimmerReturn ,
ParameterFXChorus_MainOutput ,
// Flanger Return parameters
ParameterFXFlanger_TubeReturn ,
ParameterFXFlanger_ChorusReturn ,
ParameterFXFlanger_OrbitoneReturn ,
ParameterFXFlanger_PhaserReturn ,
ParameterFXFlanger_DelayReturn ,
ParameterFXFlanger_ReverbReturn ,
ParameterFXFlanger_ShimmerReturn ,
ParameterFXFlanger_MainOutput ,
// Orbitone Return parameters
ParameterFXOrbitone_TubeReturn ,
ParameterFXOrbitone_ChorusReturn ,
ParameterFXOrbitone_FlangerReturn ,
ParameterFXOrbitone_PhaserReturn ,
ParameterFXOrbitone_DelayReturn ,
ParameterFXOrbitone_ReverbReturn ,
ParameterFXOrbitone_ShimmerReturn ,
ParameterFXOrbitone_MainOutput ,
// Phaser Return parameters
ParameterFXPhaser_TubeReturn ,
ParameterFXPhaser_ChorusReturn ,
ParameterFXPhaser_FlangerReturn ,
ParameterFXPhaser_OrbitoneReturn ,
ParameterFXPhaser_DelayReturn ,
ParameterFXPhaser_ReverbReturn ,
ParameterFXPhaser_ShimmerReturn ,
ParameterFXPhaser_MainOutput ,
// Delay Return parameters
ParameterFXDelay_TubeReturn ,
ParameterFXDelay_ChorusReturn ,
ParameterFXDelay_FlangerReturn ,
ParameterFXDelay_OrbitoneReturn ,
ParameterFXDelay_PhaserReturn ,
ParameterFXDelay_ReverbReturn ,
ParameterFXDelay_ShimmerReturn ,
ParameterFXDelay_MainOutput ,
// Reverb Return parameters
ParameterFXReverb_TubeReturn ,
ParameterFXReverb_ChorusReturn ,
ParameterFXReverb_FlangerReturn ,
ParameterFXReverb_OrbitoneReturn ,
ParameterFXReverb_PhaserReturn ,
ParameterFXReverb_DelayReturn ,
ParameterFXReverb_ShimmerReturn ,
ParameterFXReverb_MainOutput ,
// Shimmer Return parameters
ParameterFXShimmer_TubeReturn ,
ParameterFXShimmer_ChorusReturn ,
ParameterFXShimmer_FlangerReturn ,
ParameterFXShimmer_OrbitoneReturn ,
ParameterFXShimmer_PhaserReturn ,
ParameterFXShimmer_DelayReturn ,
ParameterFXShimmer_ReverbReturn ,
ParameterFXShimmer_MainOutput ,
// END FX global parameters definition
# endif
ParameterUnknown
} ;
void SetParameter ( TParameter Parameter , int nValue ) ;
int GetParameter ( TParameter Parameter ) ;
std : : string GetNewPerformanceDefaultName ( void ) ;
void SetNewPerformanceName ( std : : string nName ) ;
void SetVoiceName ( std : : string VoiceName , unsigned nTG ) ;
bool DeletePerformance ( unsigned nID ) ;
bool DoDeletePerformance ( void ) ;
enum TTGParameter
{
TGParameterVoiceBank ,
TGParameterProgram ,
TGParameterVolume ,
TGParameterPan ,
TGParameterMasterTune ,
TGParameterCutoff ,
TGParameterResonance ,
TGParameterMIDIChannel ,
# ifdef PLATE_REVERB_ENABLE
TGParameterReverbSend ,
# endif
TGParameterPitchBendRange ,
TGParameterPitchBendStep ,
TGParameterPortamentoMode ,
TGParameterPortamentoGlissando ,
TGParameterPortamentoTime ,
TGParameterMonoMode ,
TGParameterMWRange ,
TGParameterMWPitch ,
TGParameterMWAmplitude ,
TGParameterMWEGBias ,
TGParameterFCRange ,
TGParameterFCPitch ,
TGParameterFCAmplitude ,
TGParameterFCEGBias ,
TGParameterBCRange ,
TGParameterBCPitch ,
TGParameterBCAmplitude ,
TGParameterBCEGBias ,
TGParameterATRange ,
TGParameterATPitch ,
TGParameterATAmplitude ,
TGParameterATEGBias ,
# ifdef MIXING_CONSOLE_ENABLE
TGParameterMixingSendFXTube ,
TGParameterMixingSendFXChorus ,
TGParameterMixingSendFXFlanger ,
TGParameterMixingSendFXOrbittone ,
TGParameterMixingSendFXPhaser ,
TGParameterMixingSendFXDelay ,
TGParameterMixingSendFXPlateReverb ,
TGParameterMixingSendFXShimmerReverb ,
TGParameterMixingSendFXMainOutput ,
# endif // MIXING_CONSOLE_ENABLE
TGParameterUnknown
} ;
void SetTGParameter ( TTGParameter Parameter , int nValue , unsigned nTG ) ;
int GetTGParameter ( TTGParameter Parameter , unsigned nTG ) ;
// access (global or OP-related) parameter of the active voice of a TG
static const unsigned NoOP = 6 ; // for global parameters
void SetVoiceParameter ( uint8_t uchOffset , uint8_t uchValue , unsigned nOP , unsigned nTG ) ;
uint8_t GetVoiceParameter ( uint8_t uchOffset , unsigned nOP , unsigned nTG ) ;
std : : string GetVoiceName ( unsigned nTG ) ;
bool SavePerformance ( void ) ;
bool DoSavePerformance ( void ) ;
void setMasterVolume ( float32_t vol ) ;
private :
int16_t ApplyNoteLimits ( int16_t pitch , unsigned nTG ) ; // returns < 0 to ignore note
uint8_t m_uchOPMask [ CConfig : : ToneGenerators ] ;
void LoadPerformanceParameters ( void ) ;
void ProcessSound ( void ) ;
# ifdef ARM_ALLOW_MULTI_CORE
enum TCoreStatus
{
CoreStatusInit ,
CoreStatusIdle ,
CoreStatusBusy ,
CoreStatusExit ,
CoreStatusUnknown
} ;
# endif
private :
CConfig * m_pConfig ;
int m_nParameter [ ParameterUnknown ] ; // global (non-TG) parameters
CDexedAdapter * m_pTG [ CConfig : : ToneGenerators ] ;
unsigned m_nVoiceBankID [ CConfig : : ToneGenerators ] ;
unsigned m_nProgram [ CConfig : : ToneGenerators ] ;
unsigned m_nVolume [ CConfig : : ToneGenerators ] ;
unsigned m_nPan [ CConfig : : ToneGenerators ] ;
int m_nMasterTune [ CConfig : : ToneGenerators ] ;
int m_nCutoff [ CConfig : : ToneGenerators ] ;
int m_nResonance [ CConfig : : ToneGenerators ] ;
unsigned m_nMIDIChannel [ CConfig : : ToneGenerators ] ;
unsigned m_nPitchBendRange [ CConfig : : ToneGenerators ] ;
unsigned m_nPitchBendStep [ CConfig : : ToneGenerators ] ;
unsigned m_nPortamentoMode [ CConfig : : ToneGenerators ] ;
unsigned m_nPortamentoGlissando [ CConfig : : ToneGenerators ] ;
unsigned m_nPortamentoTime [ CConfig : : ToneGenerators ] ;
bool m_bMonoMode [ CConfig : : ToneGenerators ] ;
unsigned m_nModulationWheelRange [ CConfig : : ToneGenerators ] ;
unsigned m_nModulationWheelTarget [ CConfig : : ToneGenerators ] ;
unsigned m_nFootControlRange [ CConfig : : ToneGenerators ] ;
unsigned m_nFootControlTarget [ CConfig : : ToneGenerators ] ;
unsigned m_nBreathControlRange [ CConfig : : ToneGenerators ] ;
unsigned m_nBreathControlTarget [ CConfig : : ToneGenerators ] ;
unsigned m_nAftertouchRange [ CConfig : : ToneGenerators ] ;
unsigned m_nAftertouchTarget [ CConfig : : ToneGenerators ] ;
unsigned m_nNoteLimitLow [ CConfig : : ToneGenerators ] ;
unsigned m_nNoteLimitHigh [ CConfig : : ToneGenerators ] ;
int m_nNoteShift [ CConfig : : ToneGenerators ] ;
# ifdef MIXING_CONSOLE_ENABLE
unsigned m_nFXSendLevel [ CConfig : : ToneGenerators ] [ MixerOutput : : kFXCount ] ;
unsigned m_nFXReturnLevel [ MixerOutput : : kFXCount - 1 ] [ MixerOutput : : kFXCount ] ;
# else
unsigned m_nReverbSend [ CConfig : : ToneGenerators ] ;
# endif
uint8_t m_nRawVoiceData [ 156 ] ;
float32_t nMasterVolume ;
CUserInterface m_UI ;
CSysExFileLoader m_SysExFileLoader ;
CPerformanceConfig m_PerformanceConfig ;
CMIDIKeyboard * m_pMIDIKeyboard [ CConfig : : MaxUSBMIDIDevices ] ;
CPCKeyboard m_PCKeyboard ;
CSerialMIDIDevice m_SerialMIDI ;
bool m_bUseSerial ;
CSoundBaseDevice * m_pSoundDevice ;
bool m_bChannelsSwapped ;
unsigned m_nQueueSizeFrames ;
# ifdef ARM_ALLOW_MULTI_CORE
unsigned m_nActiveTGsLog2 ;
volatile TCoreStatus m_CoreStatus [ CORES ] ;
volatile unsigned m_nFramesToProcess ;
float32_t m_OutputLevel [ CConfig : : ToneGenerators ] [ CConfig : : MaxChunkSize ] ;
# endif
CPerformanceTimer m_GetChunkTimer ;
bool m_bProfileEnabled ;
# ifdef MIXING_CONSOLE_ENABLE
Mixer * mixing_console_ ;
# endif
# ifdef PLATE_REVERB_ENABLE
AudioEffectPlateReverb * reverb ;
AudioStereoMixer < CConfig : : ToneGenerators > * tg_mixer ;
AudioStereoMixer < CConfig : : ToneGenerators > * reverb_send_mixer ;
# endif
CSpinLock m_FXSpinLock ;
bool m_bSavePerformance ;
bool m_bSavePerformanceNewFile ;
bool m_bSetNewPerformance ;
unsigned m_nSetNewPerformanceID ;
bool m_bDeletePerformance ;
unsigned m_nDeletePerformanceID ;
bool m_bLoadPerformanceBusy ;
bool m_bSaveAsDeault ;
} ;
# endif