diff options
Diffstat (limited to 'src/drumgizmo.cc')
-rw-r--r-- | src/drumgizmo.cc | 56 |
1 files changed, 44 insertions, 12 deletions
diff --git a/src/drumgizmo.cc b/src/drumgizmo.cc index 7ce05ef..fb4f042 100644 --- a/src/drumgizmo.cc +++ b/src/drumgizmo.cc @@ -50,10 +50,12 @@ DrumGizmo::DrumGizmo(AudioOutputEngine *o, AudioInputEngine *i) loader(), oe(o), ie(i) { is_stopping = false; + cacheManager.init(1000, true); // start thread } DrumGizmo::~DrumGizmo() { + cacheManager.deinit(); // stop thread } bool DrumGizmo::loadkit(std::string file) @@ -398,43 +400,73 @@ void DrumGizmo::getSamples(int ch, int pos, sample_t *s, size_t sz) break; } + // Don't handle event now is is scheduled for a future iteration? + if(evt->offset > (pos + sz)) { + continue; + } + + size_t buffer_offset = 0; + + if(evt->cache_id == CACHE_NOID) { + size_t initial_chunksize = (pos + sz) - evt->offset; + evt->buffer = + cacheManager.open(af, initial_chunksize, ch, evt->cache_id); + evt->buffer_size = initial_chunksize; + } + else { + buffer_offset = evt->offset; + } + { MutexAutolock l(af->mutex); - size_t n = 0; + size_t n = 0; // default start point is 0. + + // If we are not at offset 0 in current buffer: if(evt->offset > (size_t)pos) n = evt->offset - pos; - size_t end = sz; + + size_t end = sz; // default end point is the end of the buffer. + + // Find the end point intra-buffer if((evt->t + end - n) > af->size) end = af->size - evt->t + n; + + // This should not be necessary but make absolutely shure that we do + // not write over the end of the buffer. if(end > sz) end = sz; + size_t t = 0; // Internal buffer counter if(evt->rampdown == NO_RAMPDOWN) { #ifdef SSE -// DEBUG(drumgizmo,"%d\n", evt->t); fflush(stdout); - size_t optend = ((end - n) / N) * N + n; - for(; n < optend; n += N) { - *(vNsf*)&(s[n]) += *(vNsf*)&(af->data[evt->t]); - evt->t += N; - } + size_t optend = ((end - n) / N) * N + n; + for(; n < optend; n += N) { + *(vNsf*)&(s[n]) += *(vNsf*)&(evt->buffer[t]); + t += N; + } #endif for(; n < end; n++) { - s[n] += af->data[evt->t]; - evt->t++; + s[n] += evt->buffer[t]; + t++; } } else { // Ramp down in progress. for(; n < end && evt->rampdown; n++) { float scale = (float)evt->rampdown/(float)evt->ramp_start; - s[n] += af->data[evt->t] * scale; - evt->t++; + s[n] += evt->buffer[t] * scale; + t++; evt->rampdown--; } if(evt->rampdown == 0) { removeevent = true; // Down ramp done. Remove event. + cacheManager.close(evt->cache_id); } } + evt->t += t; // Add internal buffer counter to "global" event counter. if(evt->t >= af->size) { removeevent = true; + cacheManager.close(evt->cache_id); + } else { + evt->buffer = cacheManager.next(evt->cache_id, evt->buffer_size); } } |