Mercurial > hg > svgui
diff layer/SpectrogramLayer.cpp @ 33:651e4e868bcc
* Implement play mute, level and pan controls and a layer visibility control
* Handle swapping the buffers in AudioCallbackPlaySource more gracefully, so
that in many cases it can be done inaudibly. Still gets it wrong when
playing in a noncontiguous selection.
* Fix to SV file save for non-2d sparse models
* Fixes to LED button drawing and AudioDial mouse functionality
* Add progress bar for Ogg file import
* Reshuffle PropertyContainer and its subclasses so it can be a QObject
* Add layer dormancy (invisible layer permitted to free its cache space)
* Optimisations to SpectrogramLayer, removing locks when reading/writing
individual pixels in the cache (should be unnecessary there) -- there's
still an issue here as we need a lock when reading from the model in
case the model is replaced, and we don't currently have one
* Several munlock() calls to make it harder to exhaust real memory if
running in an RT mode with mlockall() active
author | Chris Cannam |
---|---|
date | Fri, 17 Feb 2006 18:04:26 +0000 |
parents | fc802f7b112e |
children | c43f2c4f66f2 |
line wrap: on
line diff
--- a/layer/SpectrogramLayer.cpp Wed Feb 15 17:58:35 2006 +0000 +++ b/layer/SpectrogramLayer.cpp Fri Feb 17 18:04:26 2006 +0000 @@ -49,7 +49,6 @@ m_fillThread(0), m_updateTimer(0), m_lastFillExtent(0), - m_dormant(false), m_exiting(false) { if (config == MelodicRange) { @@ -597,16 +596,29 @@ } void -SpectrogramLayer::setLayerDormant() +SpectrogramLayer::setLayerDormant(bool dormant) { - m_mutex.lock(); - m_dormant = true; - delete m_cache; - m_cache = 0; - m_pixmapCacheInvalid = true; - delete m_pixmapCache; - m_pixmapCache = 0; - m_mutex.unlock(); + if (dormant == m_dormant) return; + + if (dormant) { + + m_mutex.lock(); + m_dormant = true; + + delete m_cache; + m_cache = 0; + + m_pixmapCacheInvalid = true; + delete m_pixmapCache; + m_pixmapCache = 0; + + m_mutex.unlock(); + + } else { + + m_dormant = false; + fillCache(); + } } void @@ -983,8 +995,17 @@ m_layer.m_cache = new Cache(width, height); m_layer.setCacheColourmap(); + m_layer.m_cache->fill(0); - m_layer.m_cache->fill(0); + // We don't need a lock when writing to or reading from + // the pixels in the cache, because it's a fixed size + // array. We do need to ensure we have the width and + // height of the cache and the FFT parameters fixed before + // we unlock, in case they change in the model while we + // aren't holding a lock. It's safe for us to continue to + // use the "old" values if that happens, because they will + // continue to match the dimensions of the actual cache + // (which we manage, not the model). m_layer.m_mutex.unlock(); double *input = (double *) @@ -1002,7 +1023,6 @@ std::cerr << "WARNING: fftw_plan_dft_r2c_1d(" << windowSize << ") failed!" << std::endl; fftw_free(input); fftw_free(output); - m_layer.m_mutex.lock(); continue; } @@ -1014,8 +1034,6 @@ if (doVisibleFirst) { - m_layer.m_mutex.lock(); - for (size_t f = visibleStart; f < visibleEnd; f += windowIncrement) { m_layer.fillCacheColumn(int((f - start) / windowIncrement), @@ -1023,9 +1041,6 @@ windowSize, windowIncrement, windower, false); - m_layer.m_mutex.unlock(); - m_layer.m_mutex.lock(); - if (m_layer.m_cacheInvalid || m_layer.m_exiting) { interrupted = true; m_fillExtent = 0; @@ -1039,8 +1054,6 @@ counter = 0; } } - - m_layer.m_mutex.unlock(); } m_layer.m_cachedInitialVisibleArea = true; @@ -1290,9 +1303,7 @@ } if (m_dormant) { - std::cerr << "SpectrogramLayer::paint(): Layer is dormant, de-hibernating" << std::endl; - m_dormant = false; - ((SpectrogramLayer *)this)->fillCache(); + std::cerr << "SpectrogramLayer::paint(): Layer is dormant" << std::endl; return; }