2020-12-02 18:12:34 +01:00
|
|
|
#pragma once
|
2021-02-15 16:55:54 +01:00
|
|
|
|
2021-09-06 15:27:58 +02:00
|
|
|
constexpr uint32_t SwapByteOrderInt(uint32_t val)
|
2021-02-15 16:55:54 +01:00
|
|
|
{
|
2021-09-06 15:27:58 +02:00
|
|
|
return (val >> 24) |
|
|
|
|
((val << 8) & 0x00FF0000) |
|
|
|
|
((val >> 8) & 0x0000FF00) |
|
|
|
|
(val << 24);
|
|
|
|
}
|
|
|
|
|
|
|
|
constexpr uint16_t SwapByteOrderShort(uint16_t val)
|
|
|
|
{
|
|
|
|
return static_cast<uint16_t>((val >> 8) | (val << 8));
|
|
|
|
}
|
2021-02-15 16:55:54 +01:00
|
|
|
|
|
|
|
#pragma pack(push)
|
|
|
|
#pragma pack(1)
|
|
|
|
struct riff_block
|
|
|
|
{
|
2021-10-09 11:33:33 +02:00
|
|
|
uint32_t TkStart;
|
|
|
|
uint32_t CbBuffer;
|
2021-02-15 16:55:54 +01:00
|
|
|
char AData[4];
|
|
|
|
};
|
|
|
|
|
|
|
|
struct riff_data
|
|
|
|
{
|
2021-10-09 11:33:33 +02:00
|
|
|
uint32_t Data;
|
|
|
|
uint32_t DataSize;
|
|
|
|
uint32_t BlocksPerChunk;
|
2021-02-15 16:55:54 +01:00
|
|
|
riff_block Blocks[1];
|
|
|
|
};
|
|
|
|
|
|
|
|
struct riff_header
|
|
|
|
{
|
2021-10-09 11:33:33 +02:00
|
|
|
uint32_t Riff;
|
|
|
|
uint32_t FileSize;
|
|
|
|
uint32_t Mids;
|
|
|
|
uint32_t Fmt;
|
|
|
|
uint32_t FmtSize;
|
|
|
|
uint32_t dwTimeFormat;
|
|
|
|
uint32_t cbMaxBuffer;
|
|
|
|
uint32_t dwFlags;
|
2021-02-15 16:55:54 +01:00
|
|
|
riff_data Data;
|
|
|
|
};
|
|
|
|
|
2021-09-09 10:40:54 +02:00
|
|
|
struct midi_event
|
2021-09-06 15:27:58 +02:00
|
|
|
{
|
2021-10-09 11:33:33 +02:00
|
|
|
uint32_t iTicks;
|
|
|
|
uint32_t iEvent;
|
2021-09-06 15:27:58 +02:00
|
|
|
};
|
|
|
|
|
|
|
|
struct midi_header
|
|
|
|
{
|
|
|
|
explicit midi_header(uint16_t tickdiv)
|
|
|
|
: tickdiv(tickdiv)
|
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2021-09-29 16:53:49 +02:00
|
|
|
const char MThd[4]{'M', 'T', 'h', 'd'};
|
2021-09-06 15:27:58 +02:00
|
|
|
const uint32_t chunklen = SwapByteOrderInt(6);
|
|
|
|
const int16_t format = SwapByteOrderShort(0);
|
|
|
|
const uint16_t ntracks = SwapByteOrderShort(1);
|
|
|
|
uint16_t tickdiv;
|
|
|
|
};
|
|
|
|
|
|
|
|
struct midi_track
|
|
|
|
{
|
|
|
|
explicit midi_track(uint32_t chunklen)
|
|
|
|
: chunklen(chunklen)
|
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2021-09-29 16:53:49 +02:00
|
|
|
const char MTrk[4]{'M', 'T', 'r', 'k'};
|
2021-09-06 15:27:58 +02:00
|
|
|
uint32_t chunklen;
|
|
|
|
};
|
|
|
|
|
2021-02-15 16:55:54 +01:00
|
|
|
static_assert(sizeof(riff_block) == 0xC, "Wrong size of riff_block");
|
|
|
|
static_assert(sizeof(riff_data) == 0x18, "Wrong size of riff_data");
|
|
|
|
static_assert(sizeof(riff_header) == 0x38, "Wrong size of riff_header");
|
2021-09-09 10:40:54 +02:00
|
|
|
static_assert(sizeof(midi_event) == 8, "Wrong size of midi_event2");
|
2021-09-06 15:27:58 +02:00
|
|
|
static_assert(sizeof(midi_header) == 14, "Wrong size of midi_header");
|
|
|
|
static_assert(sizeof(midi_track) == 8, "Wrong size of midi_track");
|
|
|
|
|
2021-02-15 16:55:54 +01:00
|
|
|
#pragma pack(pop)
|
|
|
|
|
2022-05-23 11:45:18 +02:00
|
|
|
enum class MidiTracks
|
|
|
|
{
|
|
|
|
None,
|
|
|
|
Track1,
|
|
|
|
Track2,
|
|
|
|
Track3
|
|
|
|
};
|
|
|
|
|
2020-12-02 18:12:34 +01:00
|
|
|
class midi
|
|
|
|
{
|
|
|
|
public:
|
2022-12-02 12:46:22 +01:00
|
|
|
static int music_init(bool mixOpen, int volume);
|
2021-01-23 11:33:30 +01:00
|
|
|
static void music_shutdown();
|
2022-05-23 11:45:18 +02:00
|
|
|
static void music_play();
|
|
|
|
static void music_stop();
|
2022-01-12 15:17:38 +01:00
|
|
|
static void SetVolume(int volume);
|
2022-05-23 11:45:18 +02:00
|
|
|
static bool play_track(MidiTracks track, bool replay);
|
|
|
|
static MidiTracks get_active_track();
|
2021-09-06 15:27:58 +02:00
|
|
|
private:
|
2021-10-01 17:55:44 +02:00
|
|
|
static std::vector<Mix_Music*> LoadedTracks;
|
2022-05-23 11:45:18 +02:00
|
|
|
static Mix_Music* track1, * track2, * track3;
|
|
|
|
static MidiTracks active_track, NextTrack;
|
2022-01-12 15:17:38 +01:00
|
|
|
static int Volume;
|
2022-12-02 12:46:22 +01:00
|
|
|
static bool IsPlaying, MixOpen;
|
2022-01-12 15:17:38 +01:00
|
|
|
|
2022-05-20 18:32:09 +02:00
|
|
|
static void StopPlayback();
|
2021-09-30 07:51:48 +02:00
|
|
|
static Mix_Music* load_track(std::string fileName);
|
2022-11-22 10:40:50 +01:00
|
|
|
static Mix_Music* load_track_sub(std::string fileName, bool isMidi);
|
2022-05-23 11:45:18 +02:00
|
|
|
static Mix_Music* TrackToMidi(MidiTracks track);
|
2021-09-14 14:33:18 +02:00
|
|
|
static std::vector<uint8_t>* MdsToMidi(std::string file);
|
2020-12-02 18:12:34 +01:00
|
|
|
};
|