From: <sag...@us...> - 2009-08-09 23:08:05
|
Revision: 318 http://modplug.svn.sourceforge.net/modplug/?rev=318&view=rev Author: saga-games Date: 2009-08-09 23:07:50 +0000 (Sun, 09 Aug 2009) Log Message: ----------- [New] Rearrange samples is back! And this time, it's even fully functional! [New] Started support for Image Orpheus modules. Does not work yet. [New] XM Compatibility Export [Fix] Fixed crash in instrument view that occured if RowsPerBeat was 0 [Imp] XM Compatibility: Using MilkyTracker's arpeggio logic for better XM arpeggio compatibility - still not perfect! [Imp] Compatibility: Updated several mod specifications [Imp] Pattern Editor: Showing descriptions of "special" notes in the statusbar, like it's done for effects [Imp] Module Conversion: Convert E9x to Q8x as Q0x actually means "continue" and note "no change" for the volume change [Imp] Module Creation: MOD files have 4 channels by default. [Imp] IT Loading: Detect more version of MPT that did stupid things [Imp] IT Compatibility Export: Save with custom "tracker version" header field (same as for S3M). [Ref] Renamed nC4Speed to nC5Speed as that's what it actually is. [Ref] Added "hasComments" to mod specifications [Ref] Usage of "NOTE_NONE" constant instead of "0" in many places [Ref] Shuffled around Parameter Control and Note Fade commands [Ref] More replacement of BOOL/TRUE/FALSE by bool/true/false [Ref] Using song flag for "break to row occured" instead of a seperate boolean variable Modified Paths: -------------- trunk/OpenMPT/mptrack/Ctrl_com.cpp trunk/OpenMPT/mptrack/Ctrl_smp.cpp trunk/OpenMPT/mptrack/Draw_pat.cpp trunk/OpenMPT/mptrack/Moddoc.cpp trunk/OpenMPT/mptrack/Moddoc.h trunk/OpenMPT/mptrack/Modedit.cpp trunk/OpenMPT/mptrack/Mpt_midi.cpp trunk/OpenMPT/mptrack/Mptrack.h trunk/OpenMPT/mptrack/View_ins.cpp trunk/OpenMPT/mptrack/View_pat.cpp trunk/OpenMPT/mptrack/View_smp.cpp trunk/OpenMPT/mptrack/dlg_misc.cpp trunk/OpenMPT/mptrack/dlg_misc.h trunk/OpenMPT/mptrack/mptrack.rc trunk/OpenMPT/mptrack/mptrack.vcproj trunk/OpenMPT/mptrack/mptrack_08.vcproj trunk/OpenMPT/mptrack/resource.h trunk/OpenMPT/mptrack/view_com.cpp trunk/OpenMPT/soundlib/Dlsbank.cpp trunk/OpenMPT/soundlib/LOAD_AMF.CPP trunk/OpenMPT/soundlib/LOAD_DBM.CPP trunk/OpenMPT/soundlib/LOAD_DMF.CPP trunk/OpenMPT/soundlib/LOAD_DSM.CPP trunk/OpenMPT/soundlib/Load_669.cpp trunk/OpenMPT/soundlib/Load_ams.cpp trunk/OpenMPT/soundlib/Load_far.cpp trunk/OpenMPT/soundlib/Load_gdm.cpp trunk/OpenMPT/soundlib/Load_it.cpp trunk/OpenMPT/soundlib/Load_mdl.cpp trunk/OpenMPT/soundlib/Load_med.cpp trunk/OpenMPT/soundlib/Load_mid.cpp trunk/OpenMPT/soundlib/Load_mo3.cpp trunk/OpenMPT/soundlib/Load_mod.cpp trunk/OpenMPT/soundlib/Load_mt2.cpp trunk/OpenMPT/soundlib/Load_mtm.cpp trunk/OpenMPT/soundlib/Load_okt.cpp trunk/OpenMPT/soundlib/Load_psm.cpp trunk/OpenMPT/soundlib/Load_ptm.cpp trunk/OpenMPT/soundlib/Load_s3m.cpp trunk/OpenMPT/soundlib/Load_stm.cpp trunk/OpenMPT/soundlib/Load_ult.cpp trunk/OpenMPT/soundlib/Load_umx.cpp trunk/OpenMPT/soundlib/Load_wav.cpp trunk/OpenMPT/soundlib/Load_xm.cpp trunk/OpenMPT/soundlib/Sampleio.cpp trunk/OpenMPT/soundlib/Snd_fx.cpp trunk/OpenMPT/soundlib/Sndfile.cpp trunk/OpenMPT/soundlib/Sndfile.h trunk/OpenMPT/soundlib/Sndmix.cpp trunk/OpenMPT/soundlib/mod_specifications.h trunk/OpenMPT/soundlib/modcommand.h trunk/OpenMPT/soundlib/modsmp_ctrl.cpp Added Paths: ----------- trunk/OpenMPT/soundlib/Load_imf.cpp Modified: trunk/OpenMPT/mptrack/Ctrl_com.cpp =================================================================== --- trunk/OpenMPT/mptrack/Ctrl_com.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Ctrl_com.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -139,7 +139,7 @@ } if (dwHint & HINT_MODTYPE) { - m_EditComments.SetReadOnly((m_pSndFile->m_nType & (MOD_TYPE_MOD|MOD_TYPE_S3M)) ? TRUE : FALSE); + m_EditComments.SetReadOnly(!m_pSndFile->GetModSpecifications().hasComments); } m_EditComments.SetRedraw(TRUE); Modified: trunk/OpenMPT/mptrack/Ctrl_smp.cpp =================================================================== --- trunk/OpenMPT/mptrack/Ctrl_smp.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Ctrl_smp.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -646,9 +646,9 @@ int transp = 0; if (m_pSndFile->m_nType & (MOD_TYPE_S3M|MOD_TYPE_IT|MOD_TYPE_MPT)) { - wsprintf(s, "%lu", pins->nC4Speed); + wsprintf(s, "%lu", pins->nC5Speed); m_EditFineTune.SetWindowText(s); - transp = CSoundFile::FrequencyToTranspose(pins->nC4Speed) >> 7; + transp = CSoundFile::FrequencyToTranspose(pins->nC5Speed) >> 7; } else { SetDlgItemInt(IDC_EDIT5, (int)pins->nFineTune); @@ -736,7 +736,7 @@ pins->nVolume = 256; pins->nPan = 128; pins->name[0] = 0; - if (!pins->nC4Speed) pins->nC4Speed = 22050; + if (!pins->nC5Speed) pins->nC5Speed = 22050; if (dlg.m_nFormat & 1) { pins->nLength >>= 1; @@ -1493,7 +1493,7 @@ { if(!(m_pSndFile->m_nType & MOD_TYPE_MOD)) { - if (pins->nC4Speed < 200000) pins->nC4Speed *= 2; + if (pins->nC5Speed < 200000) pins->nC5Speed *= 2; if (pins->RelativeTone < 84) pins->RelativeTone += 12; } } @@ -1619,7 +1619,7 @@ { if(!(m_pSndFile->m_nType & MOD_TYPE_MOD)) { - if (pins->nC4Speed > 2000) pins->nC4Speed /= 2; + if (pins->nC5Speed > 2000) pins->nC5Speed /= 2; if (pins->RelativeTone > -84) pins->RelativeTone -= 12; } } @@ -1720,7 +1720,7 @@ UpdateData(TRUE); //Calculate/verify samplerate at C4. - long lSampleRate = pins->nC4Speed; + long lSampleRate = pins->nC5Speed; if(m_pSndFile->m_nType & (MOD_TYPE_MOD|MOD_TYPE_XM)) lSampleRate = (double)CSoundFile::TransposeToFrequency(pins->RelativeTone, pins->nFineTune); if(lSampleRate <= 0) @@ -2161,7 +2161,7 @@ while(fft > MAX_BUFFER_LENGTH) fft >>= 1; // Get original sample rate - long lSampleRate = pins->nC4Speed; + long lSampleRate = pins->nC5Speed; if(m_pSndFile->m_nType & (MOD_TYPE_MOD|MOD_TYPE_XM)) lSampleRate = CSoundFile::TransposeToFrequency(pins->RelativeTone, pins->nFineTune); if(lSampleRate <= 0) lSampleRate = 8363; @@ -2643,9 +2643,9 @@ int n = GetDlgItemInt(IDC_EDIT5); if (m_pSndFile->m_nType & (MOD_TYPE_IT|MOD_TYPE_S3M|MOD_TYPE_MPT)) { - if ((n >= 2000) && (n <= 256000) && (n != (int)m_pSndFile->Ins[m_nSample].nC4Speed)) + if ((n >= 2000) && (n <= 256000) && (n != (int)m_pSndFile->Ins[m_nSample].nC5Speed)) { - m_pSndFile->Ins[m_nSample].nC4Speed = n; + m_pSndFile->Ins[m_nSample].nC5Speed = n; int transp = CSoundFile::FrequencyToTranspose(n) >> 7; int basenote = 60 - transp; if (basenote < BASENOTE_MIN) basenote = BASENOTE_MIN; @@ -2677,12 +2677,12 @@ int n = 60 - (m_CbnBaseNote.GetCurSel() + BASENOTE_MIN); if (m_pSndFile->m_nType & (MOD_TYPE_IT|MOD_TYPE_S3M|MOD_TYPE_MPT)) { - LONG ft = CSoundFile::FrequencyToTranspose(m_pSndFile->Ins[m_nSample].nC4Speed) & 0x7f; + LONG ft = CSoundFile::FrequencyToTranspose(m_pSndFile->Ins[m_nSample].nC5Speed) & 0x7f; n = CSoundFile::TransposeToFrequency(n, ft); - if ((n >= 500) && (n <= 256000) && (n != (int)m_pSndFile->Ins[m_nSample].nC4Speed)) + if ((n >= 500) && (n <= 256000) && (n != (int)m_pSndFile->Ins[m_nSample].nC5Speed)) { CHAR s[32]; - m_pSndFile->Ins[m_nSample].nC4Speed = n; + m_pSndFile->Ins[m_nSample].nC5Speed = n; wsprintf(s, "%lu", n); LockControls(); m_EditFineTune.SetWindowText(s); @@ -3121,19 +3121,19 @@ { if (m_pSndFile->m_nType & (MOD_TYPE_S3M|MOD_TYPE_IT|MOD_TYPE_MPT)) { - LONG d = pins->nC4Speed; + LONG d = pins->nC5Speed; if (d < 1) d = 8363; d += (pos * 25); if (d > 96000) d = 96000; if (d < 2000) d = 2000; - pins->nC4Speed = d; - int transp = CSoundFile::FrequencyToTranspose(pins->nC4Speed) >> 7; + pins->nC5Speed = d; + int transp = CSoundFile::FrequencyToTranspose(pins->nC5Speed) >> 7; int basenote = 60 - transp; if (basenote < BASENOTE_MIN) basenote = BASENOTE_MIN; if (basenote >= BASENOTE_MAX) basenote = BASENOTE_MAX-1; basenote -= BASENOTE_MIN; if (basenote != m_CbnBaseNote.GetCurSel()) m_CbnBaseNote.SetCurSel(basenote); - wsprintf(s, "%lu", pins->nC4Speed); + wsprintf(s, "%lu", pins->nC5Speed); m_EditFineTune.SetWindowText(s); } else { Modified: trunk/OpenMPT/mptrack/Draw_pat.cpp =================================================================== --- trunk/OpenMPT/mptrack/Draw_pat.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Draw_pat.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -325,23 +325,23 @@ { m_Dib.TextBlt(x, y, dx, COLUMN_HEIGHT, xsrc, ysrc + 13*COLUMN_HEIGHT); } else - if (note >= NOTE_KEYOFF) + if (note == NOTE_KEYOFF) { m_Dib.TextBlt(x, y, dx, COLUMN_HEIGHT, xsrc, ysrc + 14*COLUMN_HEIGHT); } else - if(note >= NOTE_PC) + if(note == NOTE_FADE) { + m_Dib.TextBlt(x, y, dx, COLUMN_HEIGHT, xsrc, ysrc + 17*COLUMN_HEIGHT); + } else + if(note == NOTE_PC) + { m_Dib.TextBlt(x, y, dx, COLUMN_HEIGHT, xsrc, ysrc + 15*COLUMN_HEIGHT); } else - if(note >= NOTE_PCS) + if(note == NOTE_PCS) { m_Dib.TextBlt(x, y, dx, COLUMN_HEIGHT, xsrc, ysrc + 16*COLUMN_HEIGHT); } else - if(note >= NOTE_FADE) { - m_Dib.TextBlt(x, y, dx, COLUMN_HEIGHT, xsrc, ysrc + 17*COLUMN_HEIGHT); - } else - { if(pTuning) { // Drawing custom note names string noteStr = pTuning->GetNoteName(note-NOTE_MIDDLEC); @@ -1466,11 +1466,17 @@ // Ignore update if using PC or PCs notes because instrument, volcol and effect values // have different meaning. - if(m->note != NOTE_PC && m->note != NOTE_PCS) + if((m->note != NOTE_PC && m->note != NOTE_PCS) || GetColTypeFromCursor(m_dwCursor) == 0) { switch (GetColTypeFromCursor(m_dwCursor)) { + case 0: + // display note + if(m->note >= NOTE_MIN_SPECIAL) + strcpy(s, szSpecialNoteShortDesc[m->note - NOTE_MIN_SPECIAL]); + break; case 1: + // display instrument if (m->instr) { CHAR sztmp[128] = ""; @@ -1508,10 +1514,12 @@ } break; case 2: + // display volume command if (!pModDoc->GetVolCmdInfo(pModDoc->GetIndexFromVolCmd(m->volcmd), s)) s[0] = 0; break; case 3: case 4: + // display effect command if (!pModDoc->GetEffectName(s, m->command, m->param, FALSE, nChn)) s[0] = 0; break; } Modified: trunk/OpenMPT/mptrack/Moddoc.cpp =================================================================== --- trunk/OpenMPT/mptrack/Moddoc.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Moddoc.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -72,6 +72,7 @@ ON_UPDATE_COMMAND_UI(ID_INSERT_INSTRUMENT, OnUpdateXMITMPTOnly) ON_UPDATE_COMMAND_UI(ID_INSTRUMENTS_REMOVEALL, OnUpdateInstrumentOnly) ON_UPDATE_COMMAND_UI(ID_CLEANUP_INSTRUMENTS, OnUpdateInstrumentOnly) + ON_UPDATE_COMMAND_UI(ID_REARRANGE_SAMPLES, OnUpdateSampleCount) ON_UPDATE_COMMAND_UI(ID_VIEW_INSTRUMENTS, OnUpdateXMITMPTOnly) ON_UPDATE_COMMAND_UI(ID_VIEW_COMMENTS, OnUpdateXMITMPTOnly) ON_UPDATE_COMMAND_UI(ID_VIEW_MIDIMAPPING, OnUpdateHasMIDIMappings) @@ -506,6 +507,7 @@ strcpy(fext, ".s3m"); break; case MOD_TYPE_XM: + MsgBoxHidable(XMCompatibilityExportTip); lpszDefExt = "xm"; lpszFilter = FileFilterXM; strcpy(fext, ".xm"); @@ -621,7 +623,7 @@ switch(GetModType()) { case MOD_TYPE_MOD: - m_SndFile.m_nChannels = 8; + m_SndFile.m_nChannels = 4; break; case MOD_TYPE_S3M: m_SndFile.m_nChannels = 16; @@ -851,7 +853,7 @@ pChn->pInstrument = pins; pChn->pSample = pins->pSample; pChn->nFineTune = pins->nFineTune; - pChn->nC4Speed = pins->nC4Speed; + pChn->nC5Speed = pins->nC5Speed; pChn->nPos = pChn->nPosLo = pChn->nLength = 0; pChn->nLoopStart = pins->nLoopStart; pChn->nLoopEnd = pins->nLoopEnd; @@ -1622,7 +1624,7 @@ if( AfxMessageBox(GetStrI18N(TEXT( "Compared to regular MOD save, compatibility export makes " "small adjustments to the save file in order to make the file compatible with " - "ProTracker. Note that this feature is not complete and the " + "ProTracker and other Amiga-based trackers. Note that this feature is not complete and the " "file is not guaranteed to be free of MPT-specific features.\n\n " "Important: beginning of some samples may be adjusted in the process. Proceed?")), MB_ICONINFORMATION|MB_YESNO) != IDYES ) @@ -1633,6 +1635,11 @@ pattern = FileFilterIT; ::MessageBox(NULL,"Warning: the exported file will not contain any of MPT's file-format hacks.", "Compatibility export warning.",MB_ICONINFORMATION | MB_OK); break; + case MOD_TYPE_XM: + ext = ModSpecs::xm.fileExtension; + pattern = FileFilterXM; + ::MessageBox(NULL,"Warning: the exported file will not contain any of MPT's file-format hacks.", "Compatibility export warning.",MB_ICONINFORMATION | MB_OK); + break; default: ::MessageBox(NULL,"Compatibility export is currently only available for MOD and IT modules.", "Can't do compatibility export.",MB_ICONINFORMATION | MB_OK); return; @@ -1662,7 +1669,7 @@ m_ShowSavedialog = true; // ...and force save dialog to appear when saving. break; case MOD_TYPE_XM: - m_SndFile.SaveCompatXM(dlg.GetPathName()); + m_SndFile.SaveXM(dlg.GetPathName(), 0, true); break; case MOD_TYPE_IT: m_SndFile.SaveCompatIT(dlg.GetPathName()); @@ -1927,6 +1934,12 @@ if (p) p->Enable((m_SndFile.m_nInstruments) ? TRUE : FALSE); } +void CModDoc::OnUpdateSampleCount(CCmdUI *p) +//------------------------------------------ +{ + if (p) p->Enable((m_SndFile.m_nSamples > 1) ? TRUE : FALSE); +} + void CModDoc::OnUpdateHasMIDIMappings(CCmdUI *p) //---------------------------------------------- { Modified: trunk/OpenMPT/mptrack/Moddoc.h =================================================================== --- trunk/OpenMPT/mptrack/Moddoc.h 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Moddoc.h 2009-08-09 23:07:50 UTC (rev 318) @@ -186,6 +186,7 @@ public: BOOL ChangeModType(UINT nNewType); BOOL ChangeNumChannels(UINT nNewChannels, const bool showCancelInRemoveDlg = true); + BOOL ConvertInstrumentsToSamples();; BOOL RemoveUnusedSamples(); BOOL RemoveUnusedInstruments(); @@ -193,7 +194,9 @@ BOOL RemoveUnusedPlugs(); UINT RemovePlugs(const bool (&keepMask)[MAX_MIXPLUGINS]); BOOL RemoveUnusedPatterns(BOOL bRemove=TRUE); + void RearrangeSampleList(); BOOL CompoCleanup(); + LONG InsertPattern(LONG nOrd=-1, UINT nRows=64); LONG InsertSample(BOOL bLimit=FALSE); LONG InsertInstrument(LONG lSample=0, LONG lDuplicate=0); @@ -205,11 +208,6 @@ UINT PlayNote(UINT note, UINT nins, UINT nsmp, BOOL bpause, LONG nVol=-1, LONG loopstart=0, LONG loopend=0, int nCurrentChn=-1, const uint32 nStartPos = uint32_max); //rewbs.vstiLive: added current chan param BOOL NoteOff(UINT note, BOOL bFade=FALSE, UINT nins=-1, UINT nCurrentChn=-1); //rewbs.vstiLive: add params -// -> CODE#0020 -// -> DESC="rearrange sample list" - void RearrangeSampleList(void); -// -! NEW_FEATURE#0020 - BOOL IsNotePlaying(UINT note, UINT nsmp=0, UINT nins=0); BOOL MuteChannel(UINT nChn, BOOL bMute); BOOL MuteSample(UINT nSample, BOOL bMute); @@ -339,6 +337,7 @@ afx_msg void OnUpdateXMITMPTOnly(CCmdUI *p); afx_msg void OnUpdateHasMIDIMappings(CCmdUI *p); afx_msg void OnUpdateInstrumentOnly(CCmdUI *pCmdUI); + afx_msg void OnUpdateSampleCount(CCmdUI *pCmdUI); afx_msg void OnUpdateMP3Encode(CCmdUI *pCmdUI); afx_msg void OnPatternRestart(); //rewbs.customKeys afx_msg void OnPatternPlay(); //rewbs.customKeys Modified: trunk/OpenMPT/mptrack/Modedit.cpp =================================================================== --- trunk/OpenMPT/mptrack/Modedit.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Modedit.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -205,7 +205,7 @@ case 0x50: m->param = (m->param & 0x0F) | 0x20; break; case 0x60: m->param = (m->param & 0x0F) | 0xB0; break; case 0x70: m->param = (m->param & 0x0F) | 0x40; break; - case 0x90: m->command = CMD_RETRIG; m->param &= 0x0F; break; + case 0x90: m->command = CMD_RETRIG; m->param = 0x80 | (m->param & 0x0F); break; case 0xA0: if (m->param & 0x0F) { m->command = CMD_VOLUMESLIDE; m->param = (m->param << 4) | 0x0F; } else m->command = 0; break; case 0xB0: if (m->param & 0x0F) { m->command = CMD_VOLUMESLIDE; m->param |= 0xF0; } else m->command = 0; break; } @@ -598,7 +598,7 @@ } // End if (newTypeIsIT) if(!m_SndFile.GetModSpecifications().HasNote(m->note)) - m->note = 0; + m->note = NOTE_NONE; } } @@ -611,7 +611,7 @@ { for (UINT i=1; i<=m_SndFile.m_nSamples; i++) { - m_SndFile.Ins[i].nC4Speed = CSoundFile::TransposeToFrequency(m_SndFile.Ins[i].RelativeTone, m_SndFile.Ins[i].nFineTune); + m_SndFile.Ins[i].nC5Speed = CSoundFile::TransposeToFrequency(m_SndFile.Ins[i].RelativeTone, m_SndFile.Ins[i].nFineTune); m_SndFile.Ins[i].RelativeTone = 0; m_SndFile.Ins[i].nFineTune = 0; } @@ -1558,7 +1558,7 @@ pins->nVolume = 256; pins->nGlobalVol = 64; pins->nPan = 128; - pins->nC4Speed = 8363; + pins->nC5Speed = 8363; pins->RelativeTone = 0; pins->nFineTune = 0; pins->nVibType = 0; @@ -1751,57 +1751,78 @@ } -// -> CODE#0020 -// -> DESC="rearrange sample list" -void CModDoc::RearrangeSampleList(void) -//------------------------------------- +void CModDoc::RearrangeSampleList() +//--------------------------------- { - MessageBox(NULL, "Rearrange samplelist didn't work properly and has been disabled.", NULL, MB_ICONINFORMATION); - /* - BEGIN_CRITICAL(); - UINT i,j,k,n,l,c; + if(m_SndFile.m_nSamples < 2) + return; - for(n = 1 ; n <= m_SndFile.m_nSamples ; n++){ + UINT nRemap = 0; // remap count + UINT nSampleMap[MAX_SAMPLES + 1]; // map old => new + for(UINT i = 0; i <= MAX_SAMPLES; i++) + nSampleMap[i] = i; + + // First, find out which sample slots are unused and create the new sample map + for(UINT i = 1 ; i <= m_SndFile.m_nSamples; i++) { + if(!m_SndFile.Ins[i].pSample) + { + // Move all following samples + nRemap++; + nSampleMap[i] = 0; + for(UINT j = i + 1; j <= m_SndFile.m_nSamples; j++) + nSampleMap[j]--; + } + } - if(!m_SndFile.Ins[n].pSample){ - - k = 1; + if(!nRemap) + return; - while(n+k <= m_SndFile.m_nSamples && !m_SndFile.Ins[n+k].pSample) k++; - if(n+k >= m_SndFile.m_nSamples) break; + BEGIN_CRITICAL(); - c = k; - l = 0; + // Now, move everything around + for(UINT i = 1; i <= m_SndFile.m_nSamples; i++) + { + if(nSampleMap[i] != i) + { + // This gotta be moved - while(n+k <= m_SndFile.m_nSamples && m_SndFile.Ins[n+k].pSample){ + m_SndFile.MoveSample(i, nSampleMap[i]); + m_SndFile.Ins[i].pSample = nullptr; + strcpy(m_SndFile.m_szNames[nSampleMap[i]], m_SndFile.m_szNames[i]); + m_SndFile.m_szNames[i][0] = '\0'; - m_SndFile.MoveSample(n+k,n+l); - strcpy(m_SndFile.m_szNames[n+l], m_SndFile.m_szNames[n+k]); - m_SndFile.m_szNames[n+k][0] = '\0'; - - for(i=1; i<=m_SndFile.m_nInstruments; i++){ - if(m_SndFile.Headers[i]){ - INSTRUMENTHEADER *p = m_SndFile.Headers[i]; - for(j=0; j<128; j++) if(p->Keyboard[j] == n+k) p->Keyboard[j] = n+l; - } + // Also update instrument mapping + for(UINT iInstr = 1; iInstr <= m_SndFile.m_nInstruments; iInstr++){ + if(m_SndFile.Headers[iInstr]){ + INSTRUMENTHEADER *p = m_SndFile.Headers[iInstr]; + for(WORD iNote =0; iNote < 128; iNote++) + if(p->Keyboard[iNote] == i) p->Keyboard[iNote] = nSampleMap[i]; } + } + } + } - k++; - l++; + // Go through the patterns and remap samples (if module is in sample mode) + if(!m_SndFile.m_nInstruments) + { + for (UINT nPat=0; nPat<m_SndFile.Patterns.Size(); nPat++) if (m_SndFile.Patterns[nPat]) + { + MODCOMMAND *m = m_SndFile.Patterns[nPat]; + for (UINT len = m_SndFile.PatternSize[nPat] * m_SndFile.m_nChannels; len; m++, len--) + { + m->instr = nSampleMap[m->instr]; } - - n += l; - m_SndFile.m_nSamples -= c; } } + m_SndFile.m_nSamples -= nRemap; + END_CRITICAL(); SetModified(); - UpdateAllViews(NULL, HINT_SMPNAMES); - */ + UpdateAllViews(NULL, HINT_MODTYPE); + } -// -! NEW_FEATURE#0020 BOOL CModDoc::RemoveInstrument(UINT n) @@ -2099,7 +2120,7 @@ if (s[0] > ' ' && (!mix || ((!ITStyleMix && origModCmd.note==0) || (ITStyleMix && origModCmd.note==0 && origModCmd.instr==0 && origModCmd.volcmd==0)))) { - m[col].note = 0; + m[col].note = NOTE_NONE; if (s[0] == '=') m[col].note = NOTE_KEYOFF; else if (s[0] == '^') m[col].note = NOTE_NOTECUT; else if (s[0] == '~') m[col].note = NOTE_FADE; else Modified: trunk/OpenMPT/mptrack/Mpt_midi.cpp =================================================================== --- trunk/OpenMPT/mptrack/Mpt_midi.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Mpt_midi.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -50,7 +50,7 @@ if (note < 0x80) { note += nTranspose*12; - if (note < 0) note = 0; + if (note < 0) note = NOTE_NONE; if (note > NOTE_MAX - 1) note = NOTE_MAX - 1; // -> CODE#0011 Modified: trunk/OpenMPT/mptrack/Mptrack.h =================================================================== --- trunk/OpenMPT/mptrack/Mptrack.h 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/Mptrack.h 2009-08-09 23:07:50 UTC (rev 318) @@ -398,15 +398,15 @@ /////////////////////////////////////////////////// // Tables -#define MAX_EFFECTS 35 //rewbs.smoothVST & rewbs.velocity: increased from 32. Wonder what this will break... +#define MAX_EFFECTS 37 //rewbs.smoothVST & rewbs.velocity: increased from 32. Wonder what this will break... //+1 for eric's multiplier #define MAX_VOLCMDS 16 //rewbs.voloff & rewbs.velocity: increased from 14 extern const BYTE gEffectColors[MAX_EFFECTS]; extern const LPCSTR szNoteNames[12]; extern const LPCTSTR szDefaultNoteNames[NOTE_MAX]; -const LPCTSTR szSpecialNoteNames[NOTE_MAX_SPECIAL-NOTE_MIN_SPECIAL + 1] = {TEXT("~~"), TEXT("PCs"), TEXT("PC"), TEXT("^^"), TEXT("==")}; -const LPCTSTR szSpecialNoteShortDesc[NOTE_MAX_SPECIAL-NOTE_MIN_SPECIAL + 1] = {TEXT("Param control(smooth)"), TEXT("Param control"), TEXT("Note Cut"), TEXT("Note Off")}; +const LPCTSTR szSpecialNoteNames[NOTE_MAX_SPECIAL - NOTE_MIN_SPECIAL + 1] = {TEXT("PCs"), TEXT("PC"), TEXT("~~"), TEXT("^^"), TEXT("==")}; +const LPCTSTR szSpecialNoteShortDesc[NOTE_MAX_SPECIAL - NOTE_MIN_SPECIAL + 1] = {TEXT("Param Control (Smooth)"), TEXT("Param Control"), TEXT("Note Fade"), TEXT("Note Cut"), TEXT("Note Off")}; // Make sure that special note arrays include string for every note. STATIC_ASSERT(NOTE_MAX_SPECIAL - NOTE_MIN_SPECIAL + 1 == ARRAYELEMCOUNT(szSpecialNoteNames)); Modified: trunk/OpenMPT/mptrack/View_ins.cpp =================================================================== --- trunk/OpenMPT/mptrack/View_ins.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/View_ins.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -1214,9 +1214,9 @@ nPrevTick=nTick; nRow=nTick/speed; - if (nRow % CMainFrame::m_nRowSpacing == 0) + if (nRow % max(1, CMainFrame::m_nRowSpacing) == 0) m_dcGrid.SelectObject(CMainFrame::penGray80); - else if (nRow % CMainFrame::m_nRowSpacing2 == 0) + else if (nRow % max(1, CMainFrame::m_nRowSpacing2) == 0) m_dcGrid.SelectObject(CMainFrame::penGray55); else m_dcGrid.SelectObject(CMainFrame::penGray33); Modified: trunk/OpenMPT/mptrack/View_pat.cpp =================================================================== --- trunk/OpenMPT/mptrack/View_pat.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/View_pat.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -891,7 +891,7 @@ } else { - m->note = 0; + m->note = NOTE_NONE; if (ITStyle) m->instr = 0; } @@ -4420,7 +4420,7 @@ switch(field) { - case 0: if(p->note == NOTE_PC || p->note == NOTE_PCS) p->Clear(); else {p->note = 0; if (ITStyle) p->instr = 0;} break; //Note + case 0: if(p->note == NOTE_PC || p->note == NOTE_PCS) p->Clear(); else {p->note = NOTE_NONE; if (ITStyle) p->instr = 0;} break; //Note case 1: p->instr = 0; break; //instr case 2: p->vol = 0; p->volcmd = 0; break; //Vol case 3: p->command = 0; break; //Effect Modified: trunk/OpenMPT/mptrack/View_smp.cpp =================================================================== --- trunk/OpenMPT/mptrack/View_smp.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/View_smp.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -273,7 +273,7 @@ if (pModDoc) { CSoundFile *pSndFile = pModDoc->GetSoundFile(); - LONG lSampleRate = pSndFile->Ins[m_nSample].nC4Speed; + LONG lSampleRate = pSndFile->Ins[m_nSample].nC5Speed; if (pSndFile->m_nType & (MOD_TYPE_MOD|MOD_TYPE_XM)) { lSampleRate = CSoundFile::TransposeToFrequency(pSndFile->Ins[m_nSample].RelativeTone, pSndFile->Ins[m_nSample].nFineTune); @@ -1793,7 +1793,7 @@ pfmt->id_fmt = IFFID_fmt; pfmt->hdrlen = 16; pfmt->format = 1; - pfmt->freqHz = pins->nC4Speed; + pfmt->freqHz = pins->nC5Speed; if (pSndFile->m_nType & (MOD_TYPE_MOD|MOD_TYPE_XM)) { pfmt->freqHz = CSoundFile::TransposeToFrequency(pins->RelativeTone, pins->nFineTune); @@ -1817,7 +1817,7 @@ psh->smpl_id = 0x6C706D73; psh->smpl_len = sizeof(WAVESMPLHEADER) - 8; psh->dwSamplePeriod = 22675; - if (pins->nC4Speed > 256) psh->dwSamplePeriod = 1000000000 / pins->nC4Speed; + if (pins->nC5Speed > 256) psh->dwSamplePeriod = 1000000000 / pins->nC5Speed; psh->dwBaseNote = 60; if (pins->uFlags & (CHN_LOOP|CHN_SUSTAINLOOP)) { Modified: trunk/OpenMPT/mptrack/dlg_misc.cpp =================================================================== --- trunk/OpenMPT/mptrack/dlg_misc.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/dlg_misc.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -2459,10 +2459,10 @@ chord = m_CbnShortcut.GetCurSel(); if (chord >= 0) chord = m_CbnShortcut.GetItemData(chord); if ((chord < 0) || (chord >= 3*12)) chord = 0; - UINT cnote = 0; - pChords[chord].notes[0] = 0; - pChords[chord].notes[1] = 0; - pChords[chord].notes[2] = 0; + UINT cnote = NOTE_NONE; + pChords[chord].notes[0] = NOTE_NONE; + pChords[chord].notes[1] = NOTE_NONE; + pChords[chord].notes[2] = NOTE_NONE; for (UINT i=0; i<2*12; i++) if (i != (UINT)(pChords[chord].key % 12)) { UINT n = m_Keyboard.GetFlags(i); @@ -2851,7 +2851,8 @@ { {TEXT("Tip: To create ProTracker compatible MOD-files, try compatibility export from File-menu."), 1, true}, {TEXT("Tip: To create IT-files without MPT-specific extensions included, try compatibility export from File-menu."), 1 << 1, true}, - {TEXT("Press OK to apply signed/unsigned conversion\n (note: this often significantly increases volume level)"), 1 << 2, false} + {TEXT("Press OK to apply signed/unsigned conversion\n (note: this often significantly increases volume level)"), 1 << 2, false}, + {TEXT("Tip: To create XM-files without MPT-specific extensions included, try compatibility export from File-menu."), 1 << 1, true}, }; STATIC_ASSERT(ARRAYELEMCOUNT(HidableMessages) == enMsgBoxHidableMessage_count); Modified: trunk/OpenMPT/mptrack/dlg_misc.h =================================================================== --- trunk/OpenMPT/mptrack/dlg_misc.h 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/dlg_misc.h 2009-08-09 23:07:50 UTC (rev 318) @@ -556,6 +556,7 @@ ModCompatibilityExportTip = 0, ItCompatibilityExportTip = 1, ConfirmSignUnsignWhenPlaying = 2, + XMCompatibilityExportTip = 3, enMsgBoxHidableMessage_count }; Modified: trunk/OpenMPT/mptrack/mptrack.rc =================================================================== --- trunk/OpenMPT/mptrack/mptrack.rc 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/mptrack.rc 2009-08-09 23:07:50 UTC (rev 318) @@ -1764,6 +1764,7 @@ POPUP "C&leanup" BEGIN MENUITEM "&Rearrange Patterns", ID_CLEANUP_REARRANGE + MENUITEM "Rearrange Samples", ID_REARRANGE_SAMPLES MENUITEM "&Cleanup Instruments", ID_CLEANUP_INSTRUMENTS MENUITEM "Clean&up Samples", ID_CLEANUP_SAMPLES MENUITEM "Cleanup Pa&tterns", ID_CLEANUP_PATTERNS Modified: trunk/OpenMPT/mptrack/mptrack.vcproj =================================================================== --- trunk/OpenMPT/mptrack/mptrack.vcproj 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/mptrack.vcproj 2009-08-09 23:07:50 UTC (rev 318) @@ -280,6 +280,9 @@ RelativePath="..\soundlib\Load_gdm.cpp"> </File> <File + RelativePath="..\soundlib\Load_imf.cpp"> + </File> + <File RelativePath="..\soundlib\Load_it.cpp"> </File> <File Modified: trunk/OpenMPT/mptrack/mptrack_08.vcproj =================================================================== --- trunk/OpenMPT/mptrack/mptrack_08.vcproj 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/mptrack_08.vcproj 2009-08-09 23:07:50 UTC (rev 318) @@ -377,6 +377,10 @@ > </File> <File + RelativePath="..\soundlib\Load_imf.cpp" + > + </File> + <File RelativePath="..\soundlib\Load_it.cpp" > </File> Modified: trunk/OpenMPT/mptrack/resource.h =================================================================== --- trunk/OpenMPT/mptrack/resource.h 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/resource.h 2009-08-09 23:07:50 UTC (rev 318) @@ -1109,6 +1109,7 @@ #define ID_SAMPLE_ADDSILENCE 59225 #define ID_ECHOPASTE 59226 #define ID_NOTEMAP_COPY_NOTE 59227 +#define ID_CLEANUP_REARRANGESAMPLES 59228 // Next default values for new objects // @@ -1116,7 +1117,7 @@ #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_3D_CONTROLS 1 #define _APS_NEXT_RESOURCE_VALUE 519 -#define _APS_NEXT_COMMAND_VALUE 59228 +#define _APS_NEXT_COMMAND_VALUE 59229 #define _APS_NEXT_CONTROL_VALUE 2386 #define _APS_NEXT_SYMED_VALUE 901 #endif Modified: trunk/OpenMPT/mptrack/view_com.cpp =================================================================== --- trunk/OpenMPT/mptrack/view_com.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/mptrack/view_com.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -276,8 +276,8 @@ { wsprintf(s, "%d Hz", pSndFile->GetFreqFromPeriod( - pSndFile->GetPeriodFromNote(NOTE_MIDDLEC, pins->nFineTune, pins->nC4Speed), - pins->nC4Speed)); + pSndFile->GetPeriodFromNote(NOTE_MIDDLEC, pins->nFineTune, pins->nC5Speed), + pins->nC5Speed)); } break; case SMPLIST_FILENAME: Modified: trunk/OpenMPT/soundlib/Dlsbank.cpp =================================================================== --- trunk/OpenMPT/soundlib/Dlsbank.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/Dlsbank.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -1496,7 +1496,7 @@ psmp->uFlags = CHN_16BIT; psmp->nLoopStart = pins->Regions[nRgn].ulLoopStart; psmp->nLoopEnd = pins->Regions[nRgn].ulLoopEnd; - psmp->nC4Speed = p->dwSampleRate; + psmp->nC5Speed = p->dwSampleRate; psmp->nGlobalVol = 64; psmp->nVolume = 256; psmp->nPan = 128; @@ -1564,15 +1564,15 @@ sFineTune += psmp->nFineTune; } #ifdef DLSINSTR_LOG - Log("WSMP: usUnityNote=%d.%d, %dHz (transp=%d)\n", usUnityNote, sFineTune, psmp->nC4Speed, transpose); + Log("WSMP: usUnityNote=%d.%d, %dHz (transp=%d)\n", usUnityNote, sFineTune, psmp->nC5Speed, transpose); #endif if (usUnityNote > 0x7F) usUnityNote = 60; int nBaseTune = DlsFreqToTranspose( - psmp->nC4Speed, + psmp->nC5Speed, sFineTune+(60 + transpose - usUnityNote)*100); psmp->nFineTune = (CHAR)(nBaseTune & 0x7F); psmp->RelativeTone = (CHAR)(nBaseTune >> 7); - psmp->nC4Speed = CSoundFile::TransposeToFrequency(psmp->RelativeTone, psmp->nFineTune); + psmp->nC5Speed = CSoundFile::TransposeToFrequency(psmp->RelativeTone, psmp->nFineTune); if (lVolume > 256) lVolume = 256; if (lVolume < 16) lVolume = 16; psmp->nGlobalVol = (BYTE)(lVolume / 4); // 0-64 Modified: trunk/OpenMPT/soundlib/LOAD_AMF.CPP =================================================================== --- trunk/OpenMPT/soundlib/LOAD_AMF.CPP 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/LOAD_AMF.CPP 2009-08-09 23:07:50 UTC (rev 318) @@ -167,13 +167,13 @@ -BOOL CSoundFile::ReadAMF(LPCBYTE lpStream, const DWORD dwMemLength) +bool CSoundFile::ReadAMF(LPCBYTE lpStream, const DWORD dwMemLength) //----------------------------------------------------------- { const AMFFILEHEADER *pfh = (AMFFILEHEADER *)lpStream; DWORD dwMemPos; - if ((!lpStream) || (dwMemLength < 2048)) return FALSE; + if ((!lpStream) || (dwMemLength < 2048)) return false; if ((!strncmp((LPCSTR)lpStream, "ASYLUM Music Format V1.0", 25)) && (dwMemLength > 4096)) { UINT numorders, numpats, numsamples; @@ -184,7 +184,7 @@ numsamples = 64; dwMemPos += 6; if ((!numpats) || (numpats > MAX_PATTERNS) || (!numorders) - || (numpats*64*32 + 294 + 37*64 >= dwMemLength)) return FALSE; + || (numpats*64*32 + 294 + 37*64 >= dwMemLength)) return false; m_nType = MOD_TYPE_AMF0; m_nChannels = 8; m_nInstruments = 0; @@ -226,7 +226,7 @@ const UCHAR *pin = lpStream + dwMemPos; for (UINT i=0; i<8*64; i++) { - p->note = 0; + p->note = NOTE_NONE; if (pin[0]) { p->note = pin[0] + 13; @@ -253,11 +253,11 @@ MODINSTRUMENT *psmp = &Ins[iData+1]; if (psmp->nLength) { - if(dwMemPos > dwMemLength) return FALSE; + if(dwMemPos > dwMemLength) return false; dwMemPos += ReadSample(psmp, RS_PCM8S, (LPCSTR)(lpStream+dwMemPos), dwMemLength - dwMemPos); } } - return TRUE; + return true; } //////////////////////////// // DSM/AMF @@ -269,7 +269,7 @@ || (!pfh->numorders) || (pfh->numorders > MAX_PATTERNS) || (!pfh->numsamples) || (pfh->numsamples > MAX_SAMPLES) || (pfh->numchannels < 1) || (pfh->numchannels > 32)) - return FALSE; + return false; memcpy(m_szNames[0], pfh->title, 31); dwMemPos = sizeof(AMFFILEHEADER); m_nType = MOD_TYPE_AMF; @@ -323,7 +323,7 @@ dwMemPos += m_nChannels * sizeof(USHORT); } } - if (dwMemPos + m_nSamples * (sizeof(AMFSAMPLE)+8) > dwMemLength) return TRUE; + if (dwMemPos + m_nSamples * (sizeof(AMFSAMPLE)+8) > dwMemLength) return true; // Read Samples UINT maxsampleseekpos = 0; for (UINT iIns=0; iIns<m_nSamples; iIns++) @@ -335,7 +335,7 @@ memcpy(m_szNames[iIns+1], psh->samplename, 31); memcpy(pins->name, psh->filename, 13); pins->nLength = LittleEndian(psh->length); - pins->nC4Speed = LittleEndianW(psh->c2spd); + pins->nC5Speed = LittleEndianW(psh->c2spd); pins->nGlobalVol = 64; pins->nVolume = psh->volume * 4; if (pfh->version >= 11) @@ -415,7 +415,7 @@ break; } } - return TRUE; + return true; } Modified: trunk/OpenMPT/soundlib/LOAD_DBM.CPP =================================================================== --- trunk/OpenMPT/soundlib/LOAD_DBM.CPP 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/LOAD_DBM.CPP 2009-08-09 23:07:50 UTC (rev 318) @@ -97,7 +97,7 @@ #pragma pack() -BOOL CSoundFile::ReadDBM(const BYTE *lpStream, DWORD dwMemLength) +bool CSoundFile::ReadDBM(const BYTE *lpStream, DWORD dwMemLength) //--------------------------------------------------------------- { const DBMFILEHEADER *pfh = (DBMFILEHEADER *)lpStream; @@ -107,10 +107,10 @@ if ((!lpStream) || (dwMemLength <= sizeof(DBMFILEHEADER)) || (!pfh->channels) || (pfh->dbm_id != DBM_FILE_MAGIC) || (!pfh->songs) || (pfh->song_id != DBM_ID_SONG) || (pfh->name_id != DBM_ID_NAME) || (pfh->name_len != DBM_NAMELEN) - || (pfh->info_id != DBM_ID_INFO) || (pfh->info_len != DBM_INFOLEN)) return FALSE; + || (pfh->info_id != DBM_ID_INFO) || (pfh->info_len != DBM_INFOLEN)) return false; dwMemPos = sizeof(DBMFILEHEADER); nOrders = BigEndianW(pfh->orders); - if (dwMemPos + 2 * nOrders + 8*3 >= dwMemLength) return FALSE; + if (dwMemPos + 2 * nOrders + 8*3 >= dwMemLength) return false; nInstruments = BigEndianW(pfh->instruments); nSamples = BigEndianW(pfh->samples); nPatterns = BigEndianW(pfh->patterns); @@ -181,8 +181,8 @@ psmp->nVolume = BigEndianW(pih->volume) * 4; if ((!psmp->nVolume) || (psmp->nVolume > 256)) psmp->nVolume = 256; psmp->nGlobalVol = 64; - psmp->nC4Speed = BigEndian(pih->finetune); - int f2t = FrequencyToTranspose(psmp->nC4Speed); + psmp->nC5Speed = BigEndian(pih->finetune); + int f2t = FrequencyToTranspose(psmp->nC5Speed); psmp->RelativeTone = f2t >> 7; psmp->nFineTune = f2t & 0x7F; if ((pih->looplen) && (sflags & 3)) @@ -366,6 +366,6 @@ } } } - return TRUE; + return true; } Modified: trunk/OpenMPT/soundlib/LOAD_DMF.CPP =================================================================== --- trunk/OpenMPT/soundlib/LOAD_DMF.CPP 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/LOAD_DMF.CPP 2009-08-09 23:07:50 UTC (rev 318) @@ -86,7 +86,7 @@ #endif -BOOL CSoundFile::ReadDMF(const BYTE *lpStream, DWORD dwMemLength) +bool CSoundFile::ReadDMF(const BYTE *lpStream, DWORD dwMemLength) //--------------------------------------------------------------- { const DMFHEADER *pfh = (DMFHEADER *)lpStream; @@ -96,8 +96,8 @@ BYTE infobyte[32]; BYTE smplflags[MAX_SAMPLES]; - if ((!lpStream) || (dwMemLength < 1024)) return FALSE; - if ((pfh->id != 0x464d4444) || (!pfh->version) || (pfh->version & 0xF0)) return FALSE; + if ((!lpStream) || (dwMemLength < 1024)) return false; + if ((pfh->id != 0x464d4444) || (!pfh->version) || (pfh->version & 0xF0)) return false; dwMemPos = 66; memcpy(m_szNames[0], pfh->songname, 30); m_szNames[0][30] = 0; @@ -402,7 +402,7 @@ psmp->nLength = psh->len; psmp->nLoopStart = psh->loopstart; psmp->nLoopEnd = psh->loopend; - psmp->nC4Speed = psh->c3speed; + psmp->nC5Speed = psh->c3speed; psmp->nGlobalVol = 64; psmp->nVolume = (psh->volume) ? ((WORD)psh->volume)+1 : (WORD)256; psmp->uFlags = (psh->flags & 2) ? CHN_16BIT : 0; @@ -476,11 +476,11 @@ if (!m_nSamples) { m_nType = MOD_TYPE_NONE; - return FALSE; + return false; } m_nChannels = 4; } - return TRUE; + return true; } Modified: trunk/OpenMPT/soundlib/LOAD_DSM.CPP =================================================================== --- trunk/OpenMPT/soundlib/LOAD_DSM.CPP 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/LOAD_DSM.CPP 2009-08-09 23:07:50 UTC (rev 318) @@ -85,7 +85,7 @@ #pragma pack() -BOOL CSoundFile::ReadDSM(LPCBYTE lpStream, DWORD dwMemLength) +bool CSoundFile::ReadDSM(LPCBYTE lpStream, DWORD dwMemLength) //----------------------------------------------------------- { DSMFILEHEADER *pfh = (DSMFILEHEADER *)lpStream; @@ -96,7 +96,7 @@ if ((!lpStream) || (dwMemLength < 1024) || (pfh->id_RIFF != DSMID_RIFF) || (pfh->riff_len + 8 > dwMemLength) || (pfh->riff_len < 1024) || (pfh->id_DSMF != DSMID_DSMF) || (pfh->id_SONG != DSMID_SONG) - || (pfh->song_len > dwMemLength)) return FALSE; + || (pfh->song_len > dwMemLength)) return false; psong = (DSMSONG *)(lpStream + sizeof(DSMFILEHEADER)); dwMemPos = sizeof(DSMFILEHEADER) + pfh->song_len; m_nType = MOD_TYPE_DSM; @@ -219,7 +219,7 @@ MODINSTRUMENT *psmp = &Ins[nSmp]; memcpy(psmp->name, pins->filename, 13); psmp->nGlobalVol = 64; - psmp->nC4Speed = pins->c2spd; + psmp->nC5Speed = pins->c2spd; psmp->uFlags = (WORD)((pins->flags & 1) ? CHN_LOOP : 0); psmp->nLength = pins->length; psmp->nLoopStart = pins->loopstart; @@ -234,6 +234,6 @@ break; } } - return TRUE; + return true; } Modified: trunk/OpenMPT/soundlib/Load_669.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_669.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/Load_669.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -39,7 +39,7 @@ } SAMPLE669; -BOOL CSoundFile::Read669(const BYTE *lpStream, DWORD dwMemLength) +bool CSoundFile::Read669(const BYTE *lpStream, DWORD dwMemLength) //--------------------------------------------------------------- { BOOL b669Ext; @@ -47,19 +47,19 @@ const SAMPLE669 *psmp = (const SAMPLE669 *)(lpStream + 0x1F1); DWORD dwMemPos = 0; - if ((!lpStream) || (dwMemLength < sizeof(FILEHEADER669))) return FALSE; - if ((LittleEndianW(pfh->sig) != 0x6669) && (LittleEndianW(pfh->sig) != 0x4E4A)) return FALSE; + if ((!lpStream) || (dwMemLength < sizeof(FILEHEADER669))) return false; + if ((LittleEndianW(pfh->sig) != 0x6669) && (LittleEndianW(pfh->sig) != 0x4E4A)) return false; b669Ext = (LittleEndianW(pfh->sig) == 0x4E4A) ? TRUE : FALSE; if ((!pfh->samples) || (pfh->samples > 64) || (pfh->restartpos >= 128) - || (!pfh->patterns) || (pfh->patterns > 128)) return FALSE; + || (!pfh->patterns) || (pfh->patterns > 128)) return false; DWORD dontfuckwithme = 0x1F1 + pfh->samples * sizeof(SAMPLE669) + pfh->patterns * 0x600; - if (dontfuckwithme > dwMemLength) return FALSE; + if (dontfuckwithme > dwMemLength) return false; for (UINT ichk=0; ichk<pfh->samples; ichk++) { DWORD len = LittleEndian(*((DWORD *)(&psmp[ichk].length))); dontfuckwithme += len; } - if (dontfuckwithme > dwMemLength) return FALSE; + if (dontfuckwithme > dwMemLength) return false; // That should be enough checking: this must be a 669 module. m_nType = MOD_TYPE_669; m_dwSongFlags |= SONG_LINEARSLIDES; @@ -183,7 +183,7 @@ if (len > 4) ReadSample(&Ins[n], RS_PCM8U, (LPSTR)(lpStream+dwMemPos), dwMemLength - dwMemPos); dwMemPos += len; } - return TRUE; + return true; } Modified: trunk/OpenMPT/soundlib/Load_ams.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_ams.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/Load_ams.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -45,7 +45,7 @@ -BOOL CSoundFile::ReadAMS(LPCBYTE lpStream, DWORD dwMemLength) +bool CSoundFile::ReadAMS(LPCBYTE lpStream, DWORD dwMemLength) //----------------------------------------------------------- { BYTE pkinf[MAX_SAMPLES]; @@ -53,7 +53,7 @@ DWORD dwMemPos; UINT tmp, tmp2; - if ((!lpStream) || (dwMemLength < 1024)) return FALSE; + if ((!lpStream) || (dwMemLength < 1024)) return false; if ((pfh->verhi != 0x01) || (strncmp(pfh->szHeader, "Extreme", 7)) || (!pfh->patterns) || (!pfh->orders) || (!pfh->samples) || (pfh->samples > MAX_SAMPLES) || (pfh->patterns > MAX_PATTERNS) || (pfh->orders > MAX_ORDERS)) @@ -61,7 +61,7 @@ return ReadAMS2(lpStream, dwMemLength); } dwMemPos = sizeof(AMSFILEHEADER) + pfh->extra; - if (dwMemPos + pfh->samples * sizeof(AMSSAMPLEHEADER) + 256 >= dwMemLength) return FALSE; + if (dwMemPos + pfh->samples * sizeof(AMSSAMPLEHEADER) + 256 >= dwMemLength) return false; m_nType = MOD_TYPE_AMS; m_nInstruments = 0; m_nChannels = (pfh->chncfg & 0x1F) + 1; @@ -75,7 +75,7 @@ pins->nLoopEnd = psh->loopend; pins->nGlobalVol = 64; pins->nVolume = psh->volume << 1; - pins->nC4Speed = psh->samplerate; + pins->nC5Speed = psh->samplerate; pins->nPan = (psh->finetune_and_pan & 0xF0); if (pins->nPan < 0x80) pins->nPan += 0x10; pins->nFineTune = MOD2XMFineTune(psh->finetune_and_pan & 0x0F); @@ -85,7 +85,7 @@ } // Read Song Name tmp = lpStream[dwMemPos++]; - if (dwMemPos + tmp + 1 >= dwMemLength) return TRUE; + if (dwMemPos + tmp + 1 >= dwMemLength) return true; tmp2 = (tmp < 32) ? tmp : 31; if (tmp2) memcpy(m_szNames[0], lpStream+dwMemPos, tmp2); m_szNames[0][tmp2] = 0; @@ -93,7 +93,7 @@ // Read sample names for (UINT sNam=1; sNam<=m_nSamples; sNam++) { - if (dwMemPos + 32 >= dwMemLength) return TRUE; + if (dwMemPos + 32 >= dwMemLength) return true; tmp = lpStream[dwMemPos++]; tmp2 = (tmp < 32) ? tmp : 31; if (tmp2) memcpy(m_szNames[sNam], lpStream+dwMemPos, tmp2); @@ -102,18 +102,18 @@ // Skip Channel names for (UINT cNam=0; cNam<m_nChannels; cNam++) { - if (dwMemPos + 32 >= dwMemLength) return TRUE; + if (dwMemPos + 32 >= dwMemLength) return true; tmp = lpStream[dwMemPos++]; dwMemPos += tmp; } // Read Pattern Names m_lpszPatternNames = new char[pfh->patterns * 32]; - if (!m_lpszPatternNames) return TRUE; + if (!m_lpszPatternNames) return true; m_nPatternNames = pfh->patterns; memset(m_lpszPatternNames, 0, m_nPatternNames * 32); for (UINT pNam=0; pNam < m_nPatternNames; pNam++) { - if (dwMemPos + 32 >= dwMemLength) return TRUE; + if (dwMemPos + 32 >= dwMemLength) return true; tmp = lpStream[dwMemPos++]; tmp2 = (tmp < 32) ? tmp : 31; if (tmp2) memcpy(m_lpszPatternNames+pNam*32, lpStream+dwMemPos, tmp2); @@ -122,11 +122,11 @@ // Read Song Comments tmp = *((WORD *)(lpStream+dwMemPos)); dwMemPos += 2; - if (dwMemPos + tmp >= dwMemLength) return TRUE; + if (dwMemPos + tmp >= dwMemLength) return true; if (tmp) { m_lpszSongComments = new char[tmp+1]; - if (!m_lpszSongComments) return TRUE; + if (!m_lpszSongComments) return true; memset(m_lpszSongComments, 0, tmp+1); memcpy(m_lpszSongComments, lpStream + dwMemPos, tmp); dwMemPos += tmp; @@ -140,13 +140,13 @@ // Read Patterns for (UINT iPat=0; iPat<pfh->patterns; iPat++) { - if (dwMemPos + 4 >= dwMemLength) return TRUE; + if (dwMemPos + 4 >= dwMemLength) return true; UINT len = *((DWORD *)(lpStream + dwMemPos)); dwMemPos += 4; - if ((len >= dwMemLength) || (dwMemPos + len > dwMemLength)) return TRUE; + if ((len >= dwMemLength) || (dwMemPos + len > dwMemLength)) return true; Patterns.Insert(iPat, 64); MODCOMMAND* m = Patterns[iPat]; - if (!m) return TRUE; + if (!m) return true; const BYTE *p = lpStream + dwMemPos; UINT row = 0, i = 0; while ((row < PatternSize[iPat]) && (i+2 < len)) @@ -240,11 +240,11 @@ // Read Samples for (UINT iSmp=1; iSmp<=m_nSamples; iSmp++) if (Ins[iSmp].nLength) { - if (dwMemPos >= dwMemLength - 9) return TRUE; + if (dwMemPos >= dwMemLength - 9) return true; UINT flags = (Ins[iSmp].uFlags & CHN_16BIT) ? RS_AMS16 : RS_AMS8; dwMemPos += ReadSample(&Ins[iSmp], flags, (LPSTR)(lpStream+dwMemPos), dwMemLength-dwMemPos); } - return TRUE; + return true; } @@ -299,7 +299,7 @@ DWORD loopend; WORD frequency; BYTE finetune; - WORD c4speed; + WORD nC5Speed; CHAR transpose; BYTE volume; BYTE flags; @@ -309,7 +309,7 @@ #pragma pack() -BOOL CSoundFile::ReadAMS2(LPCBYTE lpStream, DWORD dwMemLength) +bool CSoundFile::ReadAMS2(LPCBYTE lpStream, DWORD dwMemLength) //------------------------------------------------------------ { const AMS2FILEHEADER *pfh = (AMS2FILEHEADER *)lpStream; @@ -416,7 +416,7 @@ psmp->nLength = pams->length; psmp->nLoopStart = pams->loopstart; psmp->nLoopEnd = pams->loopend; - psmp->nC4Speed = pams->c4speed; + psmp->nC5Speed = pams->nC5Speed; psmp->RelativeTone = pams->transpose; psmp->nVolume = pams->volume / 2; packedsamples[smpmap[ismp]] = pams->flags; Modified: trunk/OpenMPT/soundlib/Load_far.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_far.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/Load_far.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -58,11 +58,11 @@ #pragma pack() -BOOL CSoundFile::ReadFAR(const BYTE *lpStream, DWORD dwMemLength) +bool CSoundFile::ReadFAR(const BYTE *lpStream, DWORD dwMemLength) //--------------------------------------------------------------- { if(dwMemLength < sizeof(FARHEADER1)) - return FALSE; + return false; FARHEADER1 farHeader; memcpy(&farHeader, lpStream, sizeof(FARHEADER1)); @@ -73,10 +73,10 @@ BYTE samplemap[8]; if ((!lpStream) || (dwMemLength < 1024) || (LittleEndian(pmh1->id) != FARFILEMAGIC) - || (pmh1->magic2[0] != 13) || (pmh1->magic2[1] != 10) || (pmh1->magic2[2] != 26)) return FALSE; + || (pmh1->magic2[0] != 13) || (pmh1->magic2[1] != 10) || (pmh1->magic2[2] != 26)) return false; headerlen = LittleEndianW(pmh1->headerlen); pmh1->stlen = LittleEndianW( pmh1->stlen ); /* inplace byteswap -- Toad */ - if ((headerlen >= dwMemLength) || (dwMemPos + pmh1->stlen + sizeof(FARHEADER2) >= dwMemLength)) return FALSE; + if ((headerlen >= dwMemLength) || (dwMemPos + pmh1->stlen + sizeof(FARHEADER2) >= dwMemLength)) return false; // Globals m_nType = MOD_TYPE_FAR; m_nChannels = 16; @@ -108,12 +108,12 @@ dwMemPos += pmh1->stlen; } // Reading orders - if (sizeof(FARHEADER2) > dwMemLength - dwMemPos) return TRUE; + if (sizeof(FARHEADER2) > dwMemLength - dwMemPos) return true; FARHEADER2 farHeader2; memcpy(&farHeader2, lpStream + dwMemPos, sizeof(FARHEADER2)); pmh2 = &farHeader2; dwMemPos += sizeof(FARHEADER2); - if (dwMemPos >= dwMemLength) return TRUE; + if (dwMemPos >= dwMemLength) return true; for (UINT iorder=0; iorder<MAX_ORDERS; iorder++) { Order[iorder] = (iorder <= pmh2->snglen) ? pmh2->orders[iorder] : Order.GetInvalidPatIndex(); @@ -121,7 +121,7 @@ m_nRestartPos = pmh2->loopto; // Reading Patterns dwMemPos += headerlen - (869 + pmh1->stlen); - if (dwMemPos >= dwMemLength) return TRUE; + if (dwMemPos >= dwMemLength) return true; // byteswap pattern data. for(uint16 psfix = 0; psfix < 256; psfix++) @@ -139,7 +139,7 @@ dwMemPos += patlen; continue; } - if (dwMemPos + patlen >= dwMemLength) return TRUE; + if (dwMemPos + patlen >= dwMemLength) return true; UINT rows = (patlen - 2) >> 6; if (!rows) { @@ -148,7 +148,7 @@ } if (rows > 256) rows = 256; if (rows < 16) rows = 16; - if(Patterns.Insert(ipat, rows)) return TRUE; + if(Patterns.Insert(ipat, rows)) return true; MODCOMMAND *m = Patterns[ipat]; UINT patbrk = lpStream[dwMemPos]; const BYTE *p = lpStream + dwMemPos + 2; @@ -239,13 +239,13 @@ dwMemPos += patlen; } // Reading samples - if (dwMemPos + 8 >= dwMemLength) return TRUE; + if (dwMemPos + 8 >= dwMemLength) return true; memcpy(samplemap, lpStream+dwMemPos, 8); dwMemPos += 8; MODINSTRUMENT *pins = &Ins[1]; for (UINT ismp=0; ismp<64; ismp++, pins++) if (samplemap[ismp >> 3] & (1 << (ismp & 7))) { - if (dwMemPos + sizeof(FARSAMPLE) > dwMemLength) return TRUE; + if (dwMemPos + sizeof(FARSAMPLE) > dwMemLength) return true; const FARSAMPLE *pfs = reinterpret_cast<const FARSAMPLE*>(lpStream + dwMemPos); dwMemPos += sizeof(FARSAMPLE); m_nSamples = ismp + 1; @@ -255,7 +255,7 @@ pins->nLoopStart = LittleEndian(pfs->reppos) ; pins->nLoopEnd = LittleEndian(pfs->repend) ; pins->nFineTune = 0; - pins->nC4Speed = 8363*2; + pins->nC5Speed = 8363*2; pins->nGlobalVol = 64; pins->nVolume = pfs->volume << 4; pins->uFlags = 0; @@ -274,6 +274,6 @@ } dwMemPos += length; } - return TRUE; + return true; } Modified: trunk/OpenMPT/soundlib/Load_gdm.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_gdm.cpp 2009-08-08 21:26:10 UTC (rev 317) +++ trunk/OpenMPT/soundlib/Load_gdm.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -10,7 +10,7 @@ * Hint 1: Most (all?) of the unsupported features were not supported in 2GDM / BWSB either. * Hint 2: Files will be played like their original formats would be played in MPT, so no * BWSB quirks including crashes and freezes are supported. :-P -*/ + */ #include "stdafx.h" #include "sndfile.h" @@ -66,17 +66,17 @@ BYTE Pan; // default pan } GDMSAMPLEHEADER, *PGDMSAMPLEHEADER; -BOOL CSoundFile::ReadGDM(const LPCBYTE lpStream, const DWORD dwMemLength) +bool CSoundFile::ReadGDM(const LPCBYTE lpStream, const DWORD dwMemLength) //----------------------------------------------------------- { - if ((!lpStream) || (dwMemLength < sizeof(GDMHEADER))) return FALSE; + if ((!lpStream) || (dwMemLength < sizeof(GDMHEADER))) return false; const PGDMHEADER pHeader = (PGDMHEADER)lpStream; // is it a valid GDM file? if( (LittleEndian(pHeader->ID) != 0xFE4D4447) || //GDM\xFE (pHeader->DOSEOF[0] != 13 || pHeader->DOSEOF[1] != 10 || pHeader->DOSEOF[2] != 26) || //CR+LF+EOF - (LittleEndian(pHeader->ID2) != 0x53464D47)) return FALSE; //GMFS + (LittleEndian(pHeader->ID2) != 0x53464D47)) return false; //GMFS // song name memset(m_szNames, 0, sizeof(m_szNames)); @@ -87,7 +87,7 @@ if(pHeader->FormMajorVer != 1 || pHeader->FormMinorVer != 0) { ::MessageBox(0, TEXT("GDM file seems to be valid, but this format version is currently not supported."), TEXT("OpenMPT GDM import"), MB_ICONERROR); - return FALSE; + return false; } // interesting question: Is TrackID, TrackMajorVer, TrackMinorVer relevant? The only TrackID should be 0 - 2GDM.exe, so the answer would be no. @@ -149,7 +149,7 @@ break; default: ::MessageBox(0, TEXT("GDM file seems to be valid, but the original format is currently not supported.\nThis should not happen."), TEXT("OpenMPT GDM import"), MB_ICONERROR); - return FALSE; + return false; break; } UINT32 iSampleOffset = LittleEndian(pHeader->SamOffset), @@ -169,7 +169,7 @@ || dwMemLength < iMTOffset || dwMemLength - iMTOffset < iMTLength || dwMemLength < iSSOffset || dwMemLength - iSSOffset < iSSLength || dwMemLength < iTGOffset || dwMemLength - iTGOffset < iTGLength) - return FALSE; + return false; // read orders Order.ReadAsByte(lpStream + iOrdOffset, pHeader->NOO + 1, dwMemLength - iOrdOffset); @@ -189,7 +189,7 @@ SetNullTerminator(m_szNames[iSmp]); memcpy(Ins[iSmp].name, pSample->FileName, 12); - Ins[iSmp].nC4Speed = LittleEndianW(pSample->C4Hertz); + Ins[iSmp].nC5Speed = LittleEndianW(pSample->C4Hertz); Ins[iSmp].nGlobalVol = 256; // not supported in this format Ins[iSmp].nLength = min(LittleEndian(pSample->Length), MAX_SAMPLE_LENGTH); // in bytes Ins[iSmp].nLoopStart = min(LittleEndian(pSample->LoopBegin), Ins[iSmp].nLength); // in samples @@ -322,7 +322,7 @@ bNote = (bNote & 0x7F) - 1; // this format doesn't have note cuts if(bNote < 0xF0) bNote = (bNote & 0x0F) + 12 * (bNote >> 4) + 13; - if(bNote == 0xFF) bNote = 0; + if(bNote == 0xFF) bNote = NOTE_NONE; m->note = bNote; m->instr = bSample; @@ -550,6 +550,6 @@ ::MessageBox(0, s, TEXT("OpenMPT GDM import"), MB_ICONWARNING); } - return TRUE; + return true; } Added: trunk/OpenMPT/soundlib/Load_imf.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_imf.cpp (rev 0) +++ trunk/OpenMPT/soundlib/Load_imf.cpp 2009-08-09 23:07:50 UTC (rev 318) @@ -0,0 +1,532 @@ +/* + * Purpose: Load IMF (Imago Orpheus) modules + * Authors: Storlek (http://schismtracker.org/) + * Johannes Schultz (OpenMPT Port) + * + * Thanks to Storlek for allowing me to use this code! + */ + +#include "stdafx.h" +#include "sndfile.h" + +#pragma pack(1) + +struct imf_channel { + char name[12]; // Channelname (ASCIIZ-String, max 11 chars) + BYTE chorus; // Default chorus + BYTE reverb; // Default reverb + BYTE panning; // Pan positions 00-FF + BYTE status; // Channel status: 0 = enabled, 1 = mute, 2 = disabled (ignore effects!) +}; + +struct imf_header { + char title[32]; // Songname (ASCIIZ-String, max. 31 chars) + UINT16 ordnum; // Number of orders saved + UINT16 patnum; // Number of patterns saved + UINT16 insnum; // Number of instruments saved + UINT16 flags; // Module flags (&1 => linear) + BYTE unused1[8]; + BYTE tempo; // Default tempo (Axx, 1..255) + BYTE bpm; // Default beats per minute (BPM) (Txx, 32..255) + BYTE master; // Default mastervolume (Vxx, 0..64) + BYTE amp; // Amplification factor (mixing volume, 4..127) + BYTE unused2[8]; + char im10[4]; // 'IM10' + struct imf_channel channels[32]; // Channel settings + BYTE orderlist[256]; // Order list (0xff = +++; blank out anything beyond ordnum) +}; + +enum { + IMF_ENV_VOL = 0, + IMF_ENV_PAN = 1, + IMF_ENV_FILTER = 2, +}; + +struct imf_env { + BYTE points; // Number of envelope points + BYTE sustain; // Envelope sustain point + BYTE loop_start; // Envelope loop start point + BYTE loop_end; // Envelope loop end point + BYTE flags; // Envelope flags + BYTE unused[3]; +}; + +struct imf_envnodes { + UINT16 tick; + UINT16 value; +}; + +struct imf_instrument { + char name[32]; // Inst. name (ASCIIZ-String, max. 31 chars) + BYTE map[120]; // Multisample settings + BYTE unused[8]; + struct imf_envnodes nodes[3][16]; + struct imf_env env[3]; + UINT16 fadeout; // Fadeout rate (0...0FFFH) + UINT16 smpnum; // Number of samples in instrument + char ii10[4]; // 'II10' +}; + +struct imf_sample { + char name[13]; // Sample filename (12345678.ABC) */ + BYTE unused1[3]; + UINT32 length; // Length + UINT32 loop_start; // Loop start + UINT32 loop_end; // Loop end + UINT32 C5Speed; // Samplerate + BYTE volume; // Default volume (0..64) + BYTE panning; // Default pan (00h = Left / 80h = Middle) + BYTE unused2[14]; + BYTE flags; // Sample flags + BYTE unused3[5]; + UINT16 ems; // Reserved for internal usage + UINT32 dram; // Reserved for internal usage + char is10[4]; // 'IS10' +}; +#pragma pack() + + +static BYTE imf_efftrans[] = { + CMD_NONE, + CMD_SPEED, // 0x01 1xx Set Tempo + CMD_TEMPO, // 0x02 2xx Set BPM + CMD_TONEPORTAMENTO, // 0x03 3xx Tone Portamento (*) + CMD_TONEPORTAVOL, // 0x04 4xy Tone Portamento + Volume Slide (*) + CMD_VIBRATO, // 0x05 5xy Vibrato (*) + CMD_VIBRATOVOL, // 0x06 6xy Vibrato + Volume Slide (*) + CMD_FINEVIBRATO, // 0x07 7xy Fine Vibrato (*) + CMD_TREMOLO, // 0x08 8xy Tremolo (*) + CMD_ARPEGGIO, // 0x09 9xy Arpeggio (*) + CMD_PANNING8, // 0x0A Axx Set Pan Position + CMD_PANNINGSLIDE, // 0x0B Bxy Pan Slide (*) + CMD_VOLUME, // 0x0C Cxx Set Volume + CMD_VOLUMESLIDE, // 0x0D Dxy Volume Slide (*) + CMD_VOLUMESLIDE, // 0x0E Exy Fine Volume Slide (*) + CMD_S3MCMDEX, // 0x0F Fxx Set Finetune + CMD_NOTESLIDEUP, // 0x10 Gxy Note Slide Up (*) + CMD_NOTESLIDEDOWN, // 0x11 Hxy Note Slide Down (*) + CMD_PORTAMENTOUP, // 0x12 Ixx Slide Up (*) + CMD_PORTAMENTODOWN, // 0x13 Jxx Slide Down (*) + CMD_PORTAMENTOUP, // 0x14 Kxx Fine Slide Up (*) + CMD_PORTAMENTODOWN, // 0x15 Lxx Fine Slide Down (*) + CMD_MIDI, // 0x16 Mxx Set Filter Cutoff - XXX + CMD_NONE, // 0x17 Nxy Filter Slide + Resonance - XXX + CMD_OFFSET, // 0x18 Oxx Set Sample Offset (*) + CMD_NONE, // 0x19 Pxx Set Fine Sample Offset - XXX + CMD_KEYOFF, // 0x1A Qxx Key Off + CMD_RETRIG, // 0x1B Rxy Retrig (*) + CMD_TREMOR, // 0x1C Sxy Tremor (*) + CMD_POSITIONJUMP, // 0x1D Txx Position Jump + CMD_PATTERNBREAK, // 0x1E Uxx Pattern Break + CMD_GLOBALVOLUME, // 0x1F Vxx Set Mastervolume + CMD_GLOBALVOLSLIDE, // 0x20 Wxy Mastervolume Slide (*) + CMD_S3MCMDEX, // 0x21 Xxx Extended Effect + // X1x Set Filter + // X3x Glissando + // X5x Vibrato Waveform + // X8x Tremolo Waveform + // XAx Pattern Loop + // XBx Pattern Delay + // XCx Note Cut + // XDx Note Delay + // XEx Ignore Envelope + // XFx Invert Loop + CMD_NONE, // 0x22 Yxx Chorus - XXX + CMD_NONE, // 0x23 Zxx Reverb - XXX +}; + +static void import_imf_effect(MODCOMMAND *note) +{ + BYTE n; + // fix some of them + switch (note->command) { + case 0xe: // fine volslide + // hackaround to get almost-right behavior for fine slides (i think!) + if (note->param == 0) + /* nothing */; + else if (note->param == 0xf0) + note->param = 0xef; + else if (note->param == 0x0f) + note->param = 0xfe; + else if (note->param & 0xf0) + note->param |= 0xf; + else + note->param |= 0xf0; + break; + case 0xf: // set finetune + // we don't implement this, but let's at least import the value + note->param = 0x20 | min(note->param >> 4, 0xf); + break; + case 0x14: // fine slide up + case 0x15: // fine slide down + // this is about as close as we can do... + if (note->param >> 4) + note->param = 0xf0 | m... [truncated message content] |