31 |
#include "helper.h" |
#include "helper.h" |
32 |
#include <math.h> |
#include <math.h> |
33 |
|
|
34 |
#define _1200TH_ROOT_OF_2 1.0005777900 |
#define _1200TH_ROOT_OF_2 1.000577789506555 |
35 |
|
#define _200TH_ROOT_OF_10 1.011579454259899 |
36 |
|
|
37 |
namespace sf2 { |
namespace sf2 { |
38 |
double ToSeconds(int Timecents) { |
double ToSeconds(int Timecents) { |
41 |
return pow(_1200TH_ROOT_OF_2, Timecents); |
return pow(_1200TH_ROOT_OF_2, Timecents); |
42 |
} |
} |
43 |
|
|
44 |
|
double ToPermilles(int Centibels) { |
45 |
|
if (Centibels == 0) return 1000.0; |
46 |
|
if (Centibels < 0) return 0.0; |
47 |
|
return pow(_200TH_ROOT_OF_10, Centibels); |
48 |
|
} |
49 |
|
|
50 |
RIFF::Chunk* GetMandatoryChunk(RIFF::List* list, uint32_t chunkId) { |
RIFF::Chunk* GetMandatoryChunk(RIFF::List* list, uint32_t chunkId) { |
51 |
RIFF::Chunk* ck = list->GetSubChunk(chunkId); |
RIFF::Chunk* ck = list->GetSubChunk(chunkId); |
52 |
if(ck == NULL) throw Exception("Mandatory chunk in RIFF list chunk not found: " + ToString(chunkId)); |
if(ck == NULL) throw Exception("Mandatory chunk in RIFF list chunk not found: " + ToString(chunkId)); |
196 |
return ChannelCount * ((pCkSm24 != NULL) ? 3 : 2); |
return ChannelCount * ((pCkSm24 != NULL) ? 3 : 2); |
197 |
} |
} |
198 |
|
|
199 |
|
bool Sample::HasLoops() { |
200 |
|
return StartLoop != 0 && EndLoop != 0; |
201 |
|
} |
202 |
|
|
203 |
/** |
/** |
204 |
* Reads \a SampleCount number of sample points from the position stored |
* Reads \a SampleCount number of sample points from the position stored |
205 |
* in \a pPlaybackState into the buffer pointed by \a pBuffer and moves |
* in \a pPlaybackState into the buffer pointed by \a pBuffer and moves |
231 |
unsigned long FrameCount, |
unsigned long FrameCount, |
232 |
PlaybackState* pPlaybackState |
PlaybackState* pPlaybackState |
233 |
) { |
) { |
234 |
// TODO: |
SetPos(pPlaybackState->position); |
235 |
return 0; |
long frames = Read(pBuffer, FrameCount); |
236 |
|
pPlaybackState->position = GetPos(); |
237 |
|
// TODO: Implement looping |
238 |
|
return frames; |
239 |
} |
} |
240 |
|
|
241 |
Region::Region() { |
Region::Region() { |
247 |
startloopAddrsOffset = endloopAddrsOffset = 0; |
startloopAddrsOffset = endloopAddrsOffset = 0; |
248 |
pan = fineTune = 0; |
pan = fineTune = 0; |
249 |
|
|
250 |
EG1PreAttack = EG1Attack = EG1Hold = EG1Decay = EG1Release = ToSeconds(-12000); |
EG1PreAttackDelay = EG1Attack = EG1Hold = EG1Decay = EG1Release = ToSeconds(-12000); |
251 |
EG1Sustain = 0; |
EG1Sustain = 0; |
252 |
|
EG2PreAttackDelay = EG2Attack = EG2Hold = EG2Decay = EG2Release = ToSeconds(-12000); |
253 |
|
EG2Sustain = 0; |
254 |
} |
} |
255 |
|
|
256 |
void Region::SetGenerator(sf2::File* pFile, GenList& Gen) { |
void Region::SetGenerator(sf2::File* pFile, GenList& Gen) { |
311 |
case FREQ_VIB_LFO: |
case FREQ_VIB_LFO: |
312 |
break; |
break; |
313 |
case DELAY_MOD_ENV: |
case DELAY_MOD_ENV: |
314 |
|
EG2PreAttackDelay = ToSeconds(Gen.GenAmount.shAmount); |
315 |
break; |
break; |
316 |
case ATTACK_MOD_ENV: |
case ATTACK_MOD_ENV: |
317 |
|
EG2Attack = ToSeconds(Gen.GenAmount.shAmount); |
318 |
break; |
break; |
319 |
case HOLD_MOD_ENV: |
case HOLD_MOD_ENV: |
320 |
|
EG2Hold = ToSeconds(Gen.GenAmount.shAmount); |
321 |
break; |
break; |
322 |
case DECAY_MOD_ENV: |
case DECAY_MOD_ENV: |
323 |
|
EG2Decay = ToSeconds(Gen.GenAmount.shAmount); |
324 |
break; |
break; |
325 |
case SUSTAIN_MOD_ENV: |
case SUSTAIN_MOD_ENV: |
326 |
|
EG2Sustain = 1000 - Gen.GenAmount.shAmount; |
327 |
break; |
break; |
328 |
case RELEASEMODENV: |
case RELEASEMODENV: |
329 |
|
EG2Release = ToSeconds(Gen.GenAmount.shAmount); |
330 |
break; |
break; |
331 |
case KEYNUM_TO_MOD_ENV_HOLD: |
case KEYNUM_TO_MOD_ENV_HOLD: |
332 |
break; |
break; |
333 |
case KEYNUM_TO_MOD_ENV_DECAY: |
case KEYNUM_TO_MOD_ENV_DECAY: |
334 |
break; |
break; |
335 |
case DELAY_VOL_ENV: |
case DELAY_VOL_ENV: |
336 |
EG1PreAttack = ToSeconds(Gen.GenAmount.shAmount); |
EG1PreAttackDelay = ToSeconds(Gen.GenAmount.shAmount); |
337 |
break; |
break; |
338 |
case ATTACK_VOL_ENV: |
case ATTACK_VOL_ENV: |
339 |
EG1Attack = ToSeconds(Gen.GenAmount.shAmount); |
EG1Attack = ToSeconds(Gen.GenAmount.shAmount); |
345 |
EG1Decay = ToSeconds(Gen.GenAmount.shAmount); |
EG1Decay = ToSeconds(Gen.GenAmount.shAmount); |
346 |
break; |
break; |
347 |
case SUSTAIN_VOL_ENV: |
case SUSTAIN_VOL_ENV: |
348 |
EG1Sustain = Gen.GenAmount.shAmount; |
EG1Sustain = ToPermilles(Gen.GenAmount.shAmount); |
349 |
break; |
break; |
350 |
case RELEASE_VOL_ENV: |
case RELEASE_VOL_ENV: |
351 |
EG1Release = ToSeconds(Gen.GenAmount.shAmount); |
EG1Release = ToSeconds(Gen.GenAmount.shAmount); |
639 |
ml.ModTransOper = ck->ReadInt16(); |
ml.ModTransOper = ck->ReadInt16(); |
640 |
PresetModLists.push_back(ml); |
PresetModLists.push_back(ml); |
641 |
} |
} |
642 |
std::cout << "Preset mod lists: " << PresetModLists.size() << std::endl; |
//std::cout << "Preset mod lists: " << PresetModLists.size() << std::endl; |
643 |
|
|
644 |
ck = GetMandatoryChunk(lstPDTA, CHUNK_ID_PGEN); |
ck = GetMandatoryChunk(lstPDTA, CHUNK_ID_PGEN); |
645 |
if (ck->GetSize() < 4 || (ck->GetSize() % 4)) { |
if (ck->GetSize() < 4 || (ck->GetSize() % 4)) { |
693 |
ml.ModTransOper = ck->ReadInt16(); |
ml.ModTransOper = ck->ReadInt16(); |
694 |
InstModLists.push_back(ml); |
InstModLists.push_back(ml); |
695 |
} |
} |
696 |
std::cout << "Instrument mod lists: " << InstModLists.size() << std::endl; |
//std::cout << "Instrument mod lists: " << InstModLists.size() << std::endl; |
697 |
|
|
698 |
ck = GetMandatoryChunk(lstPDTA, CHUNK_ID_IGEN); |
ck = GetMandatoryChunk(lstPDTA, CHUNK_ID_IGEN); |
699 |
if (ck->GetSize() < 4 || (ck->GetSize() % 4)) { |
if (ck->GetSize() < 4 || (ck->GetSize() % 4)) { |