diff --git a/include/MixHelpers.h b/include/MixHelpers.h index baf841af4..6b5516747 100644 --- a/include/MixHelpers.h +++ b/include/MixHelpers.h @@ -46,6 +46,8 @@ void addMultipliedByBuffer( sampleFrame* dst, const sampleFrame* src, float coef /*! \brief Add samples from src multiplied by coeffSrc and coeffSrcBuf to dst */ void addMultipliedByBuffers( sampleFrame* dst, const sampleFrame* src, ValueBuffer * coeffSrcBuf1, ValueBuffer * coeffSrcBuf2, int frames ); +/*! \brief Same as addMultiplied, but sanitize output (strip out infs/nans) */ +void addSanitizedMultiplied( sampleFrame* dst, const sampleFrame* src, float coeffSrc, int frames ); /*! \brief Add samples from src multiplied by coeffSrcLeft/coeffSrcRight to dst */ void addMultipliedStereo( sampleFrame* dst, const sampleFrame* src, float coeffSrcLeft, float coeffSrcRight, int frames ); diff --git a/include/ProjectJournal.h b/include/ProjectJournal.h index 011755e45..2de42c724 100644 --- a/include/ProjectJournal.h +++ b/include/ProjectJournal.h @@ -22,8 +22,8 @@ * */ -#ifndef _PROJECT_JOURNAL_H -#define _PROJECT_JOURNAL_H +#ifndef PROJECT_JOURNAL_H +#define PROJECT_JOURNAL_H #include #include @@ -37,6 +37,8 @@ class JournallingObject; class ProjectJournal { public: + static const int MAX_UNDO_STATES; + ProjectJournal(); virtual ~ProjectJournal(); @@ -88,7 +90,7 @@ private: struct CheckPoint { - CheckPoint( jo_id_t initID = 0, const DataFile&initData = DataFile( DataFile::JournalData ) ) : + CheckPoint( jo_id_t initID = 0, const DataFile& initData = DataFile( DataFile::JournalData ) ) : joID( initID ), data( initData ) { diff --git a/plugins/vestige/vestige.cpp b/plugins/vestige/vestige.cpp index 8f41b36c9..5723aafde 100644 --- a/plugins/vestige/vestige.cpp +++ b/plugins/vestige/vestige.cpp @@ -170,9 +170,10 @@ void vestigeInstrument::saveSettings( QDomDocument & _doc, QDomElement & _this ) { if( QFileInfo( m_pluginDLL ).isAbsolute() ) { - QString relativePath; - if( !( relativePath = m_pluginDLL.section( configManager:: - inst()->vstDir(), 1, 1 ) ).isEmpty() ) + QString f = QString( m_pluginDLL ).replace( QDir::separator(), '/' ); + QString vd = QString( configManager::inst()->vstDir() ).replace( QDir::separator(), '/' ); + QString relativePath; + if( !( relativePath = f.section( vd, 1, 1 ) ).isEmpty() ) { m_pluginDLL = relativePath; } diff --git a/src/core/FxMixer.cpp b/src/core/FxMixer.cpp index 2d4ac52f3..eaf34e221 100644 --- a/src/core/FxMixer.cpp +++ b/src/core/FxMixer.cpp @@ -536,7 +536,7 @@ void FxMixer::masterMix( sampleFrame * _buf ) const float v = volBuf ? 1.0f : m_fxChannels[0]->m_volumeModel.value(); - MixHelpers::addMultiplied( _buf, m_fxChannels[0]->m_buffer, v, fpp ); + MixHelpers::addSanitizedMultiplied( _buf, m_fxChannels[0]->m_buffer, v, fpp ); m_fxChannels[0]->m_peakLeft *= engine::mixer()->masterGain(); m_fxChannels[0]->m_peakRight *= engine::mixer()->masterGain(); diff --git a/src/core/MixHelpers.cpp b/src/core/MixHelpers.cpp index 9f5c2fb71..bc91e316f 100644 --- a/src/core/MixHelpers.cpp +++ b/src/core/MixHelpers.cpp @@ -22,8 +22,7 @@ * */ -#include - +#include "lmms_math.h" #include "MixHelpers.h" #include "ValueBuffer.h" @@ -126,6 +125,26 @@ void addMultipliedByBuffers( sampleFrame* dst, const sampleFrame* src, ValueBuff } +struct AddSanitizedMultipliedOp +{ + AddSanitizedMultipliedOp( float coeff ) : m_coeff( coeff ) { } + + void operator()( sampleFrame& dst, const sampleFrame& src ) const + { + dst[0] += ( isinff( src[0] ) || isnanf( src[0] ) ) ? 0.0f : src[0] * m_coeff; + dst[1] += ( isinff( src[1] ) || isnanf( src[1] ) ) ? 0.0f : src[1] * m_coeff; + } + + const float m_coeff; +}; + +void addSanitizedMultiplied( sampleFrame* dst, const sampleFrame* src, float coeffSrc, int frames ) +{ + run<>( dst, src, frames, AddSanitizedMultipliedOp(coeffSrc) ); +} + + + struct AddMultipliedStereoOp { AddMultipliedStereoOp( float coeffLeft, float coeffRight ) diff --git a/src/core/ProjectJournal.cpp b/src/core/ProjectJournal.cpp index 2c5c0d912..08ae8d6e7 100644 --- a/src/core/ProjectJournal.cpp +++ b/src/core/ProjectJournal.cpp @@ -29,6 +29,7 @@ #include "JournallingObject.h" #include "song.h" +const int ProjectJournal::MAX_UNDO_STATES = 100; // TODO: make this configurable in settings ProjectJournal::ProjectJournal() : m_joIDs(), @@ -109,6 +110,10 @@ void ProjectJournal::addJournalCheckPoint( JournallingObject *jo ) jo->saveState( dataFile, dataFile.content() ); m_undoCheckPoints.push( CheckPoint( jo->id(), dataFile ) ); + if( m_undoCheckPoints.size() > MAX_UNDO_STATES ) + { + m_undoCheckPoints.remove( 0, m_undoCheckPoints.size() - MAX_UNDO_STATES ); + } } } @@ -120,7 +125,7 @@ jo_id_t ProjectJournal::allocID( JournallingObject * _obj ) const jo_id_t EO_ID_MAX = (1 << 23)-1; jo_id_t id; while( m_joIDs.contains( id = - static_cast( (jo_id_t)rand()*(jo_id_t)rand() % + static_cast( (jo_id_t)rand()*(jo_id_t)rand() % EO_ID_MAX ) ) ) { }