From: <sag...@us...> - 2012-08-05 18:38:15
|
Revision: 1341 http://modplug.svn.sourceforge.net/modplug/?rev=1341&view=rev Author: saga-games Date: 2012-08-05 18:38:07 +0000 (Sun, 05 Aug 2012) Log Message: ----------- [Ref] Also made ModSample::uFlags a flagset. Modified Paths: -------------- trunk/OpenMPT/common/FlagSet.h trunk/OpenMPT/installer/vst_scan.iss trunk/OpenMPT/mptrack/Undo.cpp trunk/OpenMPT/mptrack/Undo.h trunk/OpenMPT/soundlib/LOAD_DMF.CPP trunk/OpenMPT/soundlib/LOAD_DSM.CPP trunk/OpenMPT/soundlib/Load_gdm.cpp trunk/OpenMPT/soundlib/Load_okt.cpp trunk/OpenMPT/soundlib/Load_psm.cpp trunk/OpenMPT/soundlib/Load_s3m.cpp trunk/OpenMPT/soundlib/ModSample.cpp trunk/OpenMPT/soundlib/ModSample.h trunk/OpenMPT/soundlib/SampleFormats.cpp trunk/OpenMPT/soundlib/Sndfile.cpp trunk/OpenMPT/soundlib/WAVTools.cpp trunk/OpenMPT/soundlib/WAVTools.h Modified: trunk/OpenMPT/common/FlagSet.h =================================================================== --- trunk/OpenMPT/common/FlagSet.h 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/common/FlagSet.h 2012-08-05 18:38:07 UTC (rev 1341) @@ -10,18 +10,18 @@ #include <string> -template <typename enum_t> +template <typename enum_t, typename store_t = enum_t> class FlagSet { public: // Default constructor (no flags set) - FlagSet() : flags(enum_t(0)) + FlagSet() : flags(store_t(0)) { } // Value constructor - explicit FlagSet(enum_t value) : flags(value) + explicit FlagSet(enum_t value) : flags(static_cast<store_t>(value)) { } @@ -29,7 +29,7 @@ // Explicit conversion operator operator enum_t() const { - return flags; + return static_cast<enum_t>(flags); } operator std::string() const @@ -56,38 +56,31 @@ return str; } - // Set all flags. - FlagSet &set() - { - flags = ~enum_t(0); - return *this; - } - // Set one or more flags. FlagSet &set(enum_t flag) { - flags = (flags | flag); + flags = (flags | static_cast<store_t>(flag)); return *this; } // Set or clear one or more flags. FlagSet &set(enum_t flag, bool val) { - flags = (val ? (flags | flag) : (flags & ~flag)); + flags = (val ? (flags | static_cast<store_t>(flag)) : (flags & ~static_cast<store_t>(flag))); return *this; } // Clear or flags. FlagSet &reset() { - flags = enum_t(0); + flags = store_t(0); return *this; } // Clear one or more flags. FlagSet &reset(enum_t flag) { - flags &= ~flag; + flags &= ~static_cast<store_t>(flag); return *this; } @@ -101,7 +94,7 @@ // Toggle one or more flags. FlagSet &flip(enum_t flag) { - flags ^= flag; + flags ^= static_cast<store_t>(flag); return *this; } @@ -114,7 +107,7 @@ // Test if one or more flags are set. Returns true if at least one of the given flags is set. bool test(enum_t flag) const { - return (flags & flag) > 0; + return (flags & static_cast<store_t>(flag)) > 0; } // Test if any flag is set. @@ -129,26 +122,26 @@ return flags == 0; } - FlagSet<enum_t> &operator = (const enum_t other) + FlagSet<enum_t, store_t> &operator = (const enum_t other) { - flags = other; + flags = static_cast<store_t>(other); return *this; } - FlagSet<enum_t> &operator &= (const enum_t other) + FlagSet<enum_t, store_t> &operator &= (const enum_t other) { - flags &= other; + flags &= static_cast<store_t>(other); return *this; } - FlagSet<enum_t> &operator |= (const enum_t other) + FlagSet<enum_t, store_t> &operator |= (const enum_t other) { - flags |= other; + flags |= static_cast<store_t>(other); return *this; } private: - enum_t flags; + store_t flags; }; Modified: trunk/OpenMPT/installer/vst_scan.iss =================================================================== --- trunk/OpenMPT/installer/vst_scan.iss 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/installer/vst_scan.iss 2012-08-05 18:38:07 UTC (rev 1341) @@ -42,6 +42,7 @@ // Try not to call a function for every file // as this could take a very long time. // . + MsgBox(FilePath, mbInformation, MB_OK); SetIniString('VST Plugins', 'Plugin' + IntToStr(VSTPluginNumber), FilePath, INIFile); VSTPluginNumber := VSTPluginNumber + 1; // <-- End action. @@ -76,7 +77,7 @@ OldVSTPluginNumber := VSTPluginNumber; // The folder to scan. - Dir := ExpandConstant('{pf}\Steinberg\VstPlugins'); + Dir := ExpandConstant('E:\VST-Plugins\'); RegQueryStringValue(HKEY_LOCAL_MACHINE, 'Software\VST', 'VSTPluginsPath', Dir); // won't touch Dir if registry path does not exist // The progress page. ProgressPage := CreateOutputProgressPage (CustomMessage ('ProgressTitle'), @@ -87,6 +88,8 @@ // Make the Cancel button visible during the operation. ;WizardForm.CancelButton.Visible := TRUE; // Scan the folder. + MsgBox(Dir, mbInformation, MB_OK); + MsgBox(INIFile, mbInformation, MB_OK); ProcessDirectory (Dir, TRUE, INIFile); // Hide the progress page. try Modified: trunk/OpenMPT/mptrack/Undo.cpp =================================================================== --- trunk/OpenMPT/mptrack/Undo.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/mptrack/Undo.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -211,8 +211,8 @@ // Check if an undo buffer actually exists. -bool CPatternUndo::CanUndo() -//-------------------------- +bool CPatternUndo::CanUndo() const +//-------------------------------- { return (UndoBuffer.size() > 0); } @@ -236,7 +236,7 @@ void CPatternUndo::RemoveLastUndoStep() //------------------------------------- { - if(CanUndo() == false) return; + if(!CanUndo()) return; DeleteUndoStep(UndoBuffer.size() - 1); } @@ -296,7 +296,7 @@ const ModSample &oldsample = pSndFile->GetSample(smp); // Save old sample header - MemCopy(sUndo.OldSample, oldsample); + sUndo.OldSample = oldsample; MemCopy(sUndo.szOldName, pSndFile->m_szNames[smp]); sUndo.nChangeType = changeType; Modified: trunk/OpenMPT/mptrack/Undo.h =================================================================== --- trunk/OpenMPT/mptrack/Undo.h 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/mptrack/Undo.h 2012-08-05 18:38:07 UTC (rev 1341) @@ -64,7 +64,7 @@ void ClearUndo(); bool PrepareUndo(PATTERNINDEX pattern, CHANNELINDEX firstChn, ROWINDEX firstRow, CHANNELINDEX numChns, ROWINDEX numRows, bool linkToPrevious = false, bool storeChannelInfo = false); PATTERNINDEX Undo(); - bool CanUndo(); + bool CanUndo() const; void RemoveLastUndoStep(); void SetParent(CModDoc *pModDoc) { m_pModDoc = pModDoc; } Modified: trunk/OpenMPT/soundlib/LOAD_DMF.CPP =================================================================== --- trunk/OpenMPT/soundlib/LOAD_DMF.CPP 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/LOAD_DMF.CPP 2012-08-05 18:38:07 UTC (rev 1341) @@ -759,7 +759,7 @@ dwMemPos += sizeof(DMFCHUNK_SAMPLEHEADER); ModSample &sample = pSndFile->GetSample(nSmp); - MemsetZero(sample); + sample.Initialize(); sample.nLength = LittleEndian(smpHead->length); sample.nSustainEnd = min(sample.nLength, LittleEndian(smpHead->loopEnd)); sample.nSustainStart = min(sample.nSustainEnd, LittleEndian(smpHead->loopStart)); @@ -778,7 +778,6 @@ sample.nVolume = 256; } sampleFlags = smpHead->flags; - sample.uFlags = 0; if((sampleFlags & DMFSMP_LOOP) != 0 && sample.nSustainEnd > sample.nSustainStart) { sample.uFlags |= CHN_SUSTAINLOOP; Modified: trunk/OpenMPT/soundlib/LOAD_DSM.CPP =================================================================== --- trunk/OpenMPT/soundlib/LOAD_DSM.CPP 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/LOAD_DSM.CPP 2012-08-05 18:38:07 UTC (rev 1341) @@ -223,7 +223,7 @@ StringFixer::ReadString<StringFixer::nullTerminated>(sample.filename, pSmp->filename); sample.nC5Speed = pSmp->c2spd; - sample.uFlags = (WORD)((pSmp->flags & 1) ? CHN_LOOP : 0); + sample.uFlags.set(CHN_LOOP, (pSmp->flags & 1) != 0); sample.nLength = pSmp->length; sample.nLoopStart = pSmp->loopstart; sample.nLoopEnd = pSmp->loopend; Modified: trunk/OpenMPT/soundlib/Load_gdm.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_gdm.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/Load_gdm.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -238,7 +238,7 @@ } } - Samples[smp].uFlags = 0; + Samples[smp].uFlags.reset(); if(gdmSample.flags & GDMSampleHeader::smpLoop) Samples[smp].uFlags |= CHN_LOOP; // Loop sample if(gdmSample.flags & GDMSampleHeader::smpVolume) Modified: trunk/OpenMPT/soundlib/Load_okt.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_okt.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/Load_okt.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -83,7 +83,7 @@ oktSmp.volume = oktSmp.volume; oktSmp.type = oktSmp.type; - MemsetZero(mptSmp); + mptSmp.Initialize(); StringFixer::ReadString<StringFixer::maybeNullTerminated>(pSndFile->m_szNames[nSmp], oktSmp.name); mptSmp.nC5Speed = 8287; @@ -91,7 +91,7 @@ mptSmp.nVolume = min(oktSmp.volume, 64) * 4; mptSmp.nLength = oktSmp.length & ~1; // round down // parse loops - if (oktSmp.loopLength > 2 && ((UINT)oktSmp.loopStart) + ((UINT)oktSmp.loopLength) <= mptSmp.nLength) + if (oktSmp.loopLength > 2 && static_cast<SmpLength>(oktSmp.loopStart) + static_cast<SmpLength>(oktSmp.loopLength) <= mptSmp.nLength) { mptSmp.nSustainStart = oktSmp.loopStart; mptSmp.nSustainEnd = oktSmp.loopStart + oktSmp.loopLength; Modified: trunk/OpenMPT/soundlib/Load_psm.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_psm.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/Load_psm.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -143,7 +143,7 @@ mptSmp.nLoopEnd = loopEnd; // Hmm... apparently we should add +1 for Extreme Pinball tunes here? See sample 8 in the medieval table music. mptSmp.nPan = 128; mptSmp.nVolume = (defaultVolume + 1) * 2; - mptSmp.uFlags = (flags & 0x80) ? CHN_LOOP : 0; + mptSmp.uFlags.set(CHN_LOOP, (flags & 0x80) != 0); LimitMax(mptSmp.nLoopEnd, mptSmp.nLength); LimitMax(mptSmp.nLoopStart, mptSmp.nLoopEnd); } @@ -201,7 +201,7 @@ mptSmp.nLoopEnd = loopEnd; mptSmp.nPan = 128; mptSmp.nVolume = (defaultVolume + 1) * 2; - mptSmp.uFlags = (flags & 0x80) ? CHN_LOOP : 0; + mptSmp.uFlags.set(CHN_LOOP, (flags & 0x80) != 0); LimitMax(mptSmp.nLoopEnd, mptSmp.nLength); LimitMax(mptSmp.nLoopStart, mptSmp.nLoopEnd); } @@ -1049,7 +1049,7 @@ mptSmp.nVolume = volume << 2; mptSmp.nGlobalVol = 256; - mptSmp.uFlags = 0; + mptSmp.uFlags.reset(); if(flags & PSM16SampleHeader::smp16Bit) { mptSmp.uFlags |= CHN_16BIT; Modified: trunk/OpenMPT/soundlib/Load_s3m.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_s3m.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/Load_s3m.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -105,13 +105,13 @@ command = '\\'; break; case CMD_XFINEPORTAUPDOWN: - if(param & 0x0F) switch(param & 0xF0) + switch(param & 0xF0) { case 0x10: command = 'F'; param = (param & 0x0F) | 0xE0; break; case 0x20: command = 'E'; param = (param & 0x0F) | 0xE0; break; case 0x90: command = 'S'; break; default: command = 0; - } else command = 0; + } break; case CMD_MODCMDEX: { @@ -300,13 +300,13 @@ mptSmp.nLength = length; mptSmp.nLoopStart = min(loopStart, mptSmp.nLength - 1); mptSmp.nLoopEnd = min(loopEnd, mptSmp.nLength); - mptSmp.uFlags = (flags & smpLoop) ? CHN_LOOP : 0; + mptSmp.uFlags.set(CHN_LOOP, (flags & smpLoop) != 0); } if(mptSmp.nLoopEnd < 2 || mptSmp.nLoopStart >= mptSmp.nLoopEnd || mptSmp.nLoopEnd - mptSmp.nLoopStart < 1) { mptSmp.nLoopStart = mptSmp.nLoopEnd = 0; - mptSmp.uFlags = 0; + mptSmp.uFlags.reset(); } // Volume / Panning @@ -369,19 +369,18 @@ // Retrieve the internal sample format flags for this sample. SampleIO GetSampleFormat(bool signedSamples) const { - SampleIO format( - (flags & S3MSampleHeader::smp16Bit) ? SampleIO::_16bit : SampleIO::_8bit, - (flags & S3MSampleHeader::smpStereo) ? SampleIO::stereoSplit : SampleIO::mono, - SampleIO::littleEndian, - signedSamples ? SampleIO::signedPCM : SampleIO::unsignedPCM); - - // MODPlugin :( - if(!(flags & S3MSampleHeader::smp16Bit) && pack == S3MSampleHeader::pADPCM) + if(pack == S3MSampleHeader::pADPCM && !(flags & S3MSampleHeader::smp16Bit) && !(flags & S3MSampleHeader::smpStereo)) { - format |= SampleIO::ADPCM; + // MODPlugin :( + return SampleIO(SampleIO::_8bit, SampleIO::mono, SampleIO::littleEndian, SampleIO::ADPCM); + } else + { + return SampleIO( + (flags & S3MSampleHeader::smp16Bit) ? SampleIO::_16bit : SampleIO::_8bit, + (flags & S3MSampleHeader::smpStereo) ? SampleIO::stereoSplit : SampleIO::mono, + SampleIO::littleEndian, + signedSamples ? SampleIO::signedPCM : SampleIO::unsignedPCM); } - - return format; } }; Modified: trunk/OpenMPT/soundlib/ModSample.cpp =================================================================== --- trunk/OpenMPT/soundlib/ModSample.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/ModSample.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -107,10 +107,10 @@ nVibSweep = 0; nVibDepth = 0; nVibRate = 0; - uFlags &= ~(CHN_PANNING | CHN_SUSTAINLOOP | CHN_LOOP); + uFlags.reset(CHN_PANNING | CHN_SUSTAINLOOP | CHN_LOOP); if(type == MOD_TYPE_XM) { - uFlags |= CHN_PANNING; + uFlags.set(CHN_PANNING); } filename[0] = '\0'; } Modified: trunk/OpenMPT/soundlib/ModSample.h =================================================================== --- trunk/OpenMPT/soundlib/ModSample.h 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/ModSample.h 2012-08-05 18:38:07 UTC (rev 1341) @@ -17,20 +17,26 @@ SmpLength nLoopStart, nLoopEnd; // Dito SmpLength nSustainStart, nSustainEnd; // Dito LPSTR pSample; // Pointer to sample data - uint32 nC5Speed; // Frequency of middle c, in Hz (for IT/S3M/MPTM) + uint32 nC5Speed; // Frequency of middle-C, in Hz (for IT/S3M/MPTM) uint16 nPan; // Default sample panning (if pan flag is set) uint16 nVolume; // Default volume uint16 nGlobalVol; // Global volume (sample volume is multiplied by this) - uint16 uFlags; // Sample flags + FlagSet<ChannelFlags, uint16> uFlags; // Sample flags int8 RelativeTone; // Relative note to middle c (for MOD/XM) int8 nFineTune; // Finetune period (for MOD/XM) uint8 nVibType; // Auto vibrato type uint8 nVibSweep; // Auto vibrato sweep (i.e. how long it takes until the vibrato effect reaches its full strength) uint8 nVibDepth; // Auto vibrato depth uint8 nVibRate; // Auto vibrato rate (speed) - //char name[MAX_SAMPLENAME]; // Maybe it would be nicer to have sample names here, but that would require some refactoring. Also, would this slow down the mixer (cache misses)? + //char name[MAX_SAMPLENAME]; // Maybe it would be nicer to have sample names here, but that would require some refactoring. Also, the current structure size is 64 Bytes - would adding the sample name here slow down the mixer (cache misses)? char filename [MAX_SAMPLEFILENAME]; + ModSample(MODTYPE type = MOD_TYPE_NONE) + { + pSample = nullptr; + Initialize(type); + } + // Return the size of one (elementary) sample in bytes. uint8 GetElementarySampleSize() const { return (uFlags & CHN_16BIT) ? 2 : 1; } Modified: trunk/OpenMPT/soundlib/SampleFormats.cpp =================================================================== --- trunk/OpenMPT/soundlib/SampleFormats.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/SampleFormats.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -65,19 +65,26 @@ if (((psig[0] == LittleEndian(0x46464952)) && (psig[2] == LittleEndian(0x45564157))) // RIFF....WAVE signature || ((psig[0] == LittleEndian(0x5453494C)) && (psig[2] == LittleEndian(0x65766177))) // LIST....wave || (psig[76/4] == LittleEndian(0x53524353)) // S3I signature - || ((psig[0] == BigEndian(0x464F524D)) && (psig[2] == BigEndian(0x46464941))) // AIFF signature - || ((psig[0] == BigEndian(0x464F524D)) && (psig[2] == BigEndian(0x41494643))) // AIFF-C signature + || ((psig[0] == BigEndian(0x464F524D)) && (psig[2] == LittleEndian(0x46464941))) // AIFF signature + || ((psig[0] == BigEndian(0x464F524D)) && (psig[2] == LittleEndian(0x43464941))) // AIFF-C signature || ((psig[0] == BigEndian(0x464F524D)) && (psig[2] == LittleEndian(0x58565338))) // 8SVX signature || (psig[0] == LittleEndian(ITSample::magic)) // ITS signature ) { + // Scanning free sample + SAMPLEINDEX nSample = GetNextFreeSample(nInstr); + if(nSample == SAMPLEINDEX_INVALID) + { + return false; + } + // Loading Instrument ModInstrument *pIns; try { - pIns = new ModInstrument(); + pIns = new ModInstrument(nSample); } catch(MPTMemoryException) { return false; @@ -86,19 +93,17 @@ DestroyInstrument(nInstr, deleteAssociatedSamples); Instruments[nInstr] = pIns; - // Scanning free sample - SAMPLEINDEX nSample = GetNextFreeSample(nInstr); - if(nSample == SAMPLEINDEX_INVALID) + ReadSampleFromFile(nSample, lpMemFile, dwFileLength); + + if(nSample > GetNumSamples()) { - return false; - } else if(nSample > GetNumSamples()) - { m_nSamples = nSample; } + if(nInstr > GetNumInstruments()) + { + m_nInstruments = nInstr; + } - Instruments[nInstr]->AssignSample(nSample); - - ReadSampleFromFile(nSample, lpMemFile, dwFileLength); return true; } return false; @@ -306,6 +311,7 @@ if(!wavFile.IsValid() || wavFile.GetNumChannels() == 0 || wavFile.GetNumChannels() > 2 + || wavFile.GetBitsPerSample() == 0 || wavFile.GetBitsPerSample() > 32 || (wavFile.GetSampleFormat() != WAVFormatChunk::fmtPCM && wavFile.GetSampleFormat() != WAVFormatChunk::fmtFloat && wavFile.GetSampleFormat() != WAVFormatChunk::fmtIMA_ADPCM)) { @@ -336,21 +342,14 @@ } else { // PCM / Float + static const SampleIO::Bitdepth bitDepth[] = { SampleIO::_8bit, SampleIO::_16bit, SampleIO::_24bit, SampleIO::_32bit }; + SampleIO sampleIO( - SampleIO::_8bit, + bitDepth[(wavFile.GetBitsPerSample() - 1) / 8], (wavFile.GetNumChannels() > 1) ? SampleIO::stereoInterleaved : SampleIO::mono, SampleIO::littleEndian, (wavFile.GetBitsPerSample() > 8) ? SampleIO::signedPCM : SampleIO::unsignedPCM); - if(wavFile.GetBitsPerSample() <= 8) - sampleIO |= SampleIO::_8bit; - else if(wavFile.GetBitsPerSample() <= 16) - sampleIO |= SampleIO::_16bit; - else if(wavFile.GetBitsPerSample() <= 24) - sampleIO |= SampleIO::_24bit; - else if(wavFile.GetBitsPerSample() <= 32) - sampleIO |= SampleIO::_32bit; - if(wavFile.GetSampleFormat() == WAVFormatChunk::fmtFloat) { sampleIO |= SampleIO::floatPCM; @@ -1346,22 +1345,25 @@ // Is this a proper sample? if(sampleInfo.numSampleFrames == 0 - || sampleInfo.numChannels < 1 || sampleInfo.numChannels > 2 - || sampleInfo.sampleSize < 1 || sampleInfo.sampleSize > 32) + || sampleInfo.numChannels == 0 || sampleInfo.numChannels > 2 + || sampleInfo.sampleSize == 0 || sampleInfo.sampleSize > 32) { return false; } // Read compression type in AIFF-C files. uint8 compression[4] = { 'N', 'O', 'N', 'E' }; - bool littleEndian = false; + SampleIO::Endianness endian = SampleIO::bigEndian; if(fileHeader.type == AIFFHeader::idAIFC) { if(!commChunk.ReadArray(compression)) { return false; } - littleEndian = !memcmp(compression, "twos", 4); + if(!memcmp(compression, "twos", 4)) + { + endian = SampleIO::littleEndian; + } } // Read SSND chunk @@ -1373,34 +1375,13 @@ return false; } - SampleIO sampleIO(SampleIO::_8bit, SampleIO::mono, SampleIO::bigEndian, SampleIO::signedPCM); - if(littleEndian) - { - sampleIO |= SampleIO::littleEndian; - } + static const SampleIO::Bitdepth bitDepth[] = { SampleIO::_8bit, SampleIO::_16bit, SampleIO::_24bit, SampleIO::_32bit }; - if(sampleInfo.numChannels == 2) - { - sampleIO |= SampleIO::stereoInterleaved; - } + SampleIO sampleIO(bitDepth[(sampleInfo.sampleSize - 1) / 8], + (sampleInfo.numChannels == 2) ? SampleIO::stereoInterleaved : SampleIO::mono, + endian, + SampleIO::signedPCM); - if(sampleInfo.sampleSize <= 8) - { - sampleIO |= SampleIO::_8bit; - } else if(sampleInfo.sampleSize <= 16) - { - sampleIO |= SampleIO::_16bit; - } else if(sampleInfo.sampleSize <= 24) - { - sampleIO |= SampleIO::_24bit; - } else if(sampleInfo.sampleSize <= 32) - { - sampleIO |= SampleIO::_32bit; - } else - { - return false; - } - if(!memcmp(compression, "fl32", 4) || !memcmp(compression, "FL32", 4)) { sampleIO |= SampleIO::floatPCM; @@ -1437,12 +1418,14 @@ if(instrHeader.sustainLoop.playMode != AIFFInstrumentLoop::noLoop) { - mptSample.uFlags |= CHN_SUSTAINLOOP | (instrHeader.sustainLoop.playMode == AIFFInstrumentLoop::loopBidi ? CHN_PINGPONGSUSTAIN : 0); + mptSample.uFlags.set(CHN_SUSTAINLOOP); + mptSample.uFlags.set(CHN_PINGPONGSUSTAIN, instrHeader.sustainLoop.playMode == AIFFInstrumentLoop::loopBidi); } if(instrHeader.releaseLoop.playMode != AIFFInstrumentLoop::noLoop) { - mptSample.uFlags |= CHN_LOOP | (instrHeader.releaseLoop.playMode == AIFFInstrumentLoop::loopBidi ? CHN_PINGPONGLOOP : 0); + mptSample.uFlags.set(CHN_LOOP); + mptSample.uFlags.set(CHN_PINGPONGLOOP, instrHeader.releaseLoop.playMode == AIFFInstrumentLoop::loopBidi); } // Read markers @@ -1471,12 +1454,12 @@ if(mptSample.nSustainStart >= mptSample.nSustainEnd) { mptSample.nSustainStart = mptSample.nSustainEnd = 0; - mptSample.uFlags &= ~CHN_SUSTAINLOOP; + mptSample.uFlags.reset(CHN_SUSTAINLOOP); } if(mptSample.nLoopStart >= mptSample.nLoopEnd) { mptSample.nLoopStart = mptSample.nLoopEnd = 0; - mptSample.uFlags &= ~CHN_LOOP; + mptSample.uFlags.reset(CHN_LOOP); } } @@ -1734,7 +1717,7 @@ void ReadExtendedInstrumentProperties(ModInstrument* pIns, const LPCBYTE pDataStart, const size_t nMemLength) //----------------------------------------------------------------------------------------------------------- { - if(pIns == 0 || pDataStart == 0 || nMemLength < 4) + if(pIns == nullptr || pDataStart == nullptr || nMemLength < 4) return; LPCBYTE pData = pDataStart; Modified: trunk/OpenMPT/soundlib/Sndfile.cpp =================================================================== --- trunk/OpenMPT/soundlib/Sndfile.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/Sndfile.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -465,7 +465,6 @@ // -! NEW_FEATURE#0023 MemsetZero(ChnMix); - MemsetZero(Samples); MemsetZero(Instruments); MemsetZero(m_szNames); MemsetZero(m_MixPlugins); @@ -522,7 +521,6 @@ m_nMaxOrderPosition = 0; m_lpszSongComments = nullptr; m_nMixLevels = mixLevels_compatible; // Will be overridden if appropriate. - MemsetZero(Samples); MemsetZero(ChnMix); MemsetZero(Instruments); MemsetZero(m_szNames); @@ -1582,7 +1580,7 @@ if (!from || from >= MAX_SAMPLES || !to || to >= MAX_SAMPLES) return false; if (/*!Ins[from].pSample ||*/ Samples[to].pSample) return true; - MemCopy(Samples[to], Samples[from]); + Samples[to] = Samples[from]; Samples[from].pSample = nullptr; Samples[from].nLength = 0; Modified: trunk/OpenMPT/soundlib/WAVTools.cpp =================================================================== --- trunk/OpenMPT/soundlib/WAVTools.cpp 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/WAVTools.cpp 2012-08-05 18:38:07 UTC (rev 1341) @@ -12,6 +12,10 @@ #include "WAVTools.h" +/////////////////////////////////////////////////////////// +// WAV Reading + + WAVReader::WAVReader(FileReader &inputFile) : file(inputFile) //----------------------------------------------------------- { @@ -69,10 +73,10 @@ // Read sample data sampleData = chunks.GetChunk(RIFFChunk::iddata); - if(!sampleData.IsValid() && chunks.ChunkExists(RIFFChunk::idpcm_)) + if(!sampleData.IsValid()) { // The old IMA ADPCM loader code looked for the "pcm " chunk instead of the "data" chunk... - // Dunno why, but we will just look for both. + // Dunno why (Windows XP's audio recorder saves IMA ADPCM files with a "data" chunk), but we will just look for both. sampleData = chunks.GetChunk(RIFFChunk::idpcm_); } @@ -86,19 +90,7 @@ } // Read sample loop points - FileReader smplChunk(chunks.GetChunk(RIFFChunk::idsmpl)); - WAVSampleInfoChunk sampleInfo; - if(smplChunk.ReadConvertEndianness(sampleInfo)) - { - for(size_t i = 0; i < sampleInfo.numLoops; i++) - { - WAVSampleLoop loopData; - if(smplChunk.ReadConvertEndianness(loopData)) - { - sampleLoops.push_back(loopData); - } - } - } + smplChunk = chunks.GetChunk(RIFFChunk::idsmpl); // Read text chunks ChunkReader listChunk = chunks.GetChunk(RIFFChunk::idLIST); @@ -131,27 +123,31 @@ // Read software name const bool isOldMPT = infoChunk.GetChunk(RIFFChunk::idISFT).ReadMagic("Modplug Tracker"); - sample.uFlags &= ~(CHN_LOOP | CHN_PINGPONGLOOP | CHN_SUSTAINLOOP | CHN_PINGPONGSUSTAIN); + sample.uFlags.reset(CHN_LOOP | CHN_PINGPONGLOOP | CHN_SUSTAINLOOP | CHN_PINGPONGSUSTAIN); // Convert loops - if(!sampleLoops.empty()) + WAVSampleInfoChunk sampleInfo; + smplChunk.Rewind(); + if(smplChunk.ReadConvertEndianness(sampleInfo)) { - size_t normalLoopIndex = 0; - if(sampleLoops.size() > 1) + WAVSampleLoop loopData; + if(sampleInfo.numLoops > 1 && smplChunk.ReadConvertEndianness(loopData)) { - sampleLoops[0].ApplyToSample(sample.nSustainStart, sample.nSustainEnd, sample.nLength, sample.uFlags, CHN_SUSTAINLOOP, CHN_PINGPONGSUSTAIN, isOldMPT); - normalLoopIndex = 1; + // First loop: Sustain loop + loopData.ApplyToSample(sample.nSustainStart, sample.nSustainEnd, sample.nLength, sample.uFlags, CHN_SUSTAINLOOP, CHN_PINGPONGSUSTAIN, isOldMPT); } - sampleLoops[normalLoopIndex].ApplyToSample(sample.nLoopStart, sample.nLoopEnd, sample.nLength, sample.uFlags, CHN_LOOP, CHN_PINGPONGLOOP, isOldMPT); + // First loop (if only one loop is present) or second loop (if more than one loop is present): Normal sample loop + if(smplChunk.ReadConvertEndianness(loopData)) + { + loopData.ApplyToSample(sample.nLoopStart, sample.nLoopEnd, sample.nLength, sample.uFlags, CHN_LOOP, CHN_PINGPONGLOOP, isOldMPT); + } } + // Read MPT extra info WAVExtraChunk mptInfo; xtraChunk.Rewind(); if(xtraChunk.ReadConvertEndianness(mptInfo)) { - if(mptInfo.flags & WAVExtraChunk::bidiLoop) sample.uFlags |= CHN_PINGPONGLOOP; - if(mptInfo.flags & WAVExtraChunk::sustainLoop) sample.uFlags |= CHN_SUSTAINLOOP; - if(mptInfo.flags & WAVExtraChunk::sustainBidi) sample.uFlags |= CHN_PINGPONGSUSTAIN; if(mptInfo.flags & WAVExtraChunk::setPanning) sample.uFlags |= CHN_PANNING; sample.nPan = Util::Min(mptInfo.defaultPan, uint16(256)); @@ -172,8 +168,8 @@ } -void WAVSampleLoop::ApplyToSample(SmpLength &start, SmpLength &end, uint32 sampleLength, uint16 &flags, uint16 enableFlag, uint16 bidiFlag, bool mptLoopFix) const -//---------------------------------------------------------------------------------------------------------------------------------------------------------------- +void WAVSampleLoop::ApplyToSample(SmpLength &start, SmpLength &end, uint32 sampleLength, FlagSet<ChannelFlags, uint16> &flags, ChannelFlags enableFlag, ChannelFlags bidiFlag, bool mptLoopFix) const +//--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- { start = Util::Min(static_cast<SmpLength>(loopStart), sampleLength); end = Clamp(static_cast<SmpLength>(loopEnd), start, sampleLength); @@ -183,9 +179,9 @@ end++; } - flags |= enableFlag; + flags.set(enableFlag); if(loopType == loopBidi) { - flags |= bidiFlag; + flags.set(bidiFlag); } } Modified: trunk/OpenMPT/soundlib/WAVTools.h =================================================================== --- trunk/OpenMPT/soundlib/WAVTools.h 2012-08-05 18:32:31 UTC (rev 1340) +++ trunk/OpenMPT/soundlib/WAVTools.h 2012-08-05 18:38:07 UTC (rev 1341) @@ -73,11 +73,18 @@ return SwapBytesLE(l); } - ChunkIdentifiers GetID() const + id_type GetID() const { uint32 i = id; - return static_cast<ChunkIdentifiers>(SwapBytesLE(i)); + return static_cast<id_type>(SwapBytesLE(i)); } + + // Convert all multi-byte numeric values to current platform's endianness or vice versa. + void ConvertEndianness() + { + SwapBytesLE(id); + SwapBytesLE(length); + } }; @@ -120,6 +127,7 @@ uint16 validBitsPerSample; uint32 channelMask; uint16 subFormat; + uint8 guid[14]; // Convert all multi-byte numeric values to current platform's endianness or vice versa. void ConvertEndianness() @@ -138,7 +146,7 @@ uint32 manufacturer; uint32 product; uint32 samplePeriod; // 1000000000 / sampleRate - uint32 baseNote; // 3Ch = C-4 -> 60 + RelativeTone + uint32 baseNote; // MIDI base note of sample uint32 pitchFraction; uint32 SMPTEFormat; uint32 SMPTEOffset; @@ -190,7 +198,25 @@ SwapBytesLE(playCount); } - void ApplyToSample(SmpLength &start, SmpLength &end, uint32 sampleLength, uint16 &flags, uint16 enableFlag, uint16 bidiFlag, bool mptLoopFix) const; + void ApplyToSample(SmpLength &start, SmpLength &end, uint32 sampleLength, FlagSet<ChannelFlags, uint16> &flags, ChannelFlags enableFlag, ChannelFlags bidiFlag, bool mptLoopFix) const; + + // Set up a loop. + void ConvertToWAV(SmpLength start, SmpLength end, bool bidi) + { + identifier = 0; + loopType = bidi ? loopBidi : loopForward; + loopStart = start; + // Loop ends are *inclusive* in the RIFF standard, while they're *exclusive* in OpenMPT. + if(end> start) + { + loopEnd = end - 1; + } else + { + loopEnd = start; + } + fraction = 0; + playCount = 0; + } }; @@ -199,9 +225,6 @@ { enum Flags { - bidiLoop = 0x04, - sustainLoop = 0x08, - sustainBidi = 0x10, setPanning = 0x20, }; @@ -226,20 +249,44 @@ }; +// Sample cue point structure for the "cue " chunk +struct WAVCuePoint +{ + uint32 id; // Unique identification value + uint32 position; // Play order position + uint32 riffChunkID; // RIFF ID of corresponding data chunk + uint32 chunkStart; // Byte Offset of Data Chunk + uint32 blockStart; // Byte Offset to sample of First Channel + uint32 offset; // Byte Offset to sample byte of First Channel + + // Convert all multi-byte numeric values to current platform's endianness or vice versa. + void ConvertEndianness() + { + SwapBytesLE(id); + SwapBytesLE(position); + SwapBytesLE(riffChunkID); + SwapBytesLE(chunkStart); + SwapBytesLE(blockStart); + SwapBytesLE(offset); + } +}; + + #pragma pack(pop) +//============= class WAVReader +//============= { protected: ChunkReader file; - FileReader sampleData, xtraChunk, wsmpChunk; + FileReader sampleData, smplChunk, xtraChunk, wsmpChunk; ChunkReader::ChunkList<RIFFChunk> infoChunk; size_t sampleLength; bool isDLS; WAVFormatChunk formatInfo; - std::vector<WAVSampleLoop> sampleLoops; public: WAVReader(FileReader &inputFile); This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |