3#include "AudioToolsConfig.h"
4#include "AudioTools/CoreAudio/AudioBasic/Debouncer.h"
5#include "AudioTools/CoreAudio/AudioHttp/AudioHttp.h"
6#include "AudioTools/CoreAudio/AudioLogger.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/AudioMetaData/MetaData.h"
14#include "AudioTools/CoreAudio/VolumeStream.h"
15#include "AudioTools/Disk/AudioSource.h"
16#include "AudioTools/AudioCodecs/AudioCodecs.h"
55 this->p_source = &source;
56 this->p_decoder = &decoder;
75 this->p_source = &source;
76 this->p_decoder = &decoder;
92 this->p_source = &source;
93 this->p_decoder = &decoder;
108 out_decoding.setDecoder(p_decoder);
111 out_decoding.setDecoder(p_decoder);
113 this->p_final_print = &output;
114 this->p_final_stream =
nullptr;
117 void setOutput(Print &output) {
122 out_decoding.setDecoder(p_decoder);
125 out_decoding.setDecoder(p_decoder);
127 this->p_final_print =
nullptr;
128 this->p_final_stream =
nullptr;
131 void setOutput(AudioStream &output) {
136 out_decoding.setDecoder(p_decoder);
139 out_decoding.setDecoder(p_decoder);
141 this->p_final_print =
nullptr;
142 this->p_final_stream = &output;
153 if (current_volume == -1.0f) {
166 out_decoding.
begin();
173 if (p_input_stream !=
nullptr) {
177 copier.
begin(out_decoding, *p_input_stream);
182 LOGW(
"-> begin: no data found");
187 LOGW(
"-> begin: no stream selected");
200 if (p_decoder !=
nullptr) {
215 this->p_decoder = &decoder;
216 out_decoding.setDecoder(p_decoder);
221 this->p_final_notify = notify;
223 if (p_decoder !=
nullptr) {
233 LOGI(
"channels: %d", (
int) info.
channels);
239 if (p_final_print !=
nullptr)
241 if (p_final_stream !=
nullptr)
243 if (p_final_notify !=
nullptr)
266 stream_increment = offset >= 0 ? 1 : -1;
275 stream_increment = 1;
284 stream_increment = 1;
293 stream_increment = -1;
301 out_decoding.
begin();
302 p_input_stream = input;
303 if (p_input_stream !=
nullptr) {
304 LOGD(
"open selected stream");
306 copier.
begin(out_decoding, *p_input_stream);
308 return p_input_stream !=
nullptr;
324 fade.setFadeInActive(
true);
326 fade.setFadeOutActive(
true);
338 if (abs(
volume - current_volume) > 0.01f) {
339 LOGI(
"setVolume(%f)",
volume);
344 LOGE(
"setVolume value '%f' out of range (0.0 -1.0)",
volume);
351 float volume()
override {
return current_volume; }
371 if (delay_if_full != 0 && ((p_final_print !=
nullptr &&
372 p_final_print->availableForWrite() == 0) ||
373 (p_final_stream !=
nullptr &&
374 p_final_stream->availableForWrite() == 0))) {
376 delay(delay_if_full);
381 if (result > 0 || timeout == 0) {
386 moveToNextFileOnTimeout();
389 if (result < bytes && silence_on_inactive){
395 if (silence_on_inactive) {
404 const char *str,
int len),
408 if (p_source->setMetadataCallback(callback)) {
410 LOGI(
"Using ICY Metadata");
414 meta_out.setCallback(callback);
415 meta_out.setFilter(sel);
439 if (p_final_print !=
nullptr) {
441 }
else if (p_final_stream !=
nullptr) {
456 bool isAutoFade() {
return is_auto_fade; }
466 bool autonext =
true;
467 bool silence_on_inactive =
false;
474 AudioDecoder *p_decoder = &no_decoder;
475 Stream *p_input_stream =
nullptr;
476 AudioOutput *p_final_print =
nullptr;
477 AudioStream *p_final_stream =
nullptr;
478 AudioInfoSupport *p_final_notify =
nullptr;
481 bool meta_active =
false;
482 uint32_t timeout = 0;
483 int stream_increment = 1;
484 float current_volume = -1.0f;
485 int delay_if_full = 100;
486 bool is_auto_fade =
true;
489 if (p_final_print !=
nullptr) {
491 }
else if (p_final_stream !=
nullptr) {
496 void moveToNextFileOnTimeout() {
499 if (p_final_stream !=
nullptr && p_final_stream->availableForWrite() == 0)
501 if (p_input_stream ==
nullptr ||
millis() > timeout) {
503 fade.setFadeInActive(
true);
505 LOGI(
"-> timeout - moving by %d", stream_increment);
507 if (!
next(stream_increment)) {
508 LOGD(
"stream is null");
521 fade.setFadeOutActive(
true);
524 fade.setFadeInActive(
true);
533 LOGD(
"%s, %zu", LOG_METHOD, len);
535 if (p->meta_active) {
536 p->meta_out.
write((
const uint8_t *)data, len);