#include <enginend/engine.h>
#include <enginend/graph/noise.h>
#include <luajit/lua.hpp>
#include <tiny/tdf.h>


Texture2D* noiseresult;
std::vector<enginend::nodes::node*>* gui=new std::vector<enginend::nodes::node*>{
	new enginend::nodes::twod::textured(noiseresult,0,0,512,512),
	new enginend::nodes::twod::text(NULL,enginend::DEFAULT,0,0,512,32,32,"")
};


class noiserenderer :public enginend::program{
public:
	tiny::TDF_FILE* config;
	std::string currentscript;
	std::vector<std::string> scripts;
	const char* CONF()override{return "scripts.tdf";}
	Image noiseout;
	noiserenderer(){
		config=new tiny::TDF_FILE;
		config->filepath=(char*)this->CONF();
		config->read();
		boost::unordered_map<std::string,tiny::TDF_DATA>luascripts=*(config->getclass({"lua"})); 
		for (auto data:luascripts){
			if (data.second.type==tiny::TDF_STR){
				scripts.push_back(*static_cast<std::string*>(data.second.datapointer));
			}
		}
		currentscript=scripts[0];
	}
	void boot() override{
		SetConfigFlags(FLAG_VSYNC_HINT);
		InitWindow(512, 512, "lua noise viewer");
		noiseout=GenImageColor(512,512,{255,255,255,255});

		
		this->currentscene=new enginend::scene();
		this->tickrate=3;
		this->framerate=3;
	}
	void tick() override{}
	void draw() override {
		
	}
	void exit() override{}
	~noiserenderer() {};
	
};

void refreshstuf(noiserenderer *program,char *refreshtdf,char *refreshnoise);

int main() {
	noiserenderer program;
	program.boot();
	struct timespec peepy;
	long time=1000000000L/((long)(program.framerate));
	char refreshtdf=program.config->getint({"tdfrefresh"});
	char refreshnoise=program.config->getint({"refreshsecs"});
	char checkrefresh=0,checkrefreshtdf=0,checkrefreshnoise=0;
	peepy.tv_nsec=time;
	peepy.tv_sec=0;
	
	while (true) {
		program.tick();
		program.draw();
		nanosleep(&peepy, nullptr);
		if (++checkrefresh==3) {
			checkrefresh=0;
			if (++checkrefreshnoise==refreshnoise) {
				checkrefreshnoise=0;
				
			}
			if (++checkrefreshtdf==refreshtdf) {
				checkrefreshtdf=0;
				refreshstuf(&program,&refreshtdf,&refreshnoise);
			}
		}
		if (IsKeyDown(KEY_LEFT_ALT)&&IsKeyDown(KEY_F4)){break;}
	}
	program.exit();
}


void refreshstuf(noiserenderer *program,char *refreshtdf,char *refreshnoise){
	tiny::TDF_FILE *tocheck=new tiny::TDF_FILE;
	tocheck->filepath=(char*)program->CONF();
	tocheck->read();
	bool  isequal=true;
	if (tocheck->todelete.size()!=program->config->todelete.size())isequal=false;
	else {
		std::string og="";
		std::string justread="";
		program->config->crawl(program->config->data,&og);
		tocheck->crawl(tocheck->data,&justread);
		isequal=og==justread;
	}
	if (!isequal){
		program->config->close();
		delete program->config;
		program->config=tocheck;
		boost::unordered_map<std::string,tiny::TDF_DATA>luascripts=*(program->config->getclass({"lua"})); 
		for (auto data:luascripts){
			if (data.second.type==tiny::TDF_STR){
				program->scripts.push_back(*static_cast<std::string*>(data.second.datapointer));
			}
		}
		*refreshtdf=program->config->getint({"tdfrefresh"});
		*refreshnoise=program->config->getint({"refreshsecs"});
		program->currentscript=program->scripts[0];
	}
	else {
		tocheck->close();
		delete tocheck;
	}
	
}