//
// Created by sebastian on 30.07.26.
//

#ifndef COLORRACE_ASSETLOADER_H
#define COLORRACE_ASSETLOADER_H
#include <condition_variable>
#include <format>
#include <mutex>
#include <queue>
#include <string>
#include <unordered_map>
#include <variant>
#include <vector>

#include "assets/AssetRequests.h"
#include "assets/LoadedAssets.h"
#include "assets/RawAssetData.h"

namespace engine {
    struct LoadingProgress {
        int total;
        int loaded;
        float fraction() const {
            return total > 0 ? static_cast<float>(loaded) / total : 1.f;
        }
        bool isDone() const {
            return loaded >= total;
        }
    };

    template<typename>
inline constexpr bool always_false = false;

    class AssetLoader {
    public:
        void scheduleAsset(const AssetRequest& request);
        void start();
        void stop();

        std::vector<LoadedAsset> processUploadQueue(int maxPerFrame);
        LoadingProgress getProgress() const;

    private:
        void loadingThreadFunc();

        static RawTextureData processTextureRequest(const TextureRequest& request);
        static RawModelBundle processModelRequest(const ModelRequest& request);
        static RawSoundData processSoundRequest(const SoundRequest& request);
        std::vector<IntermediateAsset> determineUploadQueue(int maxPerFrame);

        std::queue<AssetRequest> pendingQueue;
        std::mutex pendingMutex;
        std::condition_variable pendingCondition;

        std::queue<IntermediateAsset> readyQueue;
        std::mutex readyMutex;

        std::atomic<int> total{0};
        std::atomic<int> loaded{0};

        std::thread loadingThread;
        std::atomic<bool> running{false};
    };
}


#endif //COLORRACE_ASSETLOADER_H
