@@ -10,9 +10,20 @@ class AbstractSynth : public Synth, public MidiProcessor, public VelocityCurve {
1010protected:
1111 uint8_t note = 60 ; // C4
1212 float pb = 0 ;
13- float pb_range = 2 ;
13+ float pb_range = 2 /8192 .0f ;
14+ float mod_range = 0.5 /127 .0f ;
15+ float tuning = 440 ;
1416public:
1517 virtual ~AbstractSynth (){}
18+ /* *
19+ * Set frequency in Hertz for middle A (defaults to Stuttgart pitch, A440, 440 Hz)
20+ */
21+ void setTuning (float value){
22+ tuning = value;
23+ }
24+ float getTuning (){
25+ return tuning;
26+ }
1627 /* *
1728 * Set note in whole semitones
1829 */
@@ -50,44 +61,54 @@ class AbstractSynth : public Synth, public MidiProcessor, public VelocityCurve {
5061 * Does not update the frequency; effective from next pitch bend change
5162 */
5263 void setPitchBendRange (float range){
53- this ->pb_range = range;
54- }
64+ this ->pb_range = range/8192 .0f ;
65+ }
66+ /* *
67+ * Set modulation depth range, from 0 to 1.0
68+ */
69+ void setModulationDepthRange (float range){
70+ mod_range = range / 127 .0f ;
71+ }
5572 // MIDI handlers
56- virtual void noteOn (MidiMessage msg) override {
73+ virtual void noteOn (MidiMessage msg) {
5774 setNote (msg.getNote ());
5875 setFrequency (noteToFrequency (note+pb));
5976 setGain (velocityToGain (msg.getVelocity ()));
6077 gate (true );
6178 }
62- virtual void noteOff (MidiMessage msg) override {
79+ virtual void noteOff (MidiMessage msg) {
6380 gate (false );
6481 }
65- virtual void controlChange (MidiMessage msg) override {
82+ virtual void controlChange (MidiMessage msg) {
6683 if (msg.getControllerNumber () == MIDI_CC_MODULATION)
67- setModulation (msg.getControllerValue ()/127 .0f );
84+ setModulation (msg.getControllerValue ()/128 .0f );
6885 else if (msg.getControllerNumber () == MIDI_ALL_NOTES_OFF)
6986 allNotesOff ();
7087 }
71- virtual void channelPressure (MidiMessage msg) override {
72- setPressure (msg.getChannelPressure ()/127 .0f );
88+ virtual void channelPressure (MidiMessage msg) {
89+ setPressure (msg.getChannelPressure ()/128 .0f );
7390 }
74- virtual void polyKeyPressure (MidiMessage msg) override {
75- setPressure (msg.getPolyKeyPressure ()/127 .0f );
91+ virtual void polyKeyPressure (MidiMessage msg) {
92+ setPressure (msg.getPolyKeyPressure ()/128 .0f );
7693 }
77- virtual void setModulation (float modulation){} // default implementation does nothing
78- virtual void setPressure (float pressure){}
79- virtual void pitchbend (MidiMessage msg) override {
80- setPitchBend (pb_range*msg.getPitchBend ()/8192 .0f );
94+ virtual void modulate (MidiMessage msg) {
95+ setModulation (mod_range * msg.getControllerValue ());
96+ }
97+ virtual void pitchbend (MidiMessage msg) {
98+ setPitchBend (pb_range * msg.getPitchBend ());
8199 }
82100 virtual void allNotesOff (){
83101 gate (false );
84102 }
103+ // default implementations do nothing
104+ virtual void setModulation (float modulation){}
105+ virtual void setPressure (float pressure){}
85106 // static utility methods
86- static inline float frequencyToNote (float freq){
87- return 12 * log2f (freq / 440 ) + 69 ;
107+ inline float frequencyToNote (float freq){
108+ return 12 * log2f (freq / tuning ) + 69 ;
88109 }
89- static inline float noteToFrequency (float note){
90- return 440 * exp2f ((note - 69 ) / 12 );
110+ inline float noteToFrequency (float note){
111+ return tuning * exp2f ((note - 69 ) / 12 );
91112 }
92113};
93114
0 commit comments