#include <SDL2/SDL.h>
#include <memory>
#include "core/character.h"
#include "core/input.h"
#include "core/renderer.h"
#include "core/world.h"
#include "enemies.h"
#include "player_logic.h"

using namespace rogue;

CharacterData const player_data{
	.health = 20,
	.damage = 2,
	.sprite = 3
};

CharacterData const critte_data{
	.health = 5,
	.damage = 1,
	.sprite = 2
};

template <typename TLogicType>
Character create_character(CharacterData const &stats, Tile tile) {
	return Character(tile, new TLogicType, stats);
}

int main(int argc, char *argv[]) {
	std::unique_ptr<World> world{WorldGenerator()
		.with_world_size(20)
		.with_chunk_size(10)
		.with_room_size(6, 10)
		.with_connecting_chance(5)
		.with_player(Character({0,0}, new PlayerCharacterLogic(), player_data))
		.with_enemy(std::bind(&create_character<CritteLogic>, critte_data, std::placeholders::_1), 2)
		.generate()
	};
	RenderData data{RenderDataSetup()
		.with_window("roguelike", SDL_WINDOW_ALLOW_HIGHDPI | SDL_WINDOW_FULLSCREEN)
		.with_renderer(SDL_RENDERER_ACCELERATED)
		.with_resource_path("resources/")
		.with_sprite("wizard.png")
		.with_sprite("wall.png")
		.with_sprite("critte.png")
		.with_sprite("player.png")
		.build()
	};
	Render::provide_render_data(data);
	SDL_Event evt;
	for(;;) {
		world->render();
		Render::present();
		if(SDL_WaitEvent(&evt)) {
			if(evt.type == SDL_QUIT) {
				goto main_loop;
			} else {
				Input::process_event(evt);
			}
		}
	} main_loop:
	return 0;
}
