aboutsummaryrefslogtreecommitdiff
path: root/src/adlmidi_midiplay.cpp
diff options
context:
space:
mode:
authorWohlstand <admin@wohlnet.ru>2020-09-13 15:58:37 +0300
committerWohlstand <admin@wohlnet.ru>2020-09-13 15:58:37 +0300
commit7f66550168af30e03b7762ba9ce6a9d56f578064 (patch)
tree37e436127c4701902b63ec2d360797d16aeedda8 /src/adlmidi_midiplay.cpp
parente6806ad8a4ce1c91530e031b1aac1d89c68b9481 (diff)
downloadlibADLMIDI-7f66550168af30e03b7762ba9ce6a9d56f578064.tar.gz
libADLMIDI-7f66550168af30e03b7762ba9ce6a9d56f578064.tar.bz2
libADLMIDI-7f66550168af30e03b7762ba9ce6a9d56f578064.zip
Move all frequency computation code from a MIDIPlay into the Synth
Diffstat (limited to 'src/adlmidi_midiplay.cpp')
-rw-r--r--src/adlmidi_midiplay.cpp621
1 files changed, 6 insertions, 615 deletions
diff --git a/src/adlmidi_midiplay.cpp b/src/adlmidi_midiplay.cpp
index 572e7da..8a6751d 100644
--- a/src/adlmidi_midiplay.cpp
+++ b/src/adlmidi_midiplay.cpp
@@ -29,585 +29,9 @@
// Minimum life time of percussion notes
static const double s_drum_note_min_time = 0.03;
-
-
-
-/***************************************************************
- * Standard frequency formula *
- * *************************************************************/
-
-static inline double s_commonFreq(double note, double bend)
-{
- return BEND_COEFFICIENT * std::exp(0.057762265 * (note + bend));
-}
-
-
-
-
-/***************************************************************
- * DMX frequency model *
- * *************************************************************/
-
-// DMX volumes table
-static const int_fast32_t s_dmx_freq_table[] =
-{
- 0x0133, 0x0133, 0x0134, 0x0134, 0x0135, 0x0136, 0x0136, 0x0137,
- 0x0137, 0x0138, 0x0138, 0x0139, 0x0139, 0x013A, 0x013B, 0x013B,
- 0x013C, 0x013C, 0x013D, 0x013D, 0x013E, 0x013F, 0x013F, 0x0140,
- 0x0140, 0x0141, 0x0142, 0x0142, 0x0143, 0x0143, 0x0144, 0x0144,
-
- 0x0145, 0x0146, 0x0146, 0x0147, 0x0147, 0x0148, 0x0149, 0x0149,
- 0x014A, 0x014A, 0x014B, 0x014C, 0x014C, 0x014D, 0x014D, 0x014E,
- 0x014F, 0x014F, 0x0150, 0x0150, 0x0151, 0x0152, 0x0152, 0x0153,
- 0x0153, 0x0154, 0x0155, 0x0155, 0x0156, 0x0157, 0x0157, 0x0158,
-
- 0x0158, 0x0159, 0x015A, 0x015A, 0x015B, 0x015B, 0x015C, 0x015D,
- 0x015D, 0x015E, 0x015F, 0x015F, 0x0160, 0x0161, 0x0161, 0x0162,
- 0x0162, 0x0163, 0x0164, 0x0164, 0x0165, 0x0166, 0x0166, 0x0167,
- 0x0168, 0x0168, 0x0169, 0x016A, 0x016A, 0x016B, 0x016C, 0x016C,
-
- 0x016D, 0x016E, 0x016E, 0x016F, 0x0170, 0x0170, 0x0171, 0x0172,
- 0x0172, 0x0173, 0x0174, 0x0174, 0x0175, 0x0176, 0x0176, 0x0177,
- 0x0178, 0x0178, 0x0179, 0x017A, 0x017A, 0x017B, 0x017C, 0x017C,
- 0x017D, 0x017E, 0x017E, 0x017F, 0x0180, 0x0181, 0x0181, 0x0182,
-
- 0x0183, 0x0183, 0x0184, 0x0185, 0x0185, 0x0186, 0x0187, 0x0188,
- 0x0188, 0x0189, 0x018A, 0x018A, 0x018B, 0x018C, 0x018D, 0x018D,
- 0x018E, 0x018F, 0x018F, 0x0190, 0x0191, 0x0192, 0x0192, 0x0193,
- 0x0194, 0x0194, 0x0195, 0x0196, 0x0197, 0x0197, 0x0198, 0x0199,
-
- 0x019A, 0x019A, 0x019B, 0x019C, 0x019D, 0x019D, 0x019E, 0x019F,
- 0x01A0, 0x01A0, 0x01A1, 0x01A2, 0x01A3, 0x01A3, 0x01A4, 0x01A5,
- 0x01A6, 0x01A6, 0x01A7, 0x01A8, 0x01A9, 0x01A9, 0x01AA, 0x01AB,
- 0x01AC, 0x01AD, 0x01AD, 0x01AE, 0x01AF, 0x01B0, 0x01B0, 0x01B1,
-
- 0x01B2, 0x01B3, 0x01B4, 0x01B4, 0x01B5, 0x01B6, 0x01B7, 0x01B8,
- 0x01B8, 0x01B9, 0x01BA, 0x01BB, 0x01BC, 0x01BC, 0x01BD, 0x01BE,
- 0x01BF, 0x01C0, 0x01C0, 0x01C1, 0x01C2, 0x01C3, 0x01C4, 0x01C4,
- 0x01C5, 0x01C6, 0x01C7, 0x01C8, 0x01C9, 0x01C9, 0x01CA, 0x01CB,
-
- 0x01CC, 0x01CD, 0x01CE, 0x01CE, 0x01CF, 0x01D0, 0x01D1, 0x01D2,
- 0x01D3, 0x01D3, 0x01D4, 0x01D5, 0x01D6, 0x01D7, 0x01D8, 0x01D8,
- 0x01D9, 0x01DA, 0x01DB, 0x01DC, 0x01DD, 0x01DE, 0x01DE, 0x01DF,
- 0x01E0, 0x01E1, 0x01E2, 0x01E3, 0x01E4, 0x01E5, 0x01E5, 0x01E6,
-
- 0x01E7, 0x01E8, 0x01E9, 0x01EA, 0x01EB, 0x01EC, 0x01ED, 0x01ED,
- 0x01EE, 0x01EF, 0x01F0, 0x01F1, 0x01F2, 0x01F3, 0x01F4, 0x01F5,
- 0x01F6, 0x01F6, 0x01F7, 0x01F8, 0x01F9, 0x01FA, 0x01FB, 0x01FC,
- 0x01FD, 0x01FE, 0x01FF,
-
- 0x0200, 0x0201, 0x0201, 0x0202, 0x0203, 0x0204, 0x0205, 0x0206,
- 0x0207, 0x0208, 0x0209, 0x020A, 0x020B, 0x020C, 0x020D, 0x020E,
- 0x020F, 0x0210, 0x0210, 0x0211, 0x0212, 0x0213, 0x0214, 0x0215,
- 0x0216, 0x0217, 0x0218, 0x0219, 0x021A, 0x021B, 0x021C, 0x021D,
-
- 0x021E, 0x021F, 0x0220, 0x0221, 0x0222, 0x0223, 0x0224, 0x0225,
- 0x0226, 0x0227, 0x0228, 0x0229, 0x022A, 0x022B, 0x022C, 0x022D,
- 0x022E, 0x022F, 0x0230, 0x0231, 0x0232, 0x0233, 0x0234, 0x0235,
- 0x0236, 0x0237, 0x0238, 0x0239, 0x023A, 0x023B, 0x023C, 0x023D,
-
- 0x023E, 0x023F, 0x0240, 0x0241, 0x0242, 0x0244, 0x0245, 0x0246,
- 0x0247, 0x0248, 0x0249, 0x024A, 0x024B, 0x024C, 0x024D, 0x024E,
- 0x024F, 0x0250, 0x0251, 0x0252, 0x0253, 0x0254, 0x0256, 0x0257,
- 0x0258, 0x0259, 0x025A, 0x025B, 0x025C, 0x025D, 0x025E, 0x025F,
-
- 0x0260, 0x0262, 0x0263, 0x0264, 0x0265, 0x0266, 0x0267, 0x0268,
- 0x0269, 0x026A, 0x026C, 0x026D, 0x026E, 0x026F, 0x0270, 0x0271,
- 0x0272, 0x0273, 0x0275, 0x0276, 0x0277, 0x0278, 0x0279, 0x027A,
- 0x027B, 0x027D, 0x027E, 0x027F, 0x0280, 0x0281, 0x0282, 0x0284,
-
- 0x0285, 0x0286, 0x0287, 0x0288, 0x0289, 0x028B, 0x028C, 0x028D,
- 0x028E, 0x028F, 0x0290, 0x0292, 0x0293, 0x0294, 0x0295, 0x0296,
- 0x0298, 0x0299, 0x029A, 0x029B, 0x029C, 0x029E, 0x029F, 0x02A0,
- 0x02A1, 0x02A2, 0x02A4, 0x02A5, 0x02A6, 0x02A7, 0x02A9, 0x02AA,
-
- 0x02AB, 0x02AC, 0x02AE, 0x02AF, 0x02B0, 0x02B1, 0x02B2, 0x02B4,
- 0x02B5, 0x02B6, 0x02B7, 0x02B9, 0x02BA, 0x02BB, 0x02BD, 0x02BE,
- 0x02BF, 0x02C0, 0x02C2, 0x02C3, 0x02C4, 0x02C5, 0x02C7, 0x02C8,
- 0x02C9, 0x02CB, 0x02CC, 0x02CD, 0x02CE, 0x02D0, 0x02D1, 0x02D2,
-
- 0x02D4, 0x02D5, 0x02D6, 0x02D8, 0x02D9, 0x02DA, 0x02DC, 0x02DD,
- 0x02DE, 0x02E0, 0x02E1, 0x02E2, 0x02E4, 0x02E5, 0x02E6, 0x02E8,
- 0x02E9, 0x02EA, 0x02EC, 0x02ED, 0x02EE, 0x02F0, 0x02F1, 0x02F2,
- 0x02F4, 0x02F5, 0x02F6, 0x02F8, 0x02F9, 0x02FB, 0x02FC, 0x02FD,
-
- 0x02FF, 0x0300, 0x0302, 0x0303, 0x0304, 0x0306, 0x0307, 0x0309,
- 0x030A, 0x030B, 0x030D, 0x030E, 0x0310, 0x0311, 0x0312, 0x0314,
- 0x0315, 0x0317, 0x0318, 0x031A, 0x031B, 0x031C, 0x031E, 0x031F,
- 0x0321, 0x0322, 0x0324, 0x0325, 0x0327, 0x0328, 0x0329, 0x032B,
-
- 0x032C, 0x032E, 0x032F, 0x0331, 0x0332, 0x0334, 0x0335, 0x0337,
- 0x0338, 0x033A, 0x033B, 0x033D, 0x033E, 0x0340, 0x0341, 0x0343,
- 0x0344, 0x0346, 0x0347, 0x0349, 0x034A, 0x034C, 0x034D, 0x034F,
- 0x0350, 0x0352, 0x0353, 0x0355, 0x0357, 0x0358, 0x035A, 0x035B,
-
- 0x035D, 0x035E, 0x0360, 0x0361, 0x0363, 0x0365, 0x0366, 0x0368,
- 0x0369, 0x036B, 0x036C, 0x036E, 0x0370, 0x0371, 0x0373, 0x0374,
- 0x0376, 0x0378, 0x0379, 0x037B, 0x037C, 0x037E, 0x0380, 0x0381,
- 0x0383, 0x0384, 0x0386, 0x0388, 0x0389, 0x038B, 0x038D, 0x038E,
-
- 0x0390, 0x0392, 0x0393, 0x0395, 0x0397, 0x0398, 0x039A, 0x039C,
- 0x039D, 0x039F, 0x03A1, 0x03A2, 0x03A4, 0x03A6, 0x03A7, 0x03A9,
- 0x03AB, 0x03AC, 0x03AE, 0x03B0, 0x03B1, 0x03B3, 0x03B5, 0x03B7,
- 0x03B8, 0x03BA, 0x03BC, 0x03BD, 0x03BF, 0x03C1, 0x03C3, 0x03C4,
-
- 0x03C6, 0x03C8, 0x03CA, 0x03CB, 0x03CD, 0x03CF, 0x03D1, 0x03D2,
- 0x03D4, 0x03D6, 0x03D8, 0x03DA, 0x03DB, 0x03DD, 0x03DF, 0x03E1,
- 0x03E3, 0x03E4, 0x03E6, 0x03E8, 0x03EA, 0x03EC, 0x03ED, 0x03EF,
- 0x03F1, 0x03F3, 0x03F5, 0x03F6, 0x03F8, 0x03FA, 0x03FC, 0x03FE,
-
- 0x036C
-};
-
-static inline double s_dmxFreq(double note, double bend)
-{
- uint_fast32_t noteI = (uint_fast32_t)(note + 0.5);
- int_fast32_t bendI = 0;
- int_fast32_t outHz = 0.0;
- double bendDec = bend - (int)bend;
-
- noteI += (int)bend;
-
- bendI = (int_fast32_t)((bendDec * 128.0) / 2.0) + 128;
- bendI = bendI >> 1;
-
- int_fast32_t oct = 0;
- int_fast32_t freqIndex = (noteI << 5) + bendI;
-
- if(freqIndex < 0)
- freqIndex = 0;
- else if(freqIndex >= 284)
- {
- freqIndex -= 284;
- oct = freqIndex / 384;
- freqIndex = (freqIndex % 384) + 284;
- }
-
- outHz = s_dmx_freq_table[freqIndex];
-
- while(oct > 1)
- {
- outHz *= 2;
- oct -= 1;
- }
-
- return (double)outHz;
-}
-
-
-
-
-/***************************************************************
- * Apogee Sound System frequency model *
- ***************************************************************/
-
-static const int_fast32_t s_apogee_freq_table[31 + 1][12] =
-{
- { 0x157, 0x16b, 0x181, 0x198, 0x1b0, 0x1ca, 0x1e5, 0x202, 0x220, 0x241, 0x263, 0x287 },
- { 0x157, 0x16b, 0x181, 0x198, 0x1b0, 0x1ca, 0x1e5, 0x202, 0x220, 0x242, 0x264, 0x288 },
- { 0x158, 0x16c, 0x182, 0x199, 0x1b1, 0x1cb, 0x1e6, 0x203, 0x221, 0x243, 0x265, 0x289 },
- { 0x158, 0x16c, 0x183, 0x19a, 0x1b2, 0x1cc, 0x1e7, 0x204, 0x222, 0x244, 0x266, 0x28a },
- { 0x159, 0x16d, 0x183, 0x19a, 0x1b3, 0x1cd, 0x1e8, 0x205, 0x223, 0x245, 0x267, 0x28b },
- { 0x15a, 0x16e, 0x184, 0x19b, 0x1b3, 0x1ce, 0x1e9, 0x206, 0x224, 0x246, 0x268, 0x28c },
- { 0x15a, 0x16e, 0x185, 0x19c, 0x1b4, 0x1ce, 0x1ea, 0x207, 0x225, 0x247, 0x269, 0x28e },
- { 0x15b, 0x16f, 0x185, 0x19d, 0x1b5, 0x1cf, 0x1eb, 0x208, 0x226, 0x248, 0x26a, 0x28f },
- { 0x15b, 0x170, 0x186, 0x19d, 0x1b6, 0x1d0, 0x1ec, 0x209, 0x227, 0x249, 0x26b, 0x290 },
- { 0x15c, 0x170, 0x187, 0x19e, 0x1b7, 0x1d1, 0x1ec, 0x20a, 0x228, 0x24a, 0x26d, 0x291 },
- { 0x15d, 0x171, 0x188, 0x19f, 0x1b7, 0x1d2, 0x1ed, 0x20b, 0x229, 0x24b, 0x26e, 0x292 },
- { 0x15d, 0x172, 0x188, 0x1a0, 0x1b8, 0x1d3, 0x1ee, 0x20c, 0x22a, 0x24c, 0x26f, 0x293 },
- { 0x15e, 0x172, 0x189, 0x1a0, 0x1b9, 0x1d4, 0x1ef, 0x20d, 0x22b, 0x24d, 0x270, 0x295 },
- { 0x15f, 0x173, 0x18a, 0x1a1, 0x1ba, 0x1d4, 0x1f0, 0x20e, 0x22c, 0x24e, 0x271, 0x296 },
- { 0x15f, 0x174, 0x18a, 0x1a2, 0x1bb, 0x1d5, 0x1f1, 0x20f, 0x22d, 0x24f, 0x272, 0x297 },
- { 0x160, 0x174, 0x18b, 0x1a3, 0x1bb, 0x1d6, 0x1f2, 0x210, 0x22e, 0x250, 0x273, 0x298 },
- { 0x161, 0x175, 0x18c, 0x1a3, 0x1bc, 0x1d7, 0x1f3, 0x211, 0x22f, 0x251, 0x274, 0x299 },
- { 0x161, 0x176, 0x18c, 0x1a4, 0x1bd, 0x1d8, 0x1f4, 0x212, 0x230, 0x252, 0x276, 0x29b },
- { 0x162, 0x176, 0x18d, 0x1a5, 0x1be, 0x1d9, 0x1f5, 0x212, 0x231, 0x254, 0x277, 0x29c },
- { 0x162, 0x177, 0x18e, 0x1a6, 0x1bf, 0x1d9, 0x1f5, 0x213, 0x232, 0x255, 0x278, 0x29d },
- { 0x163, 0x178, 0x18f, 0x1a6, 0x1bf, 0x1da, 0x1f6, 0x214, 0x233, 0x256, 0x279, 0x29e },
- { 0x164, 0x179, 0x18f, 0x1a7, 0x1c0, 0x1db, 0x1f7, 0x215, 0x235, 0x257, 0x27a, 0x29f },
- { 0x164, 0x179, 0x190, 0x1a8, 0x1c1, 0x1dc, 0x1f8, 0x216, 0x236, 0x258, 0x27b, 0x2a1 },
- { 0x165, 0x17a, 0x191, 0x1a9, 0x1c2, 0x1dd, 0x1f9, 0x217, 0x237, 0x259, 0x27c, 0x2a2 },
- { 0x166, 0x17b, 0x192, 0x1aa, 0x1c3, 0x1de, 0x1fa, 0x218, 0x238, 0x25a, 0x27e, 0x2a3 },
- { 0x166, 0x17b, 0x192, 0x1aa, 0x1c3, 0x1df, 0x1fb, 0x219, 0x239, 0x25b, 0x27f, 0x2a4 },
- { 0x167, 0x17c, 0x193, 0x1ab, 0x1c4, 0x1e0, 0x1fc, 0x21a, 0x23a, 0x25c, 0x280, 0x2a6 },
- { 0x168, 0x17d, 0x194, 0x1ac, 0x1c5, 0x1e0, 0x1fd, 0x21b, 0x23b, 0x25d, 0x281, 0x2a7 },
- { 0x168, 0x17d, 0x194, 0x1ad, 0x1c6, 0x1e1, 0x1fe, 0x21c, 0x23c, 0x25e, 0x282, 0x2a8 },
- { 0x169, 0x17e, 0x195, 0x1ad, 0x1c7, 0x1e2, 0x1ff, 0x21d, 0x23d, 0x260, 0x283, 0x2a9 },
- { 0x16a, 0x17f, 0x196, 0x1ae, 0x1c8, 0x1e3, 0x1ff, 0x21e, 0x23e, 0x261, 0x284, 0x2ab },
- { 0x16a, 0x17f, 0x197, 0x1af, 0x1c8, 0x1e4, 0x200, 0x21f, 0x23f, 0x262, 0x286, 0x2ac }
-};
-
-static inline double s_apogeeFreq(double note, double bend)
-{
- uint_fast32_t noteI = (uint_fast32_t)(note + 0.5);
- int_fast32_t bendI = 0;
- int_fast32_t outHz = 0.0;
- double bendDec = bend - (int)bend;
- int_fast32_t octave;
- int_fast32_t scaleNote;
-
- noteI += (int)bend;
- bendI = (int_fast32_t)(bendDec * 32) + 32;
-
- noteI += bendI / 32;
- noteI -= 1;
-
- scaleNote = noteI % 12;
- octave = noteI / 12;
-
- outHz = s_apogee_freq_table[bendI % 32][scaleNote];
-
- while(octave > 1)
- {
- outHz *= 2;
- octave -= 1;
- }
-
- return (double)outHz;
-}
-
-
-
-
-/***************************************************************
- * Windows 9x FM drivers frequency model *
- ***************************************************************/
-
-//static const double s_9x_opl_samplerate = 50000.0;
-//static const double s_9x_opl_tune = 440.0;
-static const uint_fast8_t s_9x_opl_pitchfrac = 8;
-
-static const uint_fast32_t s_9x_opl_freq[12] =
-{
- 0xAB7, 0xB5A, 0xC07, 0xCBE, 0xD80, 0xE4D, 0xF27, 0x100E, 0x1102, 0x1205, 0x1318, 0x143A
-};
-
-static const int32_t s_9x_opl_uppitch = 31;
-static const int32_t s_9x_opl_downpitch = 27;
-
-static uint_fast32_t s_9x_opl_applypitch(uint_fast32_t freq, int_fast32_t pitch)
-{
- int32_t diff;
-
- if(pitch > 0)
- {
- diff = (pitch * s_9x_opl_uppitch) >> s_9x_opl_pitchfrac;
- freq += (diff * freq) >> 15;
- }
- else if (pitch < 0)
- {
- diff = (-pitch * s_9x_opl_downpitch) >> s_9x_opl_pitchfrac;
- freq -= (diff * freq) >> 15;
- }
-
- return freq;
-}
-
-static inline double s_9xFreq(double noteD, double bendD)
-{
- uint_fast32_t note = (uint_fast32_t)(noteD + 0.5);
- int_fast32_t bend;
- double bendDec = bendD - (int)bendD; // 0.0 ± 1.0 - one halftone
-
- uint_fast32_t freq;
- uint_fast32_t freqpitched;
- uint_fast32_t octave;
-
- uint_fast32_t bendMsb;
- uint_fast32_t bendLsb;
-
- note += (int)bendD;
- bend = (int_fast32_t)(bendDec * 4096) + 8192; // convert to MIDI standard value
-
- bendMsb = (bend >> 7) & 0x7F;
- bendLsb = (bend & 0x7F);
-
- bend = (bendMsb << 9) | (bendLsb << 2);
- bend = (int16_t)(uint16_t)(bend + 0x8000);
-
- octave = note / 12;
- freq = s_9x_opl_freq[note % 12];
- if(octave < 5)
- freq >>= (5 - octave);
- else if (octave > 5)
- freq <<= (octave - 5);
-
- freqpitched = s_9x_opl_applypitch(freq, bend);
- freqpitched *= 2;
-
- return (double)freqpitched;
-}
-
-
-
-
-/***************************************************************
- * HMI Sound Operating System frequency model *
- ***************************************************************/
-
-const size_t s_hmi_freqtable_size = 103;
-static uint_fast32_t s_hmi_freqtable[s_hmi_freqtable_size] =
-{
- 0x0157, 0x016B, 0x0181, 0x0198, 0x01B0, 0x01CA, 0x01E5, 0x0202, 0x0220, 0x0241, 0x0263, 0x0287,
- 0x0557, 0x056B, 0x0581, 0x0598, 0x05B0, 0x05CA, 0x05E5, 0x0602, 0x0620, 0x0641, 0x0663, 0x0687,
- 0x0957, 0x096B, 0x0981, 0x0998, 0x09B0, 0x09CA, 0x09E5, 0x0A02, 0x0A20, 0x0A41, 0x0A63, 0x0A87,
- 0x0D57, 0x0D6B, 0x0D81, 0x0D98, 0x0DB0, 0x0DCA, 0x0DE5, 0x0E02, 0x0E20, 0x0E41, 0x0E63, 0x0E87,
- 0x1157, 0x116B, 0x1181, 0x1198, 0x11B0, 0x11CA, 0x11E5, 0x1202, 0x1220, 0x1241, 0x1263, 0x1287,
- 0x1557, 0x156B, 0x1581, 0x1598, 0x15B0, 0x15CA, 0x15E5, 0x1602, 0x1620, 0x1641, 0x1663, 0x1687,
- 0x1957, 0x196B, 0x1981, 0x1998, 0x19B0, 0x19CA, 0x19E5, 0x1A02, 0x1A20, 0x1A41, 0x1A63, 0x1A87,
- 0x1D57, 0x1D6B, 0x1D81, 0x1D98, 0x1DB0, 0x1DCA, 0x1DE5, 0x1E02, 0x1E20, 0x1E41, 0x1E63, 0x1E87,
- 0x1EAE, 0x1EB7, 0x1F02, 0x1F30, 0x1F60, 0x1F94, 0x1FCA
-};
-
-const size_t s_hmi_bendtable_size = 12;
-static uint_fast32_t s_hmi_bendtable[s_hmi_bendtable_size] =
-{
- 0x144, 0x132, 0x121, 0x110, 0x101, 0xf8, 0xe5, 0xd8, 0xcc, 0xc1, 0xb6, 0xac
-};
-
-#define hmi_range_fix(formula, maxVal) \
- ( \
- (formula) < 0 ? \
- 0 : \
- ( \
- (formula) >= (int32_t)maxVal ? \
- (int32_t)maxVal : \
- (formula) \
- )\
- )
-
-static uint_fast32_t s_hmi_bend_calc(uint_fast32_t bend, int_fast32_t note)
-{
- const int_fast32_t midi_bend_range = 1;
- uint_fast32_t bendFactor, outFreq, fmOctave, fmFreq, newFreq, idx;
- int_fast32_t noteMod12;
-
- note -= 12;
-// while(doNote >= 12) // ugly way to MOD 12
-// doNote -= 12;
- noteMod12 = (note % 12);
-
- outFreq = s_hmi_freqtable[note];
-
- fmOctave = outFreq & 0x1c00;
- fmFreq = outFreq & 0x3ff;
-
- if(bend < 64)
- {
- bendFactor = ((63 - bend) * 1000) >> 6;
-
- idx = hmi_range_fix(note - midi_bend_range, s_hmi_freqtable_size);
- newFreq = outFreq - s_hmi_freqtable[idx];
-
- if(newFreq > 719)
- {
- newFreq = fmFreq - s_hmi_bendtable[midi_bend_range - 1];
- newFreq &= 0x3ff;
- }
-
- newFreq = (newFreq * bendFactor) / 1000;
- outFreq -= newFreq;
- }
- else
- {
- bendFactor = ((bend - 64) * 1000) >> 6;
-
- idx = hmi_range_fix(note + midi_bend_range, s_hmi_freqtable_size);
- newFreq = s_hmi_freqtable[idx] - outFreq;
-
- if(newFreq > 719)
- {
- idx = hmi_range_fix(11 - noteMod12, s_hmi_bendtable_size);
- fmFreq = s_hmi_bendtable[idx];
- outFreq = (fmOctave + 1024) | fmFreq;
-
- idx = hmi_range_fix(note + midi_bend_range, s_hmi_freqtable_size);
- newFreq = s_hmi_freqtable[idx] - outFreq;
- }
-
- newFreq = (newFreq * bendFactor) / 1000;
- outFreq += newFreq;
- }
-
- return outFreq;
-}
-#undef hmi_range_fix
-
-static inline double s_hmiFreq(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 bend;
- uint_fast32_t inFreq;
- uint_fast32_t freq;
- int_fast32_t octave;
- int_fast32_t octaveOffset = 0;
-
- note += (int)bendD;
-
- bend = (int_fast32_t)(bendDec * 64.0) + 64;
-
- while(note < 12)
- {
- octaveOffset--;
- note += 12;
- }
- while(note > 114)
- {
- octaveOffset++;
- note -= 12;
- }
-
- if(bend == 64)
- inFreq = s_hmi_freqtable[note - 12];
- else
- inFreq = s_hmi_bend_calc(bend, note);
-
- freq = inFreq & 0x3FF;
- octave = (inFreq >> 10) & 0x07;
-
- octave += octaveOffset;
-
- while(octave > 0)
- {
- freq *= 2;
- octave -= 1;
- }
-
- return freq;
-}
-
-
-
-
-/***************************************************************
- * 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;
-}
-
-
-
-
enum { MasterVolumeDefault = 127 };
+
inline bool isXgPercChannel(uint8_t msb, uint8_t lsb)
{
return (msb == 0x7E || msb == 0x7F) && (lsb == 0);
@@ -1109,7 +533,7 @@ bool MIDIplay::realTime_NoteOn(uint8_t channel, uint8_t note, uint8_t velocity)
if(ccount == 0)
{
// Only use four-op master channels
- if(synth.m_channelCategory[a] != Synth::ChanCat_4op_Master)
+ if(synth.m_channelCategory[a] != Synth::ChanCat_4op_First)
continue;
}
else
@@ -1769,7 +1193,7 @@ void MIDIplay::noteUpdate(size_t midCh,
{
const MIDIchannel::NoteInfo::Phys &ins = info.chip_channels[ccount];
uint16_t c = ins.chip_chan;
- uint16_t c_slave = info.chip_channels[1].chip_chan;
+ uint16_t c_secondary = info.chip_channels[1].chip_chan;
if(select_adlchn >= 0 && c != select_adlchn)
continue;
@@ -1866,7 +1290,6 @@ void MIDIplay::noteUpdate(size_t midCh,
double bend = midibend + ins.ains.finetune;
double phase = 0.0;
uint8_t vibrato = std::max(chan.vibrato, chan.aftertouch);
- double finalFreq;
vibrato = std::max(vibrato, info.vibrato);
@@ -1878,39 +1301,7 @@ void MIDIplay::noteUpdate(size_t midCh,
if(vibrato && (d.is_end() || d->value.vibdelay_us >= chan.vibdelay_us))
bend += static_cast<double>(vibrato) * chan.vibdepth * std::sin(chan.vibpos);
- bend += phase;
-
- // Use different frequency formulas in depend on a volume model
- switch(synth.m_volumeScale)
- {
- case Synth::VOLUME_DMX:
- case Synth::VOLUME_DMX_FIXED:
- finalFreq = s_dmxFreq(currentTone, bend);
- break;
-
- case Synth::VOLUME_APOGEE:
- case Synth::VOLUME_APOGEE_FIXED:
- finalFreq = s_apogeeFreq(currentTone, bend);
- break;
-
- case Synth::VOLUME_9X:
- case Synth::VOLUME_9X_GENERIC_FM:
- finalFreq = s_9xFreq(currentTone, bend);
- break;
-
- case Synth::VOLUME_HMI:
- finalFreq = s_hmiFreq(currentTone, bend);
- break;
-
- case Synth::VOLUME_AIL:
- finalFreq = s_ailFreq(currentTone, bend);
- break;
-
- default:
- finalFreq = s_commonFreq(currentTone, bend);
- }
-
- synth.noteOn(c, c_slave, finalFreq);
+ synth.noteOn(c, c_secondary, currentTone + bend + phase);
if(hooks.onNote)
hooks.onNote(hooks.onNote_userData, c, noteTone, midiins, vol, midibend);
@@ -2471,8 +1862,8 @@ void MIDIplay::describeChannels(char *str, char *attr, size_t size)
case Synth::ChanCat_Regular:
str[index] = '+';
break;
- case Synth::ChanCat_4op_Master:
- case Synth::ChanCat_4op_Slave:
+ case Synth::ChanCat_4op_First:
+ case Synth::ChanCat_4op_Second:
str[index] = '#';
break;
default: // rhythm-mode percussion