Blender V2.61 - r43446

AUD_LoopReader.cpp

Go to the documentation of this file.
00001 /*
00002  * ***** BEGIN GPL LICENSE BLOCK *****
00003  *
00004  * Copyright 2009-2011 Jörg Hermann Müller
00005  *
00006  * This file is part of AudaSpace.
00007  *
00008  * Audaspace is free software; you can redistribute it and/or modify
00009  * it under the terms of the GNU General Public License as published by
00010  * the Free Software Foundation; either version 2 of the License, or
00011  * (at your option) any later version.
00012  *
00013  * AudaSpace is distributed in the hope that it will be useful,
00014  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00015  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00016  * GNU General Public License for more details.
00017  *
00018  * You should have received a copy of the GNU General Public License
00019  * along with Audaspace; if not, write to the Free Software Foundation,
00020  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00021  *
00022  * ***** END GPL LICENSE BLOCK *****
00023  */
00024 
00030 #include "AUD_LoopReader.h"
00031 #include "AUD_Buffer.h"
00032 
00033 #include <cstring>
00034 
00035 AUD_LoopReader::AUD_LoopReader(AUD_Reference<AUD_IReader> reader, int loop) :
00036         AUD_EffectReader(reader), m_count(loop), m_left(loop)
00037 {
00038 }
00039 
00040 void AUD_LoopReader::seek(int position)
00041 {
00042     int len = m_reader->getLength();
00043     if(len < 0)
00044         m_reader->seek(position);
00045     else
00046     {
00047         if(m_count >= 0)
00048         {
00049             m_left = m_count - (position / len);
00050             if(m_left < 0)
00051                 m_left = 0;
00052         }
00053         m_reader->seek(position % len);
00054     }
00055 }
00056 
00057 int AUD_LoopReader::getLength() const
00058 {
00059     if(m_count < 0)
00060         return -1;
00061     return m_reader->getLength() * m_count;
00062 }
00063 
00064 int AUD_LoopReader::getPosition() const
00065 {
00066     return m_reader->getPosition() * (m_count < 0 ? 1 : m_count);
00067 }
00068 
00069 void AUD_LoopReader::read(int& length, bool& eos, sample_t* buffer)
00070 {
00071     const AUD_Specs specs = m_reader->getSpecs();
00072 
00073     int len = length;
00074 
00075     m_reader->read(length, eos, buffer);
00076 
00077     if(length < len && eos && m_left)
00078     {
00079         int pos = length;
00080         length = len;
00081 
00082         while(pos < length && eos && m_left)
00083         {
00084             if(m_left > 0)
00085                 m_left--;
00086 
00087             m_reader->seek(0);
00088 
00089             len = length - pos;
00090             m_reader->read(len, eos, buffer + pos * specs.channels);
00091 
00092             // prevent endless loop
00093             if(!len)
00094                 break;
00095 
00096             pos += len;
00097         }
00098 
00099         length = pos;
00100     }
00101 }