00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #ifndef __DLS_H__
00025 #define __DLS_H__
00026
00027 #include "RIFF.h"
00028
00029 #if WORDS_BIGENDIAN
00030 # define RIFF_TYPE_DLS 0x444C5320
00031 # define LIST_TYPE_WVPL 0x7776706C
00032 # define LIST_TYPE_DWPL 0x6477706C
00033 # define LIST_TYPE_WAVE 0x77617665
00034 # define LIST_TYPE_LINS 0X6C696E73
00035 # define LIST_TYPE_INS 0X696E7320
00036 # define LIST_TYPE_LRGN 0x6C72676E
00037 # define LIST_TYPE_LART 0x6C617274
00038 # define LIST_TYPE_LAR2 0x6C617232
00039 # define LIST_TYPE_RGN 0x72676E20
00040 # define LIST_TYPE_RGN2 0x72676E32
00041 # define CHUNK_ID_IARL 0x4941524C
00042 # define CHUNK_ID_IART 0x49415254
00043 # define CHUNK_ID_ICMS 0x49434D53
00044 # define CHUNK_ID_IGNR 0x49474E52
00045 # define CHUNK_ID_IKEY 0x494B4559
00046 # define CHUNK_ID_IMED 0x494D4544
00047 # define CHUNK_ID_ISBJ 0x4953424A
00048 # define CHUNK_ID_ISRC 0x49535243
00049 # define CHUNK_ID_ISRF 0x49535246
00050 # define CHUNK_ID_ITCH 0x49544348
00051 # define CHUNK_ID_VERS 0x76657273
00052 # define CHUNK_ID_DLID 0x646C6964
00053 # define CHUNK_ID_FMT 0x666D7420
00054 # define CHUNK_ID_DATA 0x64617461
00055 # define CHUNK_ID_INSH 0x696E7368
00056 # define CHUNK_ID_RGNH 0x72676E68
00057 # define CHUNK_ID_WLNK 0x776C6E6B
00058 # define CHUNK_ID_PTBL 0x7074626C
00059 # define CHUNK_ID_WSMP 0x77736D70
00060 # define CHUNK_ID_COLH 0x636F6C68
00061 # define CHUNK_ID_ARTL 0x6172746C
00062 # define CHUNK_ID_ART2 0x61727432
00063 #else // little endian
00064 # define RIFF_TYPE_DLS 0x20534C44
00065 # define LIST_TYPE_WVPL 0x6C707677
00066 # define LIST_TYPE_DWPL 0x6C707764
00067 # define LIST_TYPE_WAVE 0x65766177
00068 # define LIST_TYPE_LINS 0X736E696C
00069 # define LIST_TYPE_INS 0X20736E69
00070 # define LIST_TYPE_LRGN 0x6E67726C
00071 # define LIST_TYPE_LART 0x7472616C
00072 # define LIST_TYPE_LAR2 0x3272616C
00073 # define LIST_TYPE_RGN 0x206E6772
00074 # define LIST_TYPE_RGN2 0x326E6772
00075 # define CHUNK_ID_IARL 0x4C524149
00076 # define CHUNK_ID_IART 0x54524149
00077 # define CHUNK_ID_ICMS 0x534D4349
00078 # define CHUNK_ID_IGNR 0x524E4749
00079 # define CHUNK_ID_IKEY 0x59454B49
00080 # define CHUNK_ID_IMED 0x44454D49
00081 # define CHUNK_ID_ISBJ 0x4A425349
00082 # define CHUNK_ID_ISRC 0x43525349
00083 # define CHUNK_ID_ISRF 0x46525349
00084 # define CHUNK_ID_ITCH 0x48435449
00085 # define CHUNK_ID_VERS 0x73726576
00086 # define CHUNK_ID_DLID 0x64696C64
00087 # define CHUNK_ID_FMT 0x20746D66
00088 # define CHUNK_ID_DATA 0x61746164
00089 # define CHUNK_ID_INSH 0x68736E69
00090 # define CHUNK_ID_RGNH 0x686E6772
00091 # define CHUNK_ID_WLNK 0x6B6E6C77
00092 # define CHUNK_ID_PTBL 0x6C627470
00093 # define CHUNK_ID_WSMP 0x706D7377
00094 # define CHUNK_ID_COLH 0x686C6F63
00095 # define CHUNK_ID_ARTL 0x6C747261
00096 # define CHUNK_ID_ART2 0x32747261
00097 #endif // WORDS_BIGENDIAN
00098
00099 #define DLS_WAVE_FORMAT_PCM 0x0001
00100
00101
00102
00104 namespace DLS {
00105
00106 typedef std::string String;
00107
00109 struct version_t {
00110 uint16_t minor;
00111 uint16_t major;
00112 uint16_t build;
00113 uint16_t release;
00114 };
00115
00117 struct dlsid_t {
00118 uint32_t ulData1;
00119 uint16_t usData2;
00120 uint16_t usData3;
00121 uint8_t abData[8];
00122 };
00123
00125 typedef enum {
00126
00127 conn_src_none = 0x0000,
00128 conn_src_lfo = 0x0001,
00129 conn_src_keyonvelocity = 0x0002,
00130 conn_src_keynumber = 0x0003,
00131 conn_src_eg1 = 0x0004,
00132 conn_src_eg2 = 0x0005,
00133 conn_src_pitchwheel = 0x0006,
00134 conn_src_polypressure = 0x0007,
00135 conn_src_channelpressure = 0x0008,
00136 conn_src_vibrato = 0x0009,
00137
00138 conn_src_cc1 = 0x0081,
00139 conn_src_cc7 = 0x0087,
00140 conn_src_cc10 = 0x008A,
00141 conn_src_cc11 = 0x008B,
00142 conn_src_cc91 = 0x00DB,
00143 conn_src_cc93 = 0x00DD,
00144
00145 conn_src_rpn0 = 0x0100,
00146 conn_src_rpn1 = 0x0101,
00147 conn_src_rpn2 = 0x0102
00148 } conn_src_t;
00149
00151 typedef enum {
00152
00153 conn_dst_none = 0x0000,
00154 conn_dst_gain = 0x0001,
00155 conn_dst_reserved = 0x0002,
00156 conn_dst_pitch = 0x0003,
00157 conn_dst_pan = 0x0004,
00158 conn_dst_keynumber = 0x0005,
00159
00160 conn_dst_left = 0x0010,
00161 conn_dst_right = 0x0011,
00162 conn_dst_center = 0x0012,
00163 conn_dst_lfe_channel = 0x0013,
00164 conn_dst_leftrear = 0x0014,
00165 conn_dst_rightrear = 0x0015,
00166 conn_dst_chorus = 0x0080,
00167 conn_dst_reverb = 0x0081,
00168
00169 conn_dst_lfo_frequency = 0x0104,
00170 conn_dst_lfo_startdelay = 0x0105,
00171
00172 conn_dst_vib_frequency = 0x0114,
00173 conn_dst_vib_startdelay = 0x0115,
00174
00175 conn_dst_eg1_attacktime = 0x0206,
00176 conn_dst_eg1_decaytime = 0x0207,
00177 conn_dst_eg1_reserved = 0x0208,
00178 conn_dst_eg1_releasetime = 0x0209,
00179 conn_dst_eg1_sustainlevel = 0x020A,
00180 conn_dst_eg1_delaytime = 0x020B,
00181 conn_dst_eg1_holdtime = 0x020C,
00182 conn_dst_eg1_shutdowntime = 0x020D,
00183 conn_dst_eg2_attacktime = 0x030A,
00184 conn_dst_eg2_decaytime = 0x030B,
00185 conn_dst_eg2_reserved = 0x030C,
00186 conn_dst_eg2_releasetime = 0x030D,
00187 conn_dst_eg2_sustainlevel = 0x030E,
00188 conn_dst_eg2_delaytime = 0x030F,
00189 conn_dst_eg2_holdtime = 0x0310,
00190
00191 conn_dst_filter_cutoff = 0x0500,
00192 conn_dst_filter_q = 0x0501
00193 } conn_dst_t;
00194
00196 typedef enum {
00197 conn_trn_none = 0x0000,
00198 conn_trn_concave = 0x0001,
00199 conn_trn_convex = 0x0002,
00200 conn_trn_switch = 0x0003
00201 } conn_trn_t;
00202
00204 struct range_t {
00205 uint16_t low;
00206 uint16_t high;
00207 };
00208
00210 struct sample_loop_t {
00211 uint32_t Size;
00212 uint32_t LoopType;
00213 uint32_t LoopStart;
00214 uint32_t LoopLength;
00215 };
00216
00217
00218 class File;
00219 class Instrument;
00220 class Region;
00221 class Sample;
00222
00224 class Connection {
00225 public:
00226 conn_src_t Source;
00227 conn_trn_t SourceTransform;
00228 bool SourceInvert;
00229 bool SourceBipolar;
00230 conn_src_t Control;
00231 conn_trn_t ControlTransform;
00232 bool ControlInvert;
00233 bool ControlBipolar;
00234 conn_dst_t Destination;
00235 conn_trn_t DestinationTransform;
00236 uint32_t Scale;
00237 protected:
00238 struct conn_block_t {
00239 uint16_t source;
00240 uint16_t control;
00241 uint16_t destination;
00242 uint16_t transform;
00243 uint32_t scale;
00244 };
00245 Connection() {}
00246 void Init(conn_block_t* Header);
00247 conn_block_t ToConnBlock();
00248 virtual ~Connection() {}
00249 friend class Articulation;
00250 };
00251
00253 class Articulation {
00254 public:
00255 Connection* pConnections;
00256 uint32_t Connections;
00257
00258 Articulation(RIFF::Chunk* artl);
00259 virtual ~Articulation();
00260 virtual void UpdateChunks();
00261 protected:
00262 RIFF::Chunk* pArticulationCk;
00263 uint32_t HeaderSize;
00264 };
00265
00267 class Articulator {
00268 public:
00269 Articulator(RIFF::List* ParentList);
00270 Articulation* GetFirstArticulation();
00271 Articulation* GetNextArticulation();
00272 virtual void UpdateChunks();
00273 protected:
00274 typedef std::list<Articulation*> ArticulationList;
00275 RIFF::List* pParentList;
00276 ArticulationList* pArticulations;
00277 ArticulationList::iterator ArticulationsIterator;
00278
00279 void LoadArticulations();
00280 virtual ~Articulator();
00281 };
00282
00284 class Info {
00285 public:
00286 String Name;
00287 String ArchivalLocation;
00288 String CreationDate;
00289 String Comments;
00290 String Product;
00291 String Copyright;
00292 String Artists;
00293 String Genre;
00294 String Keywords;
00295 String Engineer;
00296 String Technician;
00297 String Software;
00298 String Medium;
00299 String Source;
00300 String SourceForm;
00301 String Commissioned;
00302 String Subject;
00303 bool UseFixedLengthStrings;
00304
00305 struct string_length_t {
00306 uint32_t chunkId;
00307 int length;
00308 };
00309
00310 Info(RIFF::List* list);
00311 void SetFixedStringLengths(const string_length_t* lengths);
00312 virtual ~Info();
00313 virtual void UpdateChunks();
00314 private:
00315 RIFF::List* pResourceListChunk;
00316 const string_length_t* pFixedStringLengths;
00317
00318 static void LoadString(uint32_t ChunkID, RIFF::List* lstINFO, String& s);
00319 void SaveString(uint32_t ChunkID, RIFF::List* lstINFO, const String& s, const String& sDefault);
00320 };
00321
00323 class Resource {
00324 public:
00325 Info* pInfo;
00326 dlsid_t* pDLSID;
00327
00328 Resource* GetParent() { return pParent; }
00329 virtual void UpdateChunks();
00330 void GenerateDLSID();
00331 protected:
00332 Resource* pParent;
00333 RIFF::List* pResourceList;
00334
00335 Resource(Resource* Parent, RIFF::List* lstResource);
00336 virtual ~Resource();
00337 };
00338
00340 class Sampler {
00341 public:
00342 uint8_t UnityNote;
00343 int16_t FineTune;
00344 int32_t Gain;
00345 bool NoSampleDepthTruncation;
00346 bool NoSampleCompression;
00347 uint32_t SampleLoops;
00348 sample_loop_t* pSampleLoops;
00349
00350 void AddSampleLoop(sample_loop_t* pLoopDef);
00351 void DeleteSampleLoop(sample_loop_t* pLoopDef);
00352 virtual void SetGain(int32_t gain);
00353 virtual void UpdateChunks();
00354 protected:
00355 RIFF::List* pParentList;
00356 uint32_t uiHeaderSize;
00357 uint32_t SamplerOptions;
00358 Sampler(RIFF::List* ParentList);
00359 virtual ~Sampler();
00360 };
00361
00370 class Sample : public Resource {
00371 public:
00372 uint16_t FormatTag;
00373 uint16_t Channels;
00374 uint32_t SamplesPerSecond;
00375 uint32_t AverageBytesPerSecond;
00376 uint16_t BlockAlign;
00377 uint16_t BitDepth;
00378 unsigned long SamplesTotal;
00379 uint FrameSize;
00380
00381 void* LoadSampleData();
00382 void ReleaseSampleData();
00383 unsigned long GetSize();
00384 void Resize(int iNewSize);
00385 unsigned long SetPos(unsigned long SampleCount, RIFF::stream_whence_t Whence = RIFF::stream_start);
00386 unsigned long Read(void* pBuffer, unsigned long SampleCount);
00387 unsigned long Write(void* pBuffer, unsigned long SampleCount);
00388 virtual void UpdateChunks();
00389 protected:
00390 RIFF::List* pWaveList;
00391 RIFF::Chunk* pCkData;
00392 RIFF::Chunk* pCkFormat;
00393 unsigned long ulWavePoolOffset;
00394
00395 Sample(File* pFile, RIFF::List* waveList, unsigned long WavePoolOffset);
00396 virtual ~Sample();
00397 friend class File;
00398 friend class Region;
00399 };
00400
00402 class Region : public Resource, public Articulator, public Sampler {
00403 public:
00404 range_t KeyRange;
00405 range_t VelocityRange;
00406 uint16_t KeyGroup;
00407 uint16_t Layer;
00408 bool SelfNonExclusive;
00409 bool PhaseMaster;
00410 uint16_t PhaseGroup;
00411 bool MultiChannel;
00412 uint32_t Channel;
00413
00414 Sample* GetSample();
00415 void SetSample(Sample* pSample);
00416 virtual void SetKeyRange(uint16_t Low, uint16_t High);
00417 virtual void UpdateChunks();
00418 protected:
00419 RIFF::List* pCkRegion;
00420 uint32_t WavePoolTableIndex;
00421 Sample* pSample;
00422 uint16_t FormatOptionFlags;
00423 uint16_t WaveLinkOptionFlags;
00424
00425 Region(Instrument* pInstrument, RIFF::List* rgnList);
00426 virtual ~Region();
00427 friend class Instrument;
00428 };
00429
00431 class Instrument : public Resource, public Articulator {
00432 public:
00433 bool IsDrum;
00434 uint16_t MIDIBank;
00435 uint8_t MIDIBankCoarse;
00436 uint8_t MIDIBankFine;
00437 uint32_t MIDIProgram;
00438 uint32_t Regions;
00439
00440 Region* GetFirstRegion();
00441 Region* GetNextRegion();
00442 Region* AddRegion();
00443 void DeleteRegion(Region* pRegion);
00444 virtual void UpdateChunks();
00445 protected:
00446 typedef std::list<Region*> RegionList;
00447 struct midi_locale_t {
00448 uint32_t bank;
00449 uint32_t instrument;
00450 };
00451
00452 RIFF::List* pCkInstrument;
00453 RegionList* pRegions;
00454 RegionList::iterator RegionsIterator;
00455
00456 Instrument(File* pFile, RIFF::List* insList);
00457 virtual void LoadRegions();
00458 virtual ~Instrument();
00459 friend class File;
00460 friend class Region;
00461 private:
00462 void MoveRegion(Region* pSrc, Region* pDst);
00463 };
00464
00466 class File : public Resource {
00467 public:
00468 version_t* pVersion;
00469 uint32_t Instruments;
00470
00471 File();
00472 File(RIFF::File* pRIFF);
00473 Sample* GetFirstSample();
00474 Sample* GetNextSample();
00475 Sample* AddSample();
00476 void DeleteSample(Sample* pSample);
00477 Instrument* GetFirstInstrument();
00478 Instrument* GetNextInstrument();
00479 Instrument* AddInstrument();
00480 void DeleteInstrument(Instrument* pInstrument);
00481 virtual void UpdateChunks();
00482 virtual void Save(const String& Path);
00483 virtual void Save();
00484 virtual ~File();
00485 protected:
00486 typedef std::list<Sample*> SampleList;
00487 typedef std::list<Instrument*> InstrumentList;
00488
00489 RIFF::File* pRIFF;
00490 std::list<RIFF::File*> ExtensionFiles;
00491 SampleList* pSamples;
00492 SampleList::iterator SamplesIterator;
00493 InstrumentList* pInstruments;
00494 InstrumentList::iterator InstrumentsIterator;
00495 uint32_t WavePoolHeaderSize;
00496 uint32_t WavePoolCount;
00497 uint32_t* pWavePoolTable;
00498 uint32_t* pWavePoolTableHi;
00499 bool b64BitWavePoolOffsets;
00500
00501 virtual void LoadSamples();
00502 virtual void LoadInstruments();
00503 void __ensureMandatoryChunksExist();
00504 friend class Region;
00505 private:
00506 void __UpdateWavePoolTableChunk();
00507 void __UpdateWavePoolTable();
00508 };
00509
00517 class Exception : public RIFF::Exception {
00518 public:
00519 Exception(String Message);
00520 void PrintMessage();
00521 };
00522
00523 String libraryName();
00524 String libraryVersion();
00525
00526 }
00527
00528 #endif // __DLS_H__