Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #ifndef AUDIO_AUDIOSTREAM_H
00024 #define AUDIO_AUDIOSTREAM_H
00025
00026 #include "common/ptr.h"
00027 #include "common/scummsys.h"
00028 #include "common/str.h"
00029 #include "common/types.h"
00030
00031 #include "audio/timestamp.h"
00032
00033 namespace Common {
00034 class SeekableReadStream;
00035 }
00036
00037 namespace Audio {
00038
00043 class AudioStream {
00044 public:
00045 virtual ~AudioStream() {}
00046
00060 virtual int readBuffer(int16 *buffer, const int numSamples) = 0;
00061
00063 virtual bool isStereo() const = 0;
00064
00066 virtual int getRate() const = 0;
00067
00075 virtual bool endOfData() const = 0;
00076
00085 virtual bool endOfStream() const { return endOfData(); }
00086 };
00087
00093 class RewindableAudioStream : public virtual AudioStream {
00094 public:
00100 virtual bool rewind() = 0;
00101 };
00102
00107 class LoopingAudioStream : public AudioStream {
00108 public:
00121 LoopingAudioStream(RewindableAudioStream *stream, uint loops, DisposeAfterUse::Flag disposeAfterUse = DisposeAfterUse::YES);
00122
00123 int readBuffer(int16 *buffer, const int numSamples);
00124 bool endOfData() const;
00125 bool endOfStream() const;
00126
00127 bool isStereo() const { return _parent->isStereo(); }
00128 int getRate() const { return _parent->getRate(); }
00129
00133 uint getCompleteIterations() const { return _completeIterations; }
00134 private:
00135 Common::DisposablePtr<RewindableAudioStream> _parent;
00136
00137 uint _loops;
00138 uint _completeIterations;
00139 };
00140
00153 AudioStream *makeLoopingAudioStream(RewindableAudioStream *stream, uint loops);
00154
00160 class SeekableAudioStream : public virtual RewindableAudioStream {
00161 public:
00171 static SeekableAudioStream *openStreamFile(const Common::String &basename);
00172
00179 bool seek(uint32 where) {
00180 return seek(Timestamp(where, getRate()));
00181 }
00182
00189 virtual bool seek(const Timestamp &where) = 0;
00190
00196 virtual Timestamp getLength() const = 0;
00197
00198 virtual bool rewind() { return seek(0); }
00199 };
00200
00218 AudioStream *makeLoopingAudioStream(SeekableAudioStream *stream, Timestamp start, Timestamp end, uint loops);
00219
00232 class SubLoopingAudioStream : public AudioStream {
00233 public:
00247 SubLoopingAudioStream(SeekableAudioStream *stream, uint loops,
00248 const Timestamp loopStart,
00249 const Timestamp loopEnd,
00250 DisposeAfterUse::Flag disposeAfterUse = DisposeAfterUse::YES);
00251
00252 int readBuffer(int16 *buffer, const int numSamples);
00253 bool endOfData() const;
00254 bool endOfStream() const;
00255
00256 bool isStereo() const { return _parent->isStereo(); }
00257 int getRate() const { return _parent->getRate(); }
00258 private:
00259 Common::DisposablePtr<SeekableAudioStream> _parent;
00260
00261 uint _loops;
00262 Timestamp _pos;
00263 Timestamp _loopStart, _loopEnd;
00264
00265 bool _done;
00266 };
00267
00268
00276 class SubSeekableAudioStream : public SeekableAudioStream {
00277 public:
00286 SubSeekableAudioStream(SeekableAudioStream *parent, const Timestamp start, const Timestamp end, DisposeAfterUse::Flag disposeAfterUse = DisposeAfterUse::YES);
00287
00288 int readBuffer(int16 *buffer, const int numSamples);
00289
00290 bool isStereo() const { return _parent->isStereo(); }
00291
00292 int getRate() const { return _parent->getRate(); }
00293
00294 bool endOfData() const { return (_pos >= _length) || _parent->endOfData(); }
00295 bool endOfStream() const { return (_pos >= _length) || _parent->endOfStream(); }
00296
00297 bool seek(const Timestamp &where);
00298
00299 Timestamp getLength() const { return _length; }
00300 private:
00301 Common::DisposablePtr<SeekableAudioStream> _parent;
00302
00303 const Timestamp _start;
00304 const Timestamp _length;
00305 Timestamp _pos;
00306 };
00307
00308 class QueuingAudioStream : public Audio::AudioStream {
00309 public:
00310
00317 virtual void queueAudioStream(Audio::AudioStream *audStream,
00318 DisposeAfterUse::Flag disposeAfterUse = DisposeAfterUse::YES) = 0;
00319
00333 void queueBuffer(byte *data, uint32 size, DisposeAfterUse::Flag disposeAfterUse, byte flags);
00334
00340 virtual void finish() = 0;
00341
00346 virtual uint32 numQueuedStreams() const = 0;
00347 };
00348
00352 QueuingAudioStream *makeQueuingAudioStream(int rate, bool stereo);
00353
00362 Timestamp convertTimeToStreamPos(const Timestamp &where, int rate, bool isStereo);
00363
00372 AudioStream *makeLimitingAudioStream(AudioStream *parentStream, const Timestamp &length, DisposeAfterUse::Flag disposeAfterUse = DisposeAfterUse::YES);
00373
00381 class PacketizedAudioStream : public virtual AudioStream {
00382 public:
00383 virtual ~PacketizedAudioStream() {}
00384
00388 virtual void queuePacket(Common::SeekableReadStream *data) = 0;
00389
00395 virtual void finish() = 0;
00396 };
00397
00405 class StatelessPacketizedAudioStream : public PacketizedAudioStream {
00406 public:
00407 StatelessPacketizedAudioStream(uint rate, uint channels) :
00408 _rate(rate), _channels(channels), _stream(makeQueuingAudioStream(rate, channels == 2)) {}
00409 virtual ~StatelessPacketizedAudioStream() {}
00410
00411
00412 bool isStereo() const { return _channels == 2; }
00413 int getRate() const { return _rate; }
00414 int readBuffer(int16 *data, const int numSamples) { return _stream->readBuffer(data, numSamples); }
00415 bool endOfData() const { return _stream->endOfData(); }
00416 bool endOfStream() const { return _stream->endOfStream(); }
00417
00418
00419 void queuePacket(Common::SeekableReadStream *data) { _stream->queueAudioStream(makeStream(data)); }
00420 void finish() { _stream->finish(); }
00421
00422 uint getChannels() const { return _channels; }
00423
00424 protected:
00428 virtual AudioStream *makeStream(Common::SeekableReadStream *data) = 0;
00429
00430 private:
00431 uint _rate;
00432 uint _channels;
00433 Common::ScopedPtr<QueuingAudioStream> _stream;
00434 };
00435
00440 AudioStream *makeNullAudioStream();
00441
00442 }
00443
00444 #endif