arduino-audio-tools
Loading...
Searching...
No Matches
AudioPlayer.h
1#pragma once
2
3#include "AudioTools/AudioCodecs/AudioCodecs.h"
4#include "AudioTools/CoreAudio/AudioBasic/Debouncer.h"
5#include "AudioTools/CoreAudio/AudioLogger.h"
6#include "AudioTools/CoreAudio/AudioMetaData/MetaData.h"
7#include "AudioTools/CoreAudio/AudioStreams.h"
8#include "AudioTools/CoreAudio/AudioTypes.h"
9#include "AudioTools/CoreAudio/BaseConverter.h"
10#include "AudioTools/CoreAudio/Buffers.h"
11#include "AudioTools/CoreAudio/Fade.h"
12#include "AudioTools/CoreAudio/StreamCopy.h"
13#include "AudioTools/CoreAudio/VolumeStream.h"
14#include "AudioTools/Disk/AudioSource.h"
15#include "AudioToolsConfig.h"
16
23namespace audio_tools {
24
52 public:
54 AudioPlayer() { TRACED(); }
55
65 AudioPlayer(AudioSource &source, AudioOutput &output, AudioDecoder &decoder) {
66 TRACED();
67 this->p_source = &source;
68 this->p_decoder = &decoder;
69 setOutput(output);
70 // notification for audio configuration
71 decoder.addNotifyAudioChange(*this);
72 }
73
84 AudioPlayer(AudioSource &source, Print &output, AudioDecoder &decoder,
85 AudioInfoSupport *notify = nullptr) {
86 TRACED();
87 this->p_source = &source;
88 this->p_decoder = &decoder;
89 setOutput(output);
91 }
92
102 AudioPlayer(AudioSource &source, AudioStream &output, AudioDecoder &decoder) {
103 TRACED();
104 this->p_source = &source;
105 this->p_decoder = &decoder;
106 setOutput(output);
107 // notification for audio configuration
108 decoder.addNotifyAudioChange(*this);
109 }
110
112 AudioPlayer(AudioPlayer const &) = delete;
113
116
118 void setOutput(AudioOutput &output) {
119 if (p_decoder->isResultPCM()) {
120 this->fade.setOutput(output);
121 this->volume_out.setOutput(fade);
122 out_decoding.setOutput(&volume_out);
123 out_decoding.setDecoder(p_decoder);
124 } else {
125 out_decoding.setOutput(&output);
126 out_decoding.setDecoder(p_decoder);
127 }
128 this->p_final_print = &output;
129 this->p_final_stream = nullptr;
130 }
131
133 void setOutput(Print &output) {
134 if (p_decoder->isResultPCM()) {
135 this->fade.setOutput(output);
136 this->volume_out.setOutput(fade);
137 out_decoding.setOutput(&volume_out);
138 out_decoding.setDecoder(p_decoder);
139 } else {
140 out_decoding.setOutput(&output);
141 out_decoding.setDecoder(p_decoder);
142 }
143 this->p_final_print = nullptr;
144 this->p_final_stream = nullptr;
145 }
146
148 void setOutput(AudioStream &output) {
149 if (p_decoder->isResultPCM()) {
150 this->fade.setOutput(output);
151 this->volume_out.setOutput(fade);
152 out_decoding.setOutput(&volume_out);
153 out_decoding.setDecoder(p_decoder);
154 } else {
155 out_decoding.setOutput(&output);
156 out_decoding.setDecoder(p_decoder);
157 }
158 this->p_final_print = nullptr;
159 this->p_final_stream = &output;
160 }
161
163 void setBufferSize(int size) { copier.resize(size); }
164
166 bool begin(int index = 0, bool isActive = true) {
167 TRACED();
168 bool result = false;
169 // initilaize volume
170 if (current_volume == -1.0f) {
171 setVolume(1.0f);
172 } else {
173 setVolume(current_volume);
174 }
175
176 // take definition from source
177 autonext = p_source->isAutoNext();
178
179 // initial audio info for fade from output when not defined yet
180 setupFade();
181
182 // start dependent objects
183 out_decoding.begin();
184
185 if (!p_source->begin()){
186 LOGE("Could not start audio source");
187 return false;
188 }
189 if (!meta_out.begin()){
190 LOGE("Could not start metadata output");
191 return false;
192 }
193 if (!volume_out.begin()){
194 LOGE("Could not start volume control");
195 return false;
196 }
197
198 if (index >= 0) {
199 setStream(p_source->selectStream(index));
200 if (p_input_stream != nullptr) {
201 if (meta_active) {
203 }
204 copier.begin(out_decoding, *p_input_stream);
205 timeout = millis() + p_source->timeoutAutoNext();
206 active = isActive;
207 result = true;
208 } else {
209 LOGW("-> begin: no data found");
210 active = false;
211 result = false;
212 }
213 } else {
214 LOGW("-> begin: no stream selected");
215 active = isActive;
216 result = false;
217 }
218 return result;
219 }
220
222 void end() {
223 TRACED();
224 active = false;
225 out_decoding.end();
226 meta_out.end();
227 // remove any data in the decoder
228 if (p_decoder != nullptr) {
229 LOGI("reset codec");
230 p_decoder->end();
231 p_decoder->begin();
232 }
233 }
234
236 AudioSource &audioSource() { return *p_source; }
237
239 void setAudioSource(AudioSource &source) { this->p_source = &source; }
240
242 void setDecoder(AudioDecoder &decoder) {
243 this->p_decoder = &decoder;
244 out_decoding.setDecoder(p_decoder);
245 }
246
249 this->p_final_notify = notify;
250 // notification for audio configuration
251 if (p_decoder != nullptr) {
252 p_decoder->addNotifyAudioChange(*this);
253 }
254 }
255
257 void setAudioInfo(AudioInfo info) override {
258 TRACED();
259 LOGI("sample_rate: %d", (int)info.sample_rate);
260 LOGI("bits_per_sample: %d", (int)info.bits_per_sample);
261 LOGI("channels: %d", (int)info.channels);
262 this->info = info;
263 // notifiy volume
264 volume_out.setAudioInfo(info);
265 fade.setAudioInfo(info);
266 // notifiy final ouput: e.g. i2s
267 if (p_final_print != nullptr) p_final_print->setAudioInfo(info);
268 if (p_final_stream != nullptr) p_final_stream->setAudioInfo(info);
269 if (p_final_notify != nullptr) p_final_notify->setAudioInfo(info);
270 };
271
273 AudioInfo audioInfo() override { return info; }
274
277 void play() {
278 TRACED();
279 setActive(true);
280 }
281
285 bool playPath(const char *path) {
286 TRACED();
287 if (!setPath(path)) {
288 LOGW("Could not open file: %s", path);
289 return false;
290 }
291
292 LOGI("Playing %s", path);
293 // start if inactive
294 play();
295 // process all data
296 copyAll();
297
298 LOGI("%s has finished playing", path);
299 return true;
300 }
301
303 bool playFile(const char *path) { return playPath(path); }
304
305
307 void stop() {
308 TRACED();
309 setActive(false);
310 }
311
313 bool next(int offset = 1) {
314 TRACED();
315 writeEnd();
316 stream_increment = offset >= 0 ? 1 : -1;
317 active = setStream(p_source->nextStream(offset));
318 return active;
319 }
320
322 bool setIndex(int idx) {
323 TRACED();
324 writeEnd();
325 stream_increment = 1;
326 active = setStream(p_source->selectStream(idx));
327 return active;
328 }
329
331 bool setPath(const char *path) {
332 TRACED();
333 writeEnd();
334 stream_increment = 1;
335 active = setStream(p_source->selectStream(path));
336 return active;
337 }
338
340 bool previous(int offset = 1) {
341 TRACED();
342 writeEnd();
343 stream_increment = -1;
344 active = setStream(p_source->previousStream(abs(offset)));
345 return active;
346 }
347
349 bool setStream(Stream *input) {
350 end();
351 out_decoding.begin();
352 p_input_stream = input;
353 if (p_input_stream != nullptr) {
354 LOGD("open selected stream");
355 meta_out.begin();
356 copier.begin(out_decoding, *p_input_stream);
357 }
358 // execute callback if defined
359 if (on_stream_change_callback != nullptr)
360 on_stream_change_callback(p_input_stream, p_reference);
361 return p_input_stream != nullptr;
362 }
363
365 Stream *getStream() { return p_input_stream; }
366
368 bool isActive() { return active; }
369
371 operator bool() { return isActive(); }
372
374 void setActive(bool isActive) {
375 if (is_auto_fade) {
376 if (isActive) {
377 fade.setFadeInActive(true);
378 } else {
379 fade.setFadeOutActive(true);
380 copier.copy();
381 writeSilence(2048);
382 }
383 }
384 active = isActive;
385 }
386
388 bool setVolume(float volume) override {
389 bool result = true;
390 if (volume >= 0.0f && volume <= 1.0f) {
391 if (abs(volume - current_volume) > 0.01f) {
392 LOGI("setVolume(%f)", volume);
393 volume_out.setVolume(volume);
394 current_volume = volume;
395 }
396 } else {
397 LOGE("setVolume value '%f' out of range (0.0 -1.0)", volume);
398 result = false;
399 }
400 return result;
401 }
402
404 float volume() override { return current_volume; }
405
407 void setAutoNext(bool next) { autonext = next; }
408
410 void setDelayIfOutputFull(int delayMs) { delay_if_full = delayMs; }
411
414 size_t copy() { return copy(copier.bufferSize()); }
415
417 size_t copyAll() {
418 size_t result = 0;
419 size_t step = copy();
420 while (step > 0) {
421 result += step;
422 step = copy();
423 }
424 return result;
425 }
426
428 size_t copy(size_t bytes) {
429 size_t result = 0;
430 if (active) {
431 if (delay_if_full != 0 && ((p_final_print != nullptr &&
432 p_final_print->availableForWrite() == 0) ||
433 (p_final_stream != nullptr &&
434 p_final_stream->availableForWrite() == 0))) {
435 // not ready to do anything - so we wait a bit
436 delay(delay_if_full);
437 LOGD("copy: %d -> 0", (int)bytes);
438 return 0;
439 }
440 // handle sound
441 result = copier.copyBytes(bytes);
442 if (result > 0 || timeout == 0) {
443 // reset timeout if we had any data
444 timeout = millis() + p_source->timeoutAutoNext();
445 }
446 // move to next stream after timeout
447 moveToNextFileOnTimeout();
448
449 // return silence when there was no data
450 if (result < bytes && silence_on_inactive) {
451 writeSilence(bytes - result);
452 }
453
454 } else {
455 // e.g. A2DP should still receive data to keep the connection open
456 if (silence_on_inactive) {
457 writeSilence(bytes);
458 }
459 }
460 LOGD("copy: %d -> %d", (int)bytes, (int)result);
461 return result;
462 }
463
465 void setVolumeControl(VolumeControl &vc) { volume_out.setVolumeControl(vc); }
466
469 StreamCopy &getStreamCopy() { return copier; }
470
472 void setSilenceOnInactive(bool active) { silence_on_inactive = active; }
473
475 bool isSilenceOnInactive() { return silence_on_inactive; }
476
478 void writeSilence(size_t bytes) {
479 TRACEI();
480 if (p_final_print != nullptr) {
481 p_final_print->writeSilence(bytes);
482 } else if (p_final_stream != nullptr) {
483 p_final_stream->writeSilence(bytes);
484 }
485 }
486
488 VolumeStream &getVolumeStream() { return volume_out; }
489
491 void setAutoFade(bool active) { is_auto_fade = active; }
492
494 bool isAutoFade() { return is_auto_fade; }
495
497 void setMetaDataSize(int size) { meta_out.resize(size); }
498
500 void setReference(void *ref) { p_reference = ref; }
501
503 void setMetadataCallback(void (*callback)(MetaDataType type, const char *str,
504 int len),
505 ID3TypeSelection sel = SELECT_ID3) {
506 TRACEI();
507 // setup metadata.
508 if (p_source->setMetadataCallback(callback)) {
509 // metadata is handled by source
510 LOGI("Using ICY Metadata");
511 meta_active = false;
512 } else {
513 // metadata is handled here
514 meta_out.setCallback(callback);
515 meta_out.setFilter(sel);
516 meta_active = true;
517 }
518 }
519
521 void setOnStreamChangeCallback(void (*callback)(Stream *stream_ptr,
522 void *reference)) {
523 on_stream_change_callback = callback;
524 if (p_input_stream!=nullptr) callback(p_input_stream, p_reference);
525 }
526
527 protected:
528 bool active = false;
529 bool autonext = true;
530 bool silence_on_inactive = false;
531 AudioSource *p_source = nullptr;
532 VolumeStream volume_out; // Volume control
533 FadeStream fade; // Phase in / Phase Out to avoid popping noise
534 MetaDataID3 meta_out; // Metadata parser
535 EncodedAudioOutput out_decoding; // Decoding stream
536 CopyDecoder no_decoder{true};
537 AudioDecoder *p_decoder = &no_decoder;
538 Stream *p_input_stream = nullptr;
539 AudioOutput *p_final_print = nullptr;
540 AudioStream *p_final_stream = nullptr;
541 AudioInfoSupport *p_final_notify = nullptr;
542 StreamCopy copier; // copies sound into i2s
543 AudioInfo info;
544 bool meta_active = false;
545 uint32_t timeout = 0;
546 int stream_increment = 1; // +1 moves forward; -1 moves backward
547 float current_volume = -1.0f; // illegal value which will trigger an update
548 int delay_if_full = 100;
549 bool is_auto_fade = true;
550 void *p_reference = nullptr;
551 void (*on_stream_change_callback)(Stream *stream_ptr,
552 void *reference) = nullptr;
553
554 void setupFade() {
555 if (p_final_print != nullptr) {
556 fade.setAudioInfo(p_final_print->audioInfo());
557 } else if (p_final_stream != nullptr) {
558 fade.setAudioInfo(p_final_stream->audioInfo());
559 }
560 }
561
562 void moveToNextFileOnTimeout() {
563 if (p_final_stream != nullptr && p_final_stream->availableForWrite() == 0)
564 return;
565 if (p_input_stream == nullptr || millis() > timeout) {
566 if (is_auto_fade) fade.setFadeInActive(true);
567 if (autonext) {
568 LOGI("-> timeout - moving by %d", stream_increment);
569 // open next stream
570 if (!next(stream_increment)) {
571 LOGD("stream is null");
572 }
573 } else {
574 active = false;
575 }
576 timeout = millis() + p_source->timeoutAutoNext();
577 }
578 }
579
580 void writeEnd() {
581 // end silently
582 TRACEI();
583 if (is_auto_fade) {
584 fade.setFadeOutActive(true);
585 copier.copy();
586 // start by fading in
587 fade.setFadeInActive(true);
588 }
589 // restart the decoder to make sure it does not contain any audio when we
590 // continue
591 p_decoder->begin();
592 }
593
595 static void decodeMetaData(void *obj, void *data, size_t len) {
596 LOGD("%s, %zu", LOG_METHOD, len);
597 AudioPlayer *p = (AudioPlayer *)obj;
598 if (p->meta_active) {
599 p->meta_out.write((const uint8_t *)data, len);
600 }
601 }
602};
603
604} // namespace audio_tools
Decoding of encoded audio into PCM data.
Definition AudioCodecsBase.h:18
virtual bool isResultPCM()
Returns true to indicate that the decoding result is PCM data.
Definition AudioCodecsBase.h:53
virtual void addNotifyAudioChange(AudioInfoSupport &bi)
Adds target to be notified about audio changes.
Definition AudioTypes.h:153
Supports changes to the sampling rate, bits and channels.
Definition AudioTypes.h:135
virtual void setAudioInfo(AudioInfo info)=0
Defines the input AudioInfo.
Abstract Audio Ouptut class.
Definition AudioOutput.h:25
virtual void setAudioInfo(AudioInfo newInfo) override
Defines the input AudioInfo.
Definition AudioOutput.h:49
virtual void writeSilence(size_t len)
Definition AudioOutput.h:66
High-level audio playback pipeline and controller.
Definition AudioPlayer.h:51
static void decodeMetaData(void *obj, void *data, size_t len)
Callback implementation which writes to metadata.
Definition AudioPlayer.h:595
void setOutput(Print &output)
Sets the final output to a Print (adds Volume/Fade for PCM)
Definition AudioPlayer.h:133
void setAudioSource(AudioSource &source)
Sets or replaces the AudioSource.
Definition AudioPlayer.h:239
void writeSilence(size_t bytes)
Writes the requested number of zero bytes to the output.
Definition AudioPlayer.h:478
AudioPlayer(AudioSource &source, AudioStream &output, AudioDecoder &decoder)
Construct a new Audio Player object. The processing chain is AudioSource -> Stream-copy -> EncodedAud...
Definition AudioPlayer.h:102
AudioSource & audioSource()
Returns the active AudioSource.
Definition AudioPlayer.h:236
size_t copy(size_t bytes)
Copies the requested bytes from source to decoder (call in loop)
Definition AudioPlayer.h:428
size_t copyAll()
Copies until source is exhausted (blocking)
Definition AudioPlayer.h:417
void setSilenceOnInactive(bool active)
When enabled, writes zeros while inactive to keep sinks alive.
Definition AudioPlayer.h:472
bool isSilenceOnInactive()
Returns whether silence-on-inactive is enabled.
Definition AudioPlayer.h:475
void setOnStreamChangeCallback(void(*callback)(Stream *stream_ptr, void *reference))
Defines a callback that is called when the stream is changed.
Definition AudioPlayer.h:521
void setDelayIfOutputFull(int delayMs)
Sets delay (ms) to wait when output is full.
Definition AudioPlayer.h:410
void setMetaDataSize(int size)
Sets the maximum ID3 metadata buffer size (default 256)
Definition AudioPlayer.h:497
bool setStream(Stream *input)
Activates the provided Stream as current input.
Definition AudioPlayer.h:349
void setDecoder(AudioDecoder &decoder)
Sets or replaces the AudioDecoder.
Definition AudioPlayer.h:242
StreamCopy & getStreamCopy()
Definition AudioPlayer.h:469
bool isAutoFade()
Checks whether automatic fade in/out is enabled.
Definition AudioPlayer.h:494
bool playFile(const char *path)
Obsolete: use PlayPath!
Definition AudioPlayer.h:303
bool setVolume(float volume) override
Sets volume in range [0.0, 1.0]; updates VolumeStream.
Definition AudioPlayer.h:388
Stream * getStream()
Returns the currently active input Stream (e.g., file)
Definition AudioPlayer.h:365
void play()
Definition AudioPlayer.h:277
bool next(int offset=1)
Moves to the next/previous stream by offset (negative supported)
Definition AudioPlayer.h:313
float volume() override
Returns the current volume [0.0, 1.0].
Definition AudioPlayer.h:404
bool playPath(const char *path)
Definition AudioPlayer.h:285
void addNotifyAudioChange(AudioInfoSupport *notify)
Adds/updates a listener notified on audio info changes.
Definition AudioPlayer.h:248
void stop()
Halts playback; equivalent to setActive(false)
Definition AudioPlayer.h:307
void setAutoNext(bool next)
Enables/disables auto-advance at end/timeout (overrides AudioSource)
Definition AudioPlayer.h:407
void setReference(void *ref)
Sets a user reference passed to the stream-change callback.
Definition AudioPlayer.h:500
AudioPlayer()
Default constructor.
Definition AudioPlayer.h:54
void setAutoFade(bool active)
Enables/disables automatic fade in/out to prevent pops.
Definition AudioPlayer.h:491
void setMetadataCallback(void(*callback)(MetaDataType type, const char *str, int len), ID3TypeSelection sel=SELECT_ID3)
Defines the metadata callback.
Definition AudioPlayer.h:503
void setOutput(AudioOutput &output)
Sets the final output to an AudioOutput (adds Volume/Fade for PCM)
Definition AudioPlayer.h:118
bool isActive()
Checks whether playback is active.
Definition AudioPlayer.h:368
bool previous(int offset=1)
Moves back by offset streams (defaults to 1)
Definition AudioPlayer.h:340
void end()
Ends playback and resets decoder/intermediate stages.
Definition AudioPlayer.h:222
VolumeStream & getVolumeStream()
Returns the VolumeStream used by the player.
Definition AudioPlayer.h:488
bool setPath(const char *path)
Selects stream by path without changing the source iterator.
Definition AudioPlayer.h:331
bool begin(int index=0, bool isActive=true)
Starts or restarts playback from the first or given stream index.
Definition AudioPlayer.h:166
void setAudioInfo(AudioInfo info) override
Receives and forwards updated AudioInfo to the chain.
Definition AudioPlayer.h:257
void setActive(bool isActive)
Toggles playback activity; triggers fade and optional silence.
Definition AudioPlayer.h:374
void setBufferSize(int size)
Sets the internal copy buffer size (bytes)
Definition AudioPlayer.h:163
AudioPlayer & operator=(AudioPlayer const &)=delete
Non-assignable: assignment operator is deleted.
void setOutput(AudioStream &output)
Sets the final output to an AudioStream (adds Volume/Fade for PCM)
Definition AudioPlayer.h:148
size_t copy()
Definition AudioPlayer.h:414
AudioInfo audioInfo() override
Returns the current AudioInfo of the playback chain.
Definition AudioPlayer.h:273
bool setIndex(int idx)
Selects stream by absolute index in the source.
Definition AudioPlayer.h:322
AudioPlayer(AudioSource &source, AudioOutput &output, AudioDecoder &decoder)
Construct a new Audio Player object. The processing chain is AudioSource -> Stream-copy -> EncodedAud...
Definition AudioPlayer.h:65
void setVolumeControl(VolumeControl &vc)
Sets a custom VolumeControl implementation.
Definition AudioPlayer.h:465
AudioPlayer(AudioSource &source, Print &output, AudioDecoder &decoder, AudioInfoSupport *notify=nullptr)
Construct a new Audio Player object. The processing chain is AudioSource -> Stream-copy -> EncodedAud...
Definition AudioPlayer.h:84
AudioPlayer(AudioPlayer const &)=delete
Non-copyable: copy constructor is deleted.
Abstract Audio Data Source for the AudioPlayer which is used by the Audio Players.
Definition AudioSource.h:16
virtual Stream * selectStream(int index)
Definition AudioSource.h:29
virtual Stream * previousStream(int offset)
Returns previous audio stream.
Definition AudioSource.h:25
virtual bool isAutoNext()
Returns default setting go to the next.
Definition AudioSource.h:63
virtual Stream * nextStream(int offset)=0
Returns next audio stream.
virtual int timeoutAutoNext()
Provides the timeout which is triggering to move to the next stream.
Definition AudioSource.h:50
virtual bool begin()=0
Reset actual stream and move to root.
Base class for all Audio Streams. It support the boolean operator to test if the object is ready with...
Definition BaseStream.h:122
virtual void setAudioInfo(AudioInfo newInfo) override
Defines the input AudioInfo.
Definition BaseStream.h:130
virtual void writeSilence(size_t len)
Writes len bytes of silence (=0).
Definition BaseStream.h:159
Dummy Decoder which just copies the provided data to the output. You can define if it is PCM data.
Definition CodecCopy.h:18
A more natural Print class to process encoded data (aac, wav, mp3...). Just define the output and the...
Definition AudioEncoded.h:21
void end() override
Ends the processing.
Definition AudioEncoded.h:183
bool begin() override
Starts the processing - sets the status to active.
Definition AudioEncoded.h:155
void setOutput(Print *outputStream)
Defines the output.
Definition AudioEncoded.h:104
Stream which can be used to manage fade in and fade out. Before you read or write data you need to ca...
Definition Fade.h:240
void setOutput(Print &out) override
Defines/Changes the output target.
Definition Fade.h:251
void setAudioInfo(AudioInfo info) override
Defines the input AudioInfo.
Definition Fade.h:267
Simple ID3 Meta Data Parser which supports ID3 V1 and V2 and implements the Stream interface....
Definition MetaDataID3.h:569
virtual size_t write(const uint8_t *data, size_t len)
Provide tha audio data to the API to parse for Meta Data.
Definition MetaDataID3.h:601
void resize(int size)
Defines the ID3V3 result buffer size (default is 256);.
Definition MetaDataID3.h:611
Definition NoArduino.h:62
size_t copyBytes(size_t bytes)
Definition StreamCopy.h:114
void resize(int len)
resizes the copy buffer
Definition StreamCopy.h:309
void setCallbackOnWrite(void(*onWrite)(void *obj, void *buffer, size_t len), void *obj)
Defines a callback that is notified with the wirtten data.
Definition StreamCopy.h:275
void begin()
(Re)starts the processing
Definition StreamCopy.h:56
int bufferSize()
Provides the buffer size.
Definition StreamCopy.h:291
size_t copy()
Definition StreamCopy.h:100
Definition NoArduino.h:142
Abstract class for handling of the linear input volume to determine the multiplication factor which s...
Definition VolumeControl.h:19
Adjust the volume of the related input or output: To work properly the class needs to know the bits p...
Definition VolumeStream.h:34
void setOutput(Print &out) override
Defines/Changes the output target.
Definition VolumeStream.h:70
bool setVolume(float vol) override
Defines the volume for all channels: needs to be in the range of 0 to 1.0 (if allow boost has not bee...
Definition VolumeStream.h:181
void setAudioInfo(AudioInfo cfg) override
Detines the Audio info - The bits_per_sample are critical to work properly!
Definition VolumeStream.h:165
void setVolumeControl(VolumeControl &vc)
Defines the volume control logic.
Definition VolumeStream.h:122
Supports the setting and getting of the volume.
Definition AudioTypes.h:191
ID3TypeSelection
Enum to filter by type of metadata.
Definition AbstractMetaData.h:8
MetaDataType
Type of meta info.
Definition AbstractMetaData.h:11
StreamCopyT< uint8_t > StreamCopy
We provide the typeless StreamCopy.
Definition StreamCopy.h:425
Generic Implementation of sound input and output for desktop environments using portaudio.
Definition AudioCodecsBase.h:10
uint32_t millis()
Returns the milliseconds since the start.
Definition Time.h:12
Basic Audio information which drives e.g. I2S.
Definition AudioTypes.h:55
sample_rate_t sample_rate
Sample Rate: e.g 44100.
Definition AudioTypes.h:57
uint16_t channels
Number of channels: 2=stereo, 1=mono.
Definition AudioTypes.h:59
uint8_t bits_per_sample
Number of bits per sample (int16_t = 16 bits)
Definition AudioTypes.h:61