diff options
author | Wohlstand <admin@wohlnet.ru> | 2020-09-12 12:50:26 +0300 |
---|---|---|
committer | Wohlstand <admin@wohlnet.ru> | 2020-09-12 12:50:26 +0300 |
commit | e6806ad8a4ce1c91530e031b1aac1d89c68b9481 (patch) | |
tree | 79a14686d17526ce1faf002960f3df54a43d5d4c /src/adlmidi_midiplay.cpp | |
parent | 2b6d1fcfe4895ea0d3a57ef7e7f67a79e0bdb170 (diff) | |
download | libADLMIDI-e6806ad8a4ce1c91530e031b1aac1d89c68b9481.tar.gz libADLMIDI-e6806ad8a4ce1c91530e031b1aac1d89c68b9481.tar.bz2 libADLMIDI-e6806ad8a4ce1c91530e031b1aac1d89c68b9481.zip |
Added AIL frequency model
Diffstat (limited to 'src/adlmidi_midiplay.cpp')
-rw-r--r-- | src/adlmidi_midiplay.cpp | 127 |
1 files changed, 127 insertions, 0 deletions
diff --git a/src/adlmidi_midiplay.cpp b/src/adlmidi_midiplay.cpp index 7f1f230..572e7da 100644 --- a/src/adlmidi_midiplay.cpp +++ b/src/adlmidi_midiplay.cpp @@ -480,6 +480,129 @@ static inline double s_hmiFreq(double noteD, double bendD) +/*************************************************************** + * Audio Interface Library frequency model * + ***************************************************************/ + +static const uint_fast16_t mo_freqtable[] = { + 0x02b2, 0x02b4, 0x02b7, 0x02b9, 0x02bc, 0x02be, 0x02c1, 0x02c3, + 0x02c6, 0x02c9, 0x02cb, 0x02ce, 0x02d0, 0x02d3, 0x02d6, 0x02d8, + 0x02db, 0x02dd, 0x02e0, 0x02e3, 0x02e5, 0x02e8, 0x02eb, 0x02ed, + 0x02f0, 0x02f3, 0x02f6, 0x02f8, 0x02fb, 0x02fe, 0x0301, 0x0303, + 0x0306, 0x0309, 0x030c, 0x030f, 0x0311, 0x0314, 0x0317, 0x031a, + 0x031d, 0x0320, 0x0323, 0x0326, 0x0329, 0x032b, 0x032e, 0x0331, + 0x0334, 0x0337, 0x033a, 0x033d, 0x0340, 0x0343, 0x0346, 0x0349, + 0x034c, 0x034f, 0x0352, 0x0356, 0x0359, 0x035c, 0x035f, 0x0362, + 0x0365, 0x0368, 0x036b, 0x036f, 0x0372, 0x0375, 0x0378, 0x037b, + 0x037f, 0x0382, 0x0385, 0x0388, 0x038c, 0x038f, 0x0392, 0x0395, + 0x0399, 0x039c, 0x039f, 0x03a3, 0x03a6, 0x03a9, 0x03ad, 0x03b0, + 0x03b4, 0x03b7, 0x03bb, 0x03be, 0x03c1, 0x03c5, 0x03c8, 0x03cc, + 0x03cf, 0x03d3, 0x03d7, 0x03da, 0x03de, 0x03e1, 0x03e5, 0x03e8, + 0x03ec, 0x03f0, 0x03f3, 0x03f7, 0x03fb, 0x03fe, 0xfe01, 0xfe03, + 0xfe05, 0xfe07, 0xfe08, 0xfe0a, 0xfe0c, 0xfe0e, 0xfe10, 0xfe12, + 0xfe14, 0xfe16, 0xfe18, 0xfe1a, 0xfe1c, 0xfe1e, 0xfe20, 0xfe21, + 0xfe23, 0xfe25, 0xfe27, 0xfe29, 0xfe2b, 0xfe2d, 0xfe2f, 0xfe31, + 0xfe34, 0xfe36, 0xfe38, 0xfe3a, 0xfe3c, 0xfe3e, 0xfe40, 0xfe42, + 0xfe44, 0xfe46, 0xfe48, 0xfe4a, 0xfe4c, 0xfe4f, 0xfe51, 0xfe53, + 0xfe55, 0xfe57, 0xfe59, 0xfe5c, 0xfe5e, 0xfe60, 0xfe62, 0xfe64, + 0xfe67, 0xfe69, 0xfe6b, 0xfe6d, 0xfe6f, 0xfe72, 0xfe74, 0xfe76, + 0xfe79, 0xfe7b, 0xfe7d, 0xfe7f, 0xfe82, 0xfe84, 0xfe86, 0xfe89, + 0xfe8b, 0xfe8d, 0xfe90, 0xfe92, 0xfe95, 0xfe97, 0xfe99, 0xfe9c, + 0xfe9e, 0xfea1, 0xfea3, 0xfea5, 0xfea8, 0xfeaa, 0xfead, 0xfeaf +}; + +static const uint_fast8_t mo_note_octave[] = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x01, 0x01, + 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, + 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, + 0x02, 0x02, 0x02, 0x02, 0x03, 0x03, 0x03, 0x03, + 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, + 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, + 0x04, 0x04, 0x04, 0x04, 0x05, 0x05, 0x05, 0x05, + 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, + 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, + 0x06, 0x06, 0x06, 0x06, 0x07, 0x07, 0x07, 0x07, + 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07 +}; + +static const uint_fast8_t mo_note_halftone[] = { + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x00, 0x01, 0x02, 0x03, + 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x00, 0x01, 0x02, 0x03, + 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x00, 0x01, 0x02, 0x03, + 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x00, 0x01, 0x02, 0x03, + 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b +}; + +static inline double s_ailFreq(double noteD, double bendD) +{ + int_fast32_t note = (int_fast32_t)(noteD + 0.5); + double bendDec = bendD - (int)bendD; // 0.0 ± 1.0 - one halftone + int_fast32_t pitch; + uint_fast16_t freq; + int_fast32_t octave; + int_fast32_t octaveOffset = 0; + uint_fast8_t halftones; + + note += (int)bendD; + pitch = (int_fast32_t)(bendDec * 4096) + 8192; // convert to MIDI standard value + pitch = ((pitch - 0x2000) / 0x20) * 2; + + note -= 12; + + while(note < 0) + { + octaveOffset--; + note += 12; + } + while(note > 95) + { + octaveOffset++; + note -= 12; + } + + pitch += (((uint_fast8_t)note) << 8) + 8; + pitch /= 16; + while (pitch < 12 * 16) { + pitch += 12 * 16; + } + while (pitch > 96 * 16 - 1) { + pitch -= 12 * 16; + } + + halftones = (mo_note_halftone[pitch >> 4] << 4) + (pitch & 0x0f); + freq = mo_freqtable[halftones]; + octave = mo_note_octave[pitch >> 4]; + + if((freq & 0x8000) == 0) + { + if (octave > 0) { + octave--; + } else { + freq /= 2; + } + } + + freq &= 0x3FF; + + octave += octaveOffset; + + while(octave > 0) + { + freq *= 2; + octave -= 1; + } + + return freq; +} + @@ -1779,6 +1902,10 @@ void MIDIplay::noteUpdate(size_t midCh, finalFreq = s_hmiFreq(currentTone, bend); break; + case Synth::VOLUME_AIL: + finalFreq = s_ailFreq(currentTone, bend); + break; + default: finalFreq = s_commonFreq(currentTone, bend); } |