//
// Created by Иван_Архипов on 07.11.2017.
//

#ifndef LOTRO_DAT_PATCHER_SUBDIRECTORY_H
#define LOTRO_DAT_PATCHER_SUBDIRECTORY_H

#include <vector>
#include <map>
#include <queue>
#include <unordered_map>
#include <unordered_set>
#include "SubFile.h"


extern "C++"
{
namespace LOTRO_DAT
{
    enum FILE_TYPE : int;
    class DatFile;
    class BinaryData;
    class SubFile;

    class SubDirectory
    {
    public:
        struct SubDirectoryOffsetComp {
            bool operator() (const std::shared_ptr<SubDirectory> &f, const std::shared_ptr<SubDirectory> &s){
                if (!f || !s)
                    return false;
                return f->offset_ < s->offset_;
            }
        };

        SubDirectory() = delete;
        explicit SubDirectory(const SubDirectory& other) = delete;
        SubDirectory& operator =(const SubDirectory &other) = delete;

        SubDirectory(long long offset, DatFile &dat, long long max_subdirs = 63);
        ~SubDirectory();
        void MakeDictionary(std::map<long long, std::shared_ptr<SubFile>> &dict);

        bool MakeSubDirectories();
        bool MakeSubFiles();

        void clear();

        static std::unordered_set<long long> visited_subdirectories_;
        static std::unordered_set<long long> visited_subfiles_;
        static std::set<std::shared_ptr<SubDirectory>, SubDirectoryOffsetComp> subdir_init_queue_;
        static std::set<std::shared_ptr<SubDirectory>, SubDirectoryOffsetComp> subfile_init_queue_;

    private:
        std::shared_ptr<SubFile> MakeSubfile(long long dictionary_offset, long long unknown1, long long file_id, long long file_offset,
                             long long file_size, long long timestamp, long long version, long long block_size, long long unknown2);

        FILE_TYPE GetSubfileType(long long file_id, long long file_offset) const;
        DatFile &dat_;
        long long offset_;
        long long max_subdirs_;

        std::vector<std::shared_ptr<SubDirectory>> subdirs_;
        std::vector<std::shared_ptr<SubFile>> subfiles_;
    };
}
};

#endif //LOTRO_DAT_PATCHER_SUBDIRECTORY_H
