#ifndef _H_XMLLOADER_H
#define _H_XMLLOADER_H

#include <vector>
#include <string>
#include <memory>
#include <unordered_map>

struct Tile;

struct EntityData {
	bool isPlayer;
	int x = 0, y = 0;
	std::string sprite;
	float frameSize = 0.f;
	std::string weapon = "pistolGun";
	std::string script;
	bool isDirectional = false;
};

struct MapData {
	std::string name;
	std::string file;
	int width = 0, height = 0;
	float tileSize = 32.f;
	std::vector<std::vector<std::shared_ptr<Tile>>> groundTiles;
};

struct SceneData {
	std::string id;
	std::string type;

	MapData map;
	std::vector<EntityData> entities;
};

struct WeaponData {
	std::string name;
	float fireSpeed = 250.0f;
	std::string script = "";
	std::string sprite;
	bool animated = false;
	float frameSize;
	float sizeX = 50.f, sizeY = 50.f;
	float offsetX = 0.f, offsetY = 0.f;
	float bulletFrameSize;
	float bulletSizeX = 50.f, bulletSizeY = 50.f;
	std::string bulletSprite;
	bool bulletAnimated = false;
	float bulletSpread = 1.0f, bulletSpeed = 3.0f, bulletDrop = 500.f;
	float modMin = 0.5f, modMax = 1.0f;
};

class XMLLoader
{
public:
	XMLLoader() {}
	bool loadScenes(const char* sceneFolder);
	bool loadWeapons(const char* weaponFolder);

	const std::shared_ptr<SceneData> getSceneData(const std::string& id) const { 
		try {
			return scenes.at(id);
		}
		catch (std::exception&) {
			return nullptr;
		}
	}
	const WeaponData* getWeaponDataByName(const char* name) const;

	void clearData() { scenes.clear(); weaponData.clear(); }
protected:
	bool loadXmlScene(const char* xmlFile, SceneData* out);
	bool loadMap(const char* xmlFile, SceneData* out);
	bool loadEntityData(const char* xmlFile, SceneData* out);
private:
	std::unordered_map<std::string, std::shared_ptr<SceneData>> scenes;

	std::vector<WeaponData> weaponData;
};

#endif // _H_XMLLOADER_H