arduino-audio-tools
All Classes Namespaces Files Functions Variables Typedefs Enumerations Friends Modules Pages
AudioIO.h
1#pragma once
2#include "AudioTools/CoreAudio/AudioOutput.h"
3#include "AudioTools/CoreAudio/AudioStreams.h"
4
5#ifndef MAX_ZERO_READ_COUNT
6# define MAX_ZERO_READ_COUNT 3
7#endif
8
9#ifndef CHANNEL_SELECT_BUFFER_SIZE
10# define CHANNEL_SELECT_BUFFER_SIZE 256
11#endif
12
13
14namespace audio_tools {
22template <class T>
24 public:
29 void begin(T *transform, Stream *source) {
30 TRACED();
31 active = true;
32 p_stream = source;
33 p_transform = transform;
34 if (transform == nullptr) {
35 LOGE("transform is NULL");
36 active = false;
37 }
38 if (p_stream == nullptr) {
39 LOGE("p_stream is NULL");
40 active = false;
41 }
42 }
43
45 void resizeReadBuffer(int size) {
46 buffer.resize(size);
47 }
49 void resizeResultQueue(int size) {
50 result_queue_buffer.resize(size);
51 result_queue.begin();
52 }
53
54
55 size_t readBytes(uint8_t *data, size_t len) {
56 LOGD("TransformationReader::readBytes: %d", (int)len);
57 if (!active) {
58 LOGE("inactive");
59 return 0;
60 }
61 if (p_stream == nullptr) {
62 LOGE("p_stream is NULL");
63 return 0;
64 }
65
66 // we read half the necessary bytes
67 if (buffer.size() == 0) {
68 int size = (0.5f / p_transform->getByteFactor() * len);
69 // process full samples/frames
70 size = size / 4 * 4;
71 LOGI("read size: %d", size);
72 buffer.resize(size);
73 }
74
75 if (result_queue_buffer.size() == 0) {
76 // make sure that the ring buffer is big enough
77 int rb_size = len * result_queue_factor;
78 LOGI("buffer size: %d", rb_size);
79 result_queue_buffer.resize(rb_size);
80 result_queue.begin();
81 }
82
83 if (result_queue.available() < len) {
84 Print *tmp = setupOutput();
85 int zero_count = 0;
86 while (result_queue.available() < len) {
87 int read_eff = p_stream->readBytes(buffer.data(), buffer.size());
88 if (read_eff > 0) {
89 zero_count = 0; // reset 0 count
90 if (read_eff != buffer.size()){
91 LOGD("readBytes %d -> %d", buffer.size(), read_eff);
92 }
93 int write_eff = p_transform->write(buffer.data(), read_eff);
94 if (write_eff != read_eff){
95 LOGE("write %d -> %d", read_eff, write_eff);
96 }
97 } else {
98 // limit the number of reads which provide 0;
99 if (++zero_count > MAX_ZERO_READ_COUNT){
100 break;
101 }
102 // wait for some more data
103 delay(5);
104 }
105 }
106 restoreOutput(tmp);
107 }
108
109 int result_len = min((int)len, result_queue.available());
110 result_len = result_queue.readBytes(data, result_len);
111 LOGD("TransformationReader::readBytes: %d -> %d", (int)len,
112 result_len);
113
114 return result_len;
115 }
116
117 void end() {
118 result_queue_buffer.resize(0);
119 buffer.resize(0);
120 }
121
123 void setResultQueueFactor(int factor) { result_queue_factor = factor; }
124
125 protected:
126 RingBuffer<uint8_t> result_queue_buffer{0};
127 QueueStream<uint8_t> result_queue{result_queue_buffer}; //
128 Stream *p_stream = nullptr;
129 Vector<uint8_t> buffer{0}; // we allocate memory only when needed
130 T *p_transform = nullptr;
131 bool active = false;
132 int result_queue_factor = 5;
133
138 Print *result = p_transform->getPrint();
139 p_transform->setOutput((Print &)result_queue);
140
141 return result;
142 }
145 void restoreOutput(Print *out) {
146 if (out) p_transform->setOutput(*out);
147 }
148};
149
157 public:
158 virtual void setStream(Stream &stream) override {
159 TRACED();
160 p_stream = &stream;
161 p_print = &stream;
162 }
163
164 virtual void setStream(AudioStream &stream) {
165 TRACED();
166 p_stream = &stream;
167 p_print = &stream;
168 //setNotifyOnOutput(stream);
169 addNotifyAudioChange(stream);
170 }
171
172 virtual void setOutput(AudioOutput &print) {
173 TRACED();
174 p_print = &print;
176 }
177
178 virtual void setOutput(Print &print) override {
179 TRACED();
180 p_print = &print;
181 }
182
183 virtual Print *getPrint() { return p_print; }
184
185 virtual Stream *getStream() { return p_stream; }
186
187 size_t readBytes(uint8_t *data, size_t len) override {
188 LOGD("ReformatBaseStream::readBytes: %d", (int)len);
189 return reader.readBytes(data, len);
190 }
191
192 int available() override {
193 return DEFAULT_BUFFER_SIZE; // reader.availableForWrite();
194 }
195
196 int availableForWrite() override {
197 return DEFAULT_BUFFER_SIZE; // reader.availableForWrite();
198 }
199
200 virtual float getByteFactor() = 0;
201
202 void end() override {
203 TRACED();
204 AudioStream::end();
205 reader.end();
206 }
207
209 void resizeReadResultQueue(int size) { reader.resizeResultQueue(size);}
210
213
214
215 protected:
217 Stream *p_stream = nullptr;
218 Print *p_print = nullptr;
219
220 void setupReader() {
221 if (getStream() != nullptr) {
222 reader.begin(this, getStream());
223 }
224 }
225};
226
232
238 public:
239 AdapterPrintToAudioOutput() = default;
240 AdapterPrintToAudioOutput(Print &print) { setStream(print); }
241 void setStream(Print& out) { p_print = &out; }
242 void setAudioInfo(AudioInfo info) { cfg = info;}
243 size_t write(const uint8_t *data, size_t len) {
244 return p_print->write(data, len);
245 }
247 virtual bool isDeletable() { return true; }
248
249 AudioInfo audioInfo() {return cfg; }
250
251 protected:
252 Print *p_print = nullptr;
253 AudioInfo cfg;
254};
255
261 public:
263
264 AdapterAudioStreamToAudioOutput(AudioStream &stream) { setStream(stream); }
265
266 void setStream(AudioStream &stream) { p_stream = &stream; }
267
268 void setAudioInfo(AudioInfo info) override { p_stream->setAudioInfo(info); }
269
270 AudioInfo audioInfo() override { return p_stream->audioInfo(); }
271
272 size_t write(const uint8_t *data, size_t len) override {
273 return p_stream->write(data, len);
274 }
275
276 int availableForWrite() override { return p_stream->availableForWrite(); }
277
278 bool begin() override { return p_stream->begin(); }
279
280 void end() override { p_stream->end(); }
281
283 virtual bool isDeletable() override { return true; }
284
285 operator bool() override { return *p_stream; }
286
287 protected:
288 AudioStream *p_stream = nullptr;
289};
290
296 public:
298
299 AdapterAudioOutputToAudioStream(AudioOutput &stream) { setOutput(stream); }
300
301 void setOutput(AudioOutput &stream) { p_stream = &stream; }
302
303 void setAudioInfo(AudioInfo info) override { p_stream->setAudioInfo(info); }
304
305 AudioInfo audioInfo() override { return p_stream->audioInfo(); }
306
307 size_t write(const uint8_t *data, size_t len) override {
308 return p_stream->write(data, len);
309 }
310
311 bool begin() override { return p_stream->begin(); }
312
313 void end() override { p_stream->end(); }
314
316 virtual bool isDeletable() { return true; }
317
318 operator bool() override { return *p_stream; }
319
320 protected:
321 AudioOutput *p_stream = nullptr;
322};
323
331 public:
333 MultiOutput() = default;
334
335 MultiOutput(Print &out) { add(out); }
336
339
340 MultiOutput(AudioStream &out) { add(out); }
341
344 add(out1);
345 add(out2);
346 }
347
350 add(out1);
351 add(out2);
352 }
353
356 MultiOutput(Print &out1, Print &out2) {
357 add(out1);
358 add(out2);
359 }
360
361 virtual ~MultiOutput() {
362 for (int j = 0; j < vector.size(); j++) {
363 if (vector[j]->isDeletable()) {
364 delete vector[j];
365 }
366 }
367 }
368
370 void add(AudioOutput &out) { vector.push_back(&out); }
371
373 void add(AudioStream &stream) {
376 vector.push_back(out);
377 }
378
379 void add(Print &print) {
381 vector.push_back(out);
382 }
383
384 void flush() {
385 for (int j = 0; j < vector.size(); j++) {
386 vector[j]->flush();
387 }
388 }
389
391 for (int j = 0; j < vector.size(); j++) {
392 vector[j]->setAudioInfo(info);
393 }
394 }
395
396 size_t write(const uint8_t *data, size_t len) {
397 for (int j = 0; j < vector.size(); j++) {
398 int open = len;
399 int start = 0;
400 while (open > 0) {
401 int written = vector[j]->write(data + start, open);
402 open -= written;
403 start += written;
404 }
405 }
406 return len;
407 }
408
409 size_t write(uint8_t ch) {
410 for (int j = 0; j < vector.size(); j++) {
411 int open = 1;
412 while (open > 0) {
413 open -= vector[j]->write(ch);
414 }
415 }
416 return 1;
417 }
418
419 protected:
420 Vector<AudioOutput *> vector;
422 void setOutput(Print &out) { add(out); }
423};
424
435 public:
436 TimedStream() = default;
437
438 TimedStream(AudioStream &io, long startSeconds = 0, long endSeconds = -1) {
439 p_stream = &io;
440 p_print = &io;
441 p_info = &io;
442 setStartSec(startSeconds);
443 setEndSec(endSeconds);
444 }
445
446 TimedStream(AudioOutput &o, long startSeconds = 0, long endSeconds = -1) {
447 p_print = &o;
448 p_info = &o;
449 setStartSec(startSeconds);
450 setEndSec(endSeconds);
451 }
452
455 void setStartSec(uint32_t startSeconds) {
456 start_ms = startSeconds * 1000;
457 calculateByteLimits();
458 }
459
461 void setStartMs(uint32_t ms) {
462 start_ms = ms;
463 calculateByteLimits();
464 }
465
468 void setEndSec(uint32_t endSeconds) {
469 end_ms = endSeconds * 1000;
470 calculateByteLimits();
471 }
472
474 void setEndMs(uint32_t ms) {
475 end_ms = ms;
476 calculateByteLimits();
477 }
478
480 bool isPlaying() {
481 if (current_bytes < start_bytes) return false;
482 if (end_bytes > 0 && current_bytes > end_bytes) return false;
483 return true;
484 }
485
487 bool isActive() {
488 return (current_bytes < end_bytes && current_bytes >= start_bytes);
489 }
490
491 bool begin(AudioInfo info) {
492 setAudioInfo(info);
493 return begin();
494 }
495
496 bool begin() override {
497 calculateByteLimits();
498 current_bytes = 0;
499 LOGI("byte range %u - %u",(unsigned) start_bytes,(unsigned) end_bytes);
500 return true;
501 }
502
503 operator bool() override { return isActive(); }
504
508 size_t readBytes(uint8_t *data, size_t len) override {
509 // if reading is not supported we stop
510 if (p_stream == nullptr) return 0;
511 // Positioin to start
512 if (start_bytes > current_bytes){
513 consumeBytes(start_bytes - current_bytes);
514 }
515 // if we are past the end we stop
516 if (!isActive()) return 0;
517 // read the data now
518 size_t result = 0;
519 do {
520 result = p_stream->readBytes(data, len);
521 current_bytes += len;
522 // ignore data before start time
523 } while (result > 0 && current_bytes < start_bytes);
524 return isPlaying() ? result : 0;
525 }
526
528 size_t write(const uint8_t *data, size_t len) override {
529 if (current_bytes >= end_bytes) return 0;
530 current_bytes += len;
531 if (current_bytes < start_bytes) return len;
532 return p_print->write(data, len);
533 }
534
536 int available() override {
537 if (p_stream == nullptr) return 0;
538 return current_bytes < end_bytes ? p_stream->available() : 0;
539 }
540
542 void setAudioInfo(AudioInfo info) override {
544 if (p_info) p_info->setAudioInfo(info);
545 calculateByteLimits();
546 }
547
548 int availableForWrite() override {
549 return current_bytes < end_bytes ? p_print->availableForWrite() : 0;
550 }
551
554 void setCompressionRatio(float ratio) { compression_ratio = ratio; }
555
558 return info.sample_rate * info.channels * info.bits_per_sample / 8;
559 }
560
561 void setOutput(Print &out) override { p_print = &out; }
562
563 void setStream(Stream &stream) override {
564 p_print = &stream;
565 p_stream = &stream;
566 }
567
568 void setOutput(AudioOutput &out) {
569 p_print = &out;
570 p_info = &out;
571 }
572
573 void setStream(AudioOutput &out) {
574 p_print = &out;
575 p_info = &out;
576 }
577
578 void setStream(AudioStream &stream) {
579 p_print = &stream;
580 p_stream = &stream;
581 p_info = &stream;
582 }
583
584 size_t size() {
585 return end_bytes - start_bytes;
586 }
587
588 protected:
589 Stream *p_stream = nullptr;
590 Print *p_print = nullptr;
591 AudioInfoSupport *p_info = nullptr;
592 uint32_t start_ms = 0;
593 uint32_t end_ms = UINT32_MAX;
594 uint32_t start_bytes = 0;
595 uint32_t end_bytes = UINT32_MAX;
596 uint32_t current_bytes = 0;
597 float compression_ratio = 1.0;
598
599 void consumeBytes(uint32_t len){
600 int open = len;
601 uint8_t buffer[1024];
602 while (open > 0){
603 int toread = min(1024, open);
604 p_stream->readBytes(buffer, toread);
605 open -= toread;
606 }
607 current_bytes += len;
608 LOGD("consumed %u -> %u",(unsigned) len, (unsigned)current_bytes);
609 }
610
611 void calculateByteLimits() {
612 float bytes_per_second = bytesPerSecond();
613 if (bytes_per_second > 0) {
614 start_bytes = bytes_per_second * start_ms / compression_ratio / 1000;
615 end_bytes = bytes_per_second * end_ms / compression_ratio / 1000;
616 } else {
617 LOGE("AudioInfo not defined");
618 }
619 }
620};
621
632 public:
633 ChannelsSelectOutput() = default;
634
635 bool begin(AudioInfo info) override {
636 setAudioInfo(info);
637 return begin();
638 }
639
640 bool begin() override {
641 AudioOutput::begin();
642 // make sure that selected channels are valid
643 for (auto &out : out_channels) {
644 for (auto &ch : out.channels) {
645 if (ch > cfg.channels - 1) {
646 LOGE("Channel '%d' not valid for max %d channels", ch, cfg.channels);
647 return false;
648 }
649 }
650 }
651 return true;
652 }
653
656 void addOutput(AudioOutput &out, uint16_t channel) {
657 Vector<uint16_t> channels;
658 channels.push_back(channel);
660 def.channels = channels;
661 def.p_out = &out;
662 def.p_audio_info = &out;
663 out_channels.push_back(def);
664 }
665
668 void addOutput(AudioStream &out, uint16_t channel) {
669 Vector<uint16_t> channels;
670 channels.push_back(channel);
672 def.channels = channels;
673 def.p_out = &out;
674 def.p_audio_info = &out;
675 out_channels.push_back(def);
676 }
677
680 void addOutput(Print &out, uint16_t channel) {
681 Vector<uint16_t> channels;
682 channels.push_back(channel);
684 def.channels = channels;
685 def.p_out = &out;
686 out_channels.push_back(def);
687 }
688
691 void addOutput(Print &out, uint16_t left, uint16_t right) {
692 Vector<uint16_t> channels;
693 channels.push_back(left);
694 channels.push_back(right);
696 def.channels = channels;
697 def.p_out = &out;
698 out_channels.push_back(def);
699 }
700
703 void addOutput(AudioOutput &out, uint16_t left, uint16_t right) {
704 Vector<uint16_t> channels;
705 channels.push_back(left);
706 channels.push_back(right);
708 def.channels = channels;
709 def.p_out = &out;
710 def.p_audio_info = &out;
711 out_channels.push_back(def);
712 }
713
716 void addOutput(AudioStream &out, uint16_t left, uint16_t right) {
717 Vector<uint16_t> channels;
718 channels.push_back(left);
719 channels.push_back(right);
721 def.channels = channels;
722 def.p_out = &out;
723 def.p_audio_info = &out;
724 out_channels.push_back(def);
725 }
726
727 size_t write(const uint8_t *data, size_t len) override {
728 if (!is_active) return false;
729 LOGD("write %d", (int)len);
730 switch (cfg.bits_per_sample) {
731 case 16:
732 return writeT<int16_t>(data, len);
733 case 24:
734 return writeT<int24_t>(data, len);
735 case 32:
736 return writeT<int32_t>(data, len);
737 default:
738 return 0;
739 }
740 }
741
742 void setAudioInfo(AudioInfo ai) override {
743 this->cfg = ai;
744 //notifyAudioChange(ai);
745 for (auto &info : out_channels) {
746 auto p_notify = info.p_audio_info;
747 if (p_notify != nullptr) {
748 AudioInfo result{ai};
749 result.channels = info.channels.size();
750 p_notify->setAudioInfo(result);
751 }
752 }
753 }
754
755 protected:
757 Print *p_out = nullptr;
758 AudioInfoSupport *p_audio_info = nullptr;
759 SingleBuffer<uint8_t> buffer{CHANNEL_SELECT_BUFFER_SIZE};
760 Vector<uint16_t> channels{0};
761 };
762 Vector<ChannelSelectionOutputDef> out_channels{0};
763
764 template <typename T>
765 size_t writeT(const uint8_t *buffer, size_t size) {
766 if (!is_active) return 0;
767 int sample_count = size / sizeof(T);
768 //int result_size = sample_count / cfg.channels;
769 T *data = (T *)buffer;
770
771 for (int i = 0; i < sample_count; i += cfg.channels) {
772 T *frame = data + i;
773 for (auto &out : out_channels) {
774 T out_frame[out.channels.size()];
775 int ch_out = 0;
776 for (auto &ch : out.channels) {
777 // make sure we have a valid channel
778 int channel = (ch < cfg.channels) ? ch : cfg.channels - 1;
779 out_frame[ch_out++] = frame[channel];
780 }
781 // write to buffer
782 size_t written = out.buffer.writeArray((const uint8_t *)&out_frame, sizeof(out_frame));
783 // write buffer to final output
784 if (out.buffer.availableForWrite()<sizeof(out_frame)){
785 out.p_out->write(out.buffer.data(), out.buffer.available());
786 out.buffer.reset();
787 }
788 // if (written != sizeof(out_frame)) {
789 // LOGW("Could not write all samples %d -> %d", sizeof(out_frame), written);
790 // }
791 }
792 }
793 return size;
794 }
795
797 int getChannels(Print *out, int defaultChannels) {
798 for (auto &channels_select : out_channels) {
799 if (channels_select.p_out == out) return channels_select.channels.size();
800 }
801 return defaultChannels;
802 }
803};
804
805} // namespace audio_tools
Wrapper which converts a AudioStream to a AudioOutput.
Definition AudioIO.h:295
virtual bool isDeletable()
If true we need to release the related memory in the destructor.
Definition AudioIO.h:316
void setAudioInfo(AudioInfo info) override
Defines the input AudioInfo.
Definition AudioIO.h:303
AudioInfo audioInfo() override
provides the actual input AudioInfo
Definition AudioIO.h:305
Wrapper which converts a AudioStream to a AudioOutput.
Definition AudioIO.h:260
virtual bool isDeletable() override
If true we need to release the related memory in the destructor.
Definition AudioIO.h:283
void setAudioInfo(AudioInfo info) override
Defines the input AudioInfo.
Definition AudioIO.h:268
AudioInfo audioInfo() override
provides the actual input AudioInfo
Definition AudioIO.h:270
Wrapper which converts a Print to a AudioOutput.
Definition AudioIO.h:237
virtual bool isDeletable()
If true we need to release the related memory in the destructor.
Definition AudioIO.h:247
void setAudioInfo(AudioInfo info)
Defines the input AudioInfo.
Definition AudioIO.h:242
AudioInfo audioInfo()
provides the actual input AudioInfo
Definition AudioIO.h:249
virtual void addNotifyAudioChange(AudioInfoSupport &bi)
Adds target to be notified about audio changes.
Definition AudioTypes.h:151
Supports changes to the sampling rate, bits and channels.
Definition AudioTypes.h:133
virtual void setAudioInfo(AudioInfo info)=0
Defines the input AudioInfo.
Base class for Output Adpapters.
Definition AudioIO.h:231
Abstract Audio Ouptut class.
Definition AudioOutput.h:22
virtual bool isDeletable()
If true we need to release the related memory in the destructor.
Definition AudioOutput.h:57
Base class for all Audio Streams. It support the boolean operator to test if the object is ready with...
Definition BaseStream.h:119
virtual void setAudioInfo(AudioInfo newInfo) override
Defines the input AudioInfo.
Definition BaseStream.h:127
Flexible functionality to extract one or more channels from a multichannel signal....
Definition AudioIO.h:631
void addOutput(Print &out, uint16_t left, uint16_t right)
Definition AudioIO.h:691
void setAudioInfo(AudioInfo ai) override
Defines the input AudioInfo.
Definition AudioIO.h:742
void addOutput(Print &out, uint16_t channel)
Definition AudioIO.h:680
void addOutput(AudioOutput &out, uint16_t channel)
Definition AudioIO.h:656
int getChannels(Print *out, int defaultChannels)
Determine number of channels for destination.
Definition AudioIO.h:797
void addOutput(AudioStream &out, uint16_t channel)
Definition AudioIO.h:668
void addOutput(AudioStream &out, uint16_t left, uint16_t right)
Definition AudioIO.h:716
void addOutput(AudioOutput &out, uint16_t left, uint16_t right)
Definition AudioIO.h:703
Abstract class: Objects can be put into a pipleline.
Definition AudioOutput.h:97
Abstract class: Objects can be put into a pipleline.
Definition AudioStreams.h:68
Replicates the output to multiple destinations.
Definition AudioIO.h:330
void add(AudioOutput &out)
Add an additional AudioOutput output.
Definition AudioIO.h:370
void setAudioInfo(AudioInfo info)
Defines the input AudioInfo.
Definition AudioIO.h:390
void add(AudioStream &stream)
Add an AudioStream to the output.
Definition AudioIO.h:373
MultiOutput(AudioStream &out1, AudioStream &out2)
Defines a MultiOutput with 2 final outputs.
Definition AudioIO.h:349
MultiOutput(AudioOutput &out1, AudioOutput &out2)
Defines a MultiOutput with 2 final outputs.
Definition AudioIO.h:343
MultiOutput(AudioOutput &out)
Defines a MultiOutput with a single final outputs,.
Definition AudioIO.h:338
void setOutput(Print &out)
support for Pipleline
Definition AudioIO.h:422
MultiOutput(Print &out1, Print &out2)
Definition AudioIO.h:356
MultiOutput()=default
Defines a MultiOutput with no final output: Define your outputs with add()
Definition NoArduino.h:62
virtual bool begin() override
Activates the output.
Definition BaseStream.h:330
Base class for chained converting streams.
Definition AudioIO.h:156
virtual void setStream(Stream &stream) override
Defines/Changes the input & output.
Definition AudioIO.h:158
virtual void setOutput(Print &print) override
Defines/Changes the output target.
Definition AudioIO.h:178
virtual TransformationReader< ReformatBaseStream > & transformationReader()
Provides access to the TransformationReader.
Definition AudioIO.h:212
void resizeReadResultQueue(int size)
Define the size of the interal read result queue: same as transformationReader().resizeResultQueue(si...
Definition AudioIO.h:209
Implements a typed Ringbuffer.
Definition Buffers.h:308
virtual size_t size() override
Returns the maximum capacity of the buffer.
Definition Buffers.h:394
A simple Buffer implementation which just uses a (dynamically sized) array.
Definition Buffers.h:175
Definition NoArduino.h:142
AudioStream class that can define a start and (an optional) stop time Usually it is used to wrap an A...
Definition AudioIO.h:434
void setOutput(Print &out) override
Defines/Changes the output target.
Definition AudioIO.h:561
void setStream(Stream &stream) override
Defines/Changes the input & output.
Definition AudioIO.h:563
void setEndSec(uint32_t endSeconds)
Definition AudioIO.h:468
void setEndMs(uint32_t ms)
Defines the (optional) end time in milliseconds.
Definition AudioIO.h:474
void setCompressionRatio(float ratio)
Definition AudioIO.h:554
size_t readBytes(uint8_t *data, size_t len) override
Definition AudioIO.h:508
void setStartSec(uint32_t startSeconds)
Definition AudioIO.h:455
int available() override
Provides the available bytes until the end time has reached.
Definition AudioIO.h:536
size_t write(const uint8_t *data, size_t len) override
Plays only data for the indiated start and end time.
Definition AudioIO.h:528
void setStartMs(uint32_t ms)
Defines the start time in milliseconds.
Definition AudioIO.h:461
bool isPlaying()
Returns true if we are in a valid time range and are still playing sound.
Definition AudioIO.h:480
bool isActive()
Returns true if we are not past the end time;.
Definition AudioIO.h:487
void setAudioInfo(AudioInfo info) override
Updates the AudioInfo in the current object and in the source or target.
Definition AudioIO.h:542
int bytesPerSecond()
Calculates the bytes per second from the AudioInfo.
Definition AudioIO.h:557
ConverterStream Helper class which implements the readBytes with the help of write.
Definition AudioIO.h:23
void begin(T *transform, Stream *source)
setup of the TransformationReader class
Definition AudioIO.h:29
void resizeReadBuffer(int size)
Defines the read buffer size for individual reads.
Definition AudioIO.h:45
void restoreOutput(Print *out)
restores the original output in the converter class
Definition AudioIO.h:145
Print * setupOutput()
Definition AudioIO.h:137
void resizeResultQueue(int size)
Defines the queue size for result.
Definition AudioIO.h:49
void setResultQueueFactor(int factor)
Defines the queue size dependent on the read size.
Definition AudioIO.h:123
Vector implementation which provides the most important methods as defined by std::vector....
Definition Vector.h:21
Generic Implementation of sound input and output for desktop environments using portaudio.
Definition AudioCodecsBase.h:10
Basic Audio information which drives e.g. I2S.
Definition AudioTypes.h:53
sample_rate_t sample_rate
Sample Rate: e.g 44100.
Definition AudioTypes.h:55
uint16_t channels
Number of channels: 2=stereo, 1=mono.
Definition AudioTypes.h:57
uint8_t bits_per_sample
Number of bits per sample (int16_t = 16 bits)
Definition AudioTypes.h:59