/* * Copyright 2023 jacqueline * * SPDX-License-Identifier: GPL-3.0-only */ #include "audio/fatfs_stream_factory.hpp" #include #include #include #include "esp_log.h" #include "ff.h" #include "freertos/portmacro.h" #include "freertos/projdefs.h" #include "audio/audio_source.hpp" #include "audio/fatfs_source.hpp" #include "codec.hpp" #include "database/database.hpp" #include "database/tag_parser.hpp" #include "database/track.hpp" #include "drivers/spi.hpp" #include "tasks.hpp" #include "types.hpp" [[maybe_unused]] static const char* kTag = "SRC"; namespace audio { FatfsStreamFactory::FatfsStreamFactory(database::Handle&& handle, database::ITagParser& parser) : db_(handle), tag_parser_(parser) {} auto FatfsStreamFactory::create(database::TrackId id, uint32_t offset) -> std::shared_ptr { auto db = db_.lock(); if (!db) { return {}; } auto path = db->getTrackPath(id); if (!path) { return {}; } return create(*path, offset); } auto FatfsStreamFactory::create(std::string path, uint32_t offset) -> std::shared_ptr { auto tags = tag_parser_.ReadAndParseTags(path); if (!tags) { return {}; } if (!tags->title()) { tags->title(path); } auto stream_type = ContainerToStreamType(tags->encoding()); if (!stream_type.has_value()) { ESP_LOGE(kTag, "couldn't match container to stream"); return {}; } std::unique_ptr file = std::make_unique(); FRESULT res = f_open(file.get(), path.c_str(), FA_READ); if (res != FR_OK) { ESP_LOGE(kTag, "failed to open file! res: %i", res); return {}; } return std::make_shared( tags, std::make_unique(stream_type.value(), std::move(file)), path, offset); } auto FatfsStreamFactory::ContainerToStreamType(database::Container enc) -> std::optional { switch (enc) { case database::Container::kMp3: return codecs::StreamType::kMp3; case database::Container::kWav: return codecs::StreamType::kWav; case database::Container::kOgg: return codecs::StreamType::kVorbis; case database::Container::kFlac: return codecs::StreamType::kFlac; case database::Container::kOpus: return codecs::StreamType::kOpus; case database::Container::kWavPack: return codecs::StreamType::kWavPack; case database::Container::kAlac: return codecs::StreamType::kAlac; case database::Container::kUnsupported: default: return {}; } } } // namespace audio