/**
 * Replacement Debug Interface

 * Copyright (C) 2022 Yeoldetoast

 * This file is part of YeoldeDink

 * Yeoldedink is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 3 of the
 * License, or (at your option) any later version.

 * Yeoldedink is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * General Public License for more details.

 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see
 * <http://www.gnu.org/licenses/>.
 */

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include "SDL.h"

#include "debug_imgui.h"
#include "game_state.h"
#include "game_engine.h"
#include "live_sprites_manager.h"
#include "input.h"
#include "log.h"
#include "dinkc.h"
#include "dinkc_console.h"
#include "freedink.h"
#include "gfx.h"
#include "gfx_sprites.h"
#include "update_frame.h"
#include "live_screen.h"
#include "ImageLoader.h"
#include "status.h"
#include "sfx.h"
#include "bgm.h"
#include "DMod.h"
#include "savegame.h"
#include "paths.h"
#include "app.h"

#include "imgui.h"
#include "imgui_impl_sdl.h"
// #include "imgui_impl_sdlrenderer.h"

//For the log window
ImGuiTextBuffer Buf;
ImGuiTextFilter Filter;
ImVector <int> LineOffsets;
bool AutoScroll = true;
//For transparent overlay
static int corner = 0;
char debugbuf[128];
static int ts = 1;
char sfbuf[128];
//For various other window settings
bool render_tiles = true;
bool drawhard;
bool globinfo;
int modorder;
int sfxvol;
int musvol;

//for the var/sprite editor
int varedit = 1;
int spriedit = 1;
bool spoutline;

//Toggleable settings
bool debug_meminfo;
bool debug_pinksquares;
bool debug_drawsprites = true;
bool debug_drawgame = true;
bool debug_gamewindow;
bool debug_paused;
bool debug_conpause;
bool debug_scripboot;
bool debug_interp = true;
bool debug_infhp;

//Toggles for smaller windows
bool ultcheat;
bool graphicsopt;
bool dswitch = true;
bool logwindow;
bool keeb;
bool scripfo;
bool sprinfo;
bool varinfo;
bool sfxinfo;
bool metrics;
bool mapsquares;
bool maptiles;
bool sysinfo;
bool mapsprites;

SDL_Texture* texture1 = NULL;

void dbg_imgui(void) {
    //Only show stuff if debug is on and the game has loaded to title screen
	if (debug_mode && mode) {
//Main Menu bar
ImGui::BeginMainMenuBar();
if (ImGui::BeginMenu("File"))
{
    if (ImGui::MenuItem("Leave debug mode"))
    log_debug_off();
	//ImGui::MenuItem("Pause", NULL, &debug_paused);
	if (ImGui::MenuItem("Restart"))
		game_restart();
	if (ImGui::MenuItem("Quit")) {
	    SDL_Event ev;
	    ev.type = SDL_QUIT;
	    SDL_PushEvent(&ev);
	}
	ImGui::EndMenu();
}

if (ImGui::BeginMenu("Options")) {
	ImGui::MenuItem("Info Window", NULL, &dswitch);
	if (ImGui::MenuItem("Activate Console", "Alt+C"))
		dinkc_console_show();

	ImGui::MenuItem("Pause while console activated", NULL, &debug_conpause);

	ImGui::EndMenu();
}

if (ImGui::BeginMenu("Display")) {	
	ImGui::MenuItem("Game popout", NULL, &debug_gamewindow);
	ImGui::Separator();
	ImGui::MenuItem("Game in background", NULL, &debug_drawgame);
	ImGui::MenuItem("Pink Squares", NULL, &debug_pinksquares);
	ImGui::MenuItem("Collision Overlay", "Alt+H", &drawhard);
	ImGui::MenuItem("Tiles and background", NULL, &render_tiles);
	ImGui::MenuItem("Linear filtering", NULL, &debug_interp);
	ImGui::Separator();
	if (ImGui::MenuItem("Set window to 640x480")) {
		SDL_SetWindowSize(g_display->window, 640, 480);
	}
	if (ImGui::MenuItem("Set window to 1280x960")) {
	SDL_SetWindowSize(g_display->window, 1280, 960);
	SDL_SetWindowPosition(g_display->window, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED);
	}
	if (ImGui::MenuItem("Set window to 1920x1440")) {
		SDL_SetWindowSize(g_display->window, 1920, 1440);
		SDL_SetWindowPosition(g_display->window, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED);
	}

	if (ImGui::MenuItem("Toggle full screen display")) {
		g_display->toggleFullScreen();
	}

	ImGui::EndMenu();
}

if (ImGui::BeginMenu("Engine Info"))
{
    //ImGui::MenuItem("Debug Mode Options", NULL, &dswitch);
    ImGui::MenuItem("Debug Log", NULL, &logwindow);
	ImGui::MenuItem("Ultimate Cheat", NULL, &ultcheat);
	//ImGui::MenuItem("Graphics Options", NULL, &graphicsopt); 
    ImGui::MenuItem("Keyboard and Joystick", NULL, &keeb);
    ImGui::MenuItem("Audio", NULL, &sfxinfo);
	ImGui::MenuItem("Map Index", NULL, &mapsquares);
	ImGui::MenuItem("System Information", NULL, &sysinfo);

	ImGui::EndMenu();
}

//TODO: incorporate this in one of the other menus
//if (ImGui::BeginMenu("Log Level"))
//{
//	if (ImGui::MenuItem("Errors only"))
//		log_debug_on(0);
//	if (ImGui::MenuItem("Standard"))
//		log_debug_on(1);
//	if (ImGui::MenuItem("Verbose"))
//		log_debug_on(2);
//
//	ImGui::EndMenu();
//}

if (ImGui::BeginMenu("Screen Info"))
{
	//ImGui::MenuItem("Tile Screen Preview", NULL, &maptiles);
	ImGui::MenuItem("Sprites", NULL, &sprinfo);
	ImGui::MenuItem("Variables", NULL, &varinfo);
	ImGui::MenuItem("Scripts", NULL, &scripfo);
	//ImGui::MenuItem("Sprites", NULL, &mapsprites);
	ImGui::EndMenu();
}

if (ImGui::BeginMenu("Speed"))
{
	if (ImGui::MenuItem("Normal Speed"))
		game_set_normal_speed();
	if (ImGui::MenuItem("High speed"))
		game_set_high_speed();
	if (ImGui::MenuItem("Slow speed"))
		game_set_slow_speed();

	ImGui::EndMenu();
}


	//Only show if game has started. Does weird stuff otherwise and I can't be bothered to fix it
if (ImGui::BeginMenu("Quick Save/Load"))
{
	if (mode < 2)
	ImGui::BeginDisabled();
	if (ImGui::MenuItem("Save"))
		save_game(1337);
	


	if (ImGui::MenuItem("Load")) {
		kill_all_scripts_for_real();
		load_game(1337);
		*pupdate_status = 1;
		draw_status_all();
	}
	if (mode < 2)
	ImGui::EndDisabled();

	ImGui::EndMenu();
}

if (console_active == 1) {
	if (ImGui::BeginMenu("Warning! Console Active!")) {
		if (ImGui::MenuItem("Deactivate Console", "Alt+C"))
			dinkc_console_hide();
		ImGui::EndMenu();
	}
	
}


ImGui::EndMainMenuBar();
//ImGui::ShowDemoWindow();

//Transparent overlay info window, stolen from the demo
if (dswitch) {
ImGuiIO& io = ImGui::GetIO();
io.MouseDrawCursor = true;
ImGuiWindowFlags window_flags = ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoFocusOnAppearing | ImGuiWindowFlags_NoNav;
if (corner != -1)
    {
        const float PAD = 10.0f;
        const ImGuiViewport* viewport = ImGui::GetMainViewport();
        ImVec2 work_pos = viewport->WorkPos; // Use work area to avoid menu-bar/task-bar, if any!
        ImVec2 work_size = viewport->WorkSize;
        ImVec2 window_pos, window_pos_pivot;
        window_pos.x = (corner & 1) ? (work_pos.x + work_size.x - PAD) : (work_pos.x + PAD);
        window_pos.y = (corner & 2) ? (work_pos.y + work_size.y - PAD) : (work_pos.y + PAD);
        window_pos_pivot.x = (corner & 1) ? 1.0f : 0.0f;
        window_pos_pivot.y = (corner & 2) ? 1.0f : 0.0f;
        ImGui::SetNextWindowPos(window_pos, ImGuiCond_Always, window_pos_pivot);
        window_flags |= ImGuiWindowFlags_NoMove;
    }
	ImGui::SetNextWindowBgAlpha(0.35f); // Transparent background
    if (ImGui::Begin("Example: Simple overlay", NULL, window_flags))
    {
        ImGui::Text("Debug mode enabled. Press Alt+D to disable, Alt+C for console");
        ImGui::Separator();
		//Change the colour according to framerate
		ImVec4 col = ImVec4(1.0f, 1.0f, 0.0f, 1.0f);
		float fram = ImGui::GetIO().Framerate;
		if (fram >= 50)
			col = ImVec4(0.1f, 1.0f, 0.0f, 1.0f);
		if (fram < 30)
			col = ImVec4(1.0f, 0.0f, 0.0f, 1.0f);
		ImGui::TextColored(col, "Application average %.3f ms/frame (%.1f FPS)", 1000.0f / ImGui::GetIO().Framerate, ImGui::GetIO().Framerate);
		ImGui::Text("Sprites: %d Moveman X%d X%d: Speed: %d Y%d Y%d, Screen: %d (%d)",
					last_sprite_created, spr[1].lpx[0],
					spr[1].lpy[0], spr[1].moveman, spr[1].lpx[1], spr[1].lpy[1], *pplayer_map, g_dmod.map.loc[*pplayer_map]);
        //if (ImGui::IsMousePosValid())
        //    ImGui::Text("Raw Mouse Position: (%.1f,%.1f)", io.MousePos.x, io.MousePos.y);
        //else
        //    ImGui::Text("Mouse Position: <invalid>");
        ImGui::Text("%s", log_getLastLog());
		ImGuiInputTextFlags input_text_flags = ImGuiInputTextFlags_EnterReturnsTrue;
		if (console_active) {
			if (debug_conpause)
				debug_paused = 1;
		if (ImGui::InputText("Console Active", debugbuf, IM_ARRAYSIZE(debugbuf), input_text_flags))
			{
			ImGui::SetItemDefaultFocus();
			dinkc_execute_one_liner(debugbuf);
			strcpy(debugbuf, "");
			}
		}
        if (ImGui::BeginPopupContextWindow())
        {
            if (ImGui::MenuItem("Custom",       NULL, corner == -1)) corner = -1;
            if (ImGui::MenuItem("Top-left",     NULL, corner == 0)) corner = 0;
            if (ImGui::MenuItem("Top-right",    NULL, corner == 1)) corner = 1;
            if (ImGui::MenuItem("Bottom-left",  NULL, corner == 2)) corner = 2;
            if (ImGui::MenuItem("Bottom-right", NULL, corner == 3)) corner = 3;
            if (ImGui::MenuItem("Close")) dswitch = false;
            ImGui::EndPopup();
        }
    }
    ImGui::End();
}
//Keyboard state and gamepad in future
if (keeb) {
ImGui::Begin("Keyboard and Joystick", &keeb);
int x;
for (x = 0; x < 256; x++)
	if (input_getcharstate(x))
	ImGui::Text("Key %i", x);
	if (jinfo) {
			ImGui::Text("Name: %s", SDL_JoystickName(jinfo));
			ImGui::Text("Controller rumble available: %d", SDL_JoystickHasRumble(jinfo));
			ImGui::Text("Power level: %d", SDL_JoystickCurrentPowerLevel(jinfo));
			if (ImGui::Button("Test rumble")) {
				SDL_JoystickRumble(jinfo, 0xFFFF, 0xFFFF, 800);
				}
			}
	else {
		ImGui::Text("Joystick/Gamepad not available");
	}
ImGui::End();
}

//Log Window
if (logwindow) {
ImGui::Begin("Log", &logwindow);
ImGui::Text("Log Level:");
ImGui::SameLine();
if (ImGui::Button("Errors Only"))
log_debug_on(0);
ImGui::SameLine();
if (ImGui::Button("All Debug and Application Info"))
log_debug_on(1);
ImGui::SameLine();
if (ImGui::Button("Verbose"))
log_debug_on(2);
ImGui::Separator();
ImGui::Text("Log:");
ImGui::SameLine();
ImGui::Checkbox("Meminfo", &debug_meminfo);
ImGui::SameLine();
ImGui::Checkbox("Boot", &debug_scripboot);
ImGuiInputTextFlags input_text_flags = ImGuiInputTextFlags_EnterReturnsTrue;
	if (console_active) {
	if (ImGui::InputText("DinkC Console", debugbuf, IM_ARRAYSIZE(debugbuf), input_text_flags))
	{
		dinkc_execute_one_liner(debugbuf);
		strcpy(debugbuf, "");
	}
	}
ImGui::Separator();
ImGui::Checkbox("Auto-scroll", &AutoScroll);
ImGui::SameLine();
if (ImGui::Button("Clear"))
memset(&Buf, 0, sizeof(debugbuf));
ImGui::SameLine();
if (ImGui::Button("Copy last message to clipboard")) {
ImGui::LogToClipboard();
ImGui::LogText(log_getLastLog());
ImGui::LogFinish();
ImGui::Separator();
}
ImGui::Separator();
//Child window with text in it
ImGui::BeginChild("scrolling");
const char* buf = Buf.begin();
const char* buf_end = Buf.end();
ImGui::TextUnformatted(buf, buf_end);
if (AutoScroll)
ImGui::SetScrollHereY(1.0f);

ImGui::EndChild();
ImGui::End();
}

//Ultimate Cheat
if (ultcheat) {
ImGui::Begin("Ultimater Cheat", &ultcheat);

if (ImGui::Button("Refill health"))
    plife = plifemax;
ImGui::SameLine();
if (ImGui::Button("Redraw status bar"))
    draw_status_all();
ImGui::SameLine();
if (ImGui::Button("Unlock screen"))
	screenlock = 0;
ImGui::SameLine();
if (ImGui::Button("Load/Draw screen")) {
	game_load_screen(g_dmod.map.loc[*pplayer_map]);
	draw_screen_game();
}
if (ImGui::Button("Kill enemies")) {
	for (int i = 0; i < MAX_SPRITES_AT_ONCE; i++) {
		if (spr[i].hitpoints > 0)
		spr[i].damage = spr[i].hitpoints;
	}
}
ImGui::SameLine();
if (ImGui::Button("Unfreeze Sprite 1")) {
	spr[1].freeze = 0;
}

ImGui::Checkbox("Infinite health", &debug_infhp);
ImGui::Separator();
ImGui::SliderInt("Gold", pgold, 0, 9000);
ImGui::SliderInt("Attack", pstrength, 0, 999);
ImGui::SliderInt("Defense", pdefense, 0, 999);
ImGui::SliderInt("Magic", pmagic, 0, 999);
ImGui::SliderInt("Life", plife, 0, *plifemax);
ImGui::SliderInt("Lifemax", plifemax, 1, 500);
ImGui::SliderInt("Level", plevel, 1, 32);
ImGui::SliderInt("Map Screen", pplayer_map, 1, 768);
ImGui::SliderInt("Walk Speed (lower is faster)", &dinkspeed, 0, 5);
ImGui::SliderInt("Screen X", &spr[1].x, 0, 620);
ImGui::SliderInt("Screen Y", &spr[1].y, -1, 400);

ImGui::End();
}

if (graphicsopt) {
//Rendering options - obsoleted
ImGui::Begin("Graphics", &graphicsopt);
ImGui::Text("Video driver: %s", SDL_GetCurrentVideoDriver());
ImGui::Separator();
ImGui::Checkbox("Draw all Collision Data", &drawhard);
//ImGui::Checkbox("Draw Sprites", &debug_drawsprites);
ImGui::Checkbox("Redraw background", &render_tiles);
if (ImGui::Button("Fade Down"))
dinkc_execute_one_liner("fade_down()");
if (ImGui::Button("Fade up instantly"))
up_cycle();
ImGui::End();
}

if (scripfo) {
ImGui::Begin("Scrip Info", &scripfo, ImGuiWindowFlags_AlwaysAutoResize);
//For making scrip to show just one time
int m = 0;
//C has no reflection apparently
if (ImGui::BeginTable("table2", 13, ImGuiTableFlags_Borders)) {
	ImGui::TableSetupColumn("Name");
	ImGui::TableSetupColumn("Line");
	ImGui::TableSetupColumn("Column");
	ImGui::TableSetupColumn("Sprite");
	ImGui::TableSetupColumn("arg1");
	ImGui::TableSetupColumn("arg2");
	ImGui::TableSetupColumn("arg3");
	ImGui::TableSetupColumn("arg4");
	ImGui::TableSetupColumn("arg5");
	ImGui::TableSetupColumn("arg6");
	ImGui::TableSetupColumn("arg7");
	ImGui::TableSetupColumn("arg8");
	ImGui::TableSetupColumn("arg9");
	ImGui::TableHeadersRow();
for (int i = 0; i < MAX_SCRIPTS; i++)
	if (rinfo[i] != NULL)
    {	
		ImGui::TableNextColumn();
        ImGui::Text("%s", rinfo[i]->name);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->cur_line);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->cur_col);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->sprite);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg1);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg2);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg3);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg4);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg5);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg6);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg7);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg8);
		ImGui::TableNextColumn();
		ImGui::Text("%d", rinfo[i]->arg9);
		m++;
    }
	ImGui::EndTable();
}
ImGui::Separator();
ImGui::Text("Scrips to show:");
ImGui::SameLine();
float progress = (float)m / (float)MAX_SCRIPTS;
char buf[32];
sprintf(buf, "%d/%d", m, MAX_SCRIPTS);
ImGui::ProgressBar(progress, ImVec2(0.0f, 0.0f), buf);

ImGui::End();
}
//Sprite Information
if (sprinfo) {
    ImGui::Begin("Active Sprites", &sprinfo, ImGuiWindowFlags_AlwaysAutoResize);
	if (ImGui::BeginTabBar("spritab")) {
		if (ImGui::BeginTabItem("Sprite List")) {
    	if (ImGui::BeginTable("table1", 17, ImGuiTableFlags_Borders | ImGuiTableFlags_Reorderable)) {
			ImGui::TableSetupColumn("No.");
			ImGui::TableSetupColumn("x");
			ImGui::TableSetupColumn("y");
			ImGui::TableSetupColumn("pSeq");
			ImGui::TableSetupColumn("pFrame");
			ImGui::TableSetupColumn("Timing");
			ImGui::TableSetupColumn("Script");
			ImGui::TableSetupColumn("Brain/parms");
			ImGui::TableSetupColumn("HP");
			ImGui::TableSetupColumn("Dir");
			ImGui::TableSetupColumn("Cue");
			ImGui::TableSetupColumn("Freeze");
			ImGui::TableSetupColumn("Size");
			ImGui::TableSetupColumn("Text");
			ImGui::TableSetupColumn("Editor No.");
			ImGui::TableSetupColumn("Hard");
			ImGui::TableSetupColumn("Nodraw");
			ImGui::TableHeadersRow();
			for (int x = 1; x < MAX_SPRITES_AT_ONCE; ++x) {
				if (spr[x].active) {
					ImGui::TableNextColumn();
					ImGui::Text("%d", x);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].x);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].y);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].pseq);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].pframe);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].timing);
					ImGui::TableNextColumn();
					if (spr[x].script > 0)
					//ImGui::Text("%s", rinfo[spr[x].script]->name);
					ImGui::Text("%i", spr[x].script);
					else
					ImGui::Text("None");
					ImGui::TableNextColumn();
					ImGui::Text("%d/%d/%d", spr[x].brain, spr[x].brain_parm, spr[x].brain_parm2);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].hitpoints);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].dir);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].que);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].freeze);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].size);
					ImGui::TableNextColumn();
					ImGui::Text("%s", spr[x].text);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].sp_index);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].hard);
					ImGui::TableNextColumn();
					ImGui::Text("%d", spr[x].nodraw);
				}	
    	}
		ImGui::EndTable();
		}
		ImGui::EndTabItem();
		}
	//Sprite editor tab
	if (ImGui::BeginTabItem("Editor")) {
		ImGui::Text("Activate the console to type directly into the boxes");
		ImGui::Text("Selected Sprite: %d", spriedit);
		ImGui::SameLine();
		ImGui::PushButtonRepeat(true);
		if (ImGui::ArrowButton("##left", ImGuiDir_Left) && spriedit != 1) { spriedit--; }
		ImGui::SameLine(0.0f, ImGui::GetStyle().ItemInnerSpacing.x);
		if (ImGui::ArrowButton("##right", ImGuiDir_Right)) { spriedit++; }
		ImGui::PopButtonRepeat();
		ImGui::SameLine();
		ImGui::Checkbox("Highlight", &spoutline);
		ImGui::Separator();
		//Sprite properties
		if (ImGui::Button("Deactivate sprite")) {
			spr[spriedit].active = 0;
		}
		ImGui::SliderInt("X", &spr[spriedit].x, 0, 600);
		ImGui::SliderInt("Y", &spr[spriedit].y, 0, 400);
		ImGui::RadioButton("Frozen", &spr[spriedit].freeze, 1);
		ImGui::SameLine();
		ImGui::RadioButton("Thawed", &spr[spriedit].freeze, 0);
		ImGui::RadioButton("Not nohit", &spr[spriedit].nohit, 0);
		ImGui::SameLine();
		ImGui::RadioButton("Nohit active", &spr[spriedit].nohit, 1);
		ImGui::RadioButton("Drawn", &spr[spriedit].nodraw, 0);
		ImGui::SameLine();
		ImGui::RadioButton("Nodraw", &spr[spriedit].nodraw, 1);
		ImGui::RadioButton("Hard on", &spr[spriedit].hard, 0);
		ImGui::SameLine();
		ImGui::RadioButton("Hard off", &spr[spriedit].hard, 1);
		ImGui::SliderInt("pSequence", &spr[spriedit].pseq, 1, 1000);
		ImGui::SliderInt("pFrame", &spr[spriedit].pframe, 1, 69);
		ImGui::SliderInt("Direction", &spr[spriedit].dir, 1, 8);
		ImGui::SliderInt("Size", &spr[spriedit].size, 1, 200);
		ImGui::InputInt("Timing", &spr[spriedit].timing);
		ImGui::InputInt("Frame Delay", &spr[spriedit].frame_delay);
		//Change to drop down box eventually
		//ImGui::InputInt("Brain", &spr[spriedit].brain, 1, 2);
		ImGui::SliderInt("Depth Cue", &spr[spriedit].que, -1000, 1000);
		ImGui::InputText("Text", spr[spriedit].text, sizeof(spr[spriedit].text));
		//ImGui::SliderInt("Hitpoints", &spr[spriedit].hitpoints, 0, 100);
		ImGui::Separator();
		if (ImGui::TreeNode("More sequences")) {
			ImGui::InputInt("Sequence", &spr[spriedit].seq);
			ImGui::InputInt("Frame", &spr[spriedit].frame);
			ImGui::InputInt("Blood Sequence", &spr[spriedit].bloodseq);
			ImGui::InputInt("Blood number", &spr[spriedit].bloodnum);
			ImGui::InputInt("Base Walk", &spr[spriedit].base_walk);
			ImGui::InputInt("Base Idle", &spr[spriedit].base_idle);
			ImGui::InputInt("Base Hit", &spr[spriedit].base_hit);
			ImGui::InputInt("Base Attack", &spr[spriedit].base_attack);
			ImGui::InputInt("Base Die", &spr[spriedit].base_die);
			ImGui::TreePop();
		}
		ImGui::Separator();
		if (ImGui::TreeNode("Enemy parameters")) {
			ImGui::InputInt("Hitpoints", &spr[spriedit].hitpoints);
			ImGui::InputInt("Touch damage", &spr[spriedit].touch_damage);
			ImGui::InputInt("Defence", &spr[spriedit].defense);
			ImGui::InputInt("Strength", &spr[spriedit].strength);
			ImGui::InputInt("Experience points", &spr[spriedit].exp);

			ImGui::TreePop();
		}
		ImGui::Separator();
		if (ImGui::TreeNode("Brain and parms")) {
			ImGui::InputInt("Brain", &spr[spriedit].brain);
			ImGui::InputInt("Parm 1", &spr[spriedit].brain_parm);
			ImGui::InputInt("Parm 2", &spr[spriedit].brain_parm2);

			ImGui::TreePop();
		}
		ImGui::Separator();
		if (ImGui::TreeNode("Clipping")) {
			ImGui::InputInt("Clip top", &spr[spriedit].alt.top);
			ImGui::InputInt("Clip left", &spr[spriedit].alt.left);
			ImGui::InputInt("Clip right", &spr[spriedit].alt.right);
			ImGui::Text("Set this as high as it will go");
			ImGui::InputInt("Clip bottom", &spr[spriedit].alt.bottom);

			ImGui::TreePop();
		}
		ImGui::EndTabItem();
	}
	ImGui::EndTabBar();  
	}
	ImGui::End();
}


if (varinfo) {
    ImGui::Begin("Variables", &varinfo, ImGuiWindowFlags_AlwaysAutoResize);
	//editor and option(s)
	ImGui::Checkbox("Hide globals", &globinfo);
	ImGui::Separator();
	ImGui::Text("Variable number: %d", varedit);
	ImGui::SameLine();
	ImGui::PushButtonRepeat(true);
	if (ImGui::ArrowButton("##left", ImGuiDir_Left) && varedit != 1) { varedit--; }
	ImGui::SameLine(0.0f, ImGui::GetStyle().ItemInnerSpacing.x);
	if (ImGui::ArrowButton("##right", ImGuiDir_Right)) { varedit++; }
	ImGui::PopButtonRepeat();
	ImGui::InputInt("Value", &play.var[varedit].var);
	ImGui::Separator();
	//Table begins
	if (ImGui::BeginTable("table5", 5, ImGuiTableFlags_Borders)) {
	ImGui::TableSetupColumn("Number");
	ImGui::TableSetupColumn("Name");
	ImGui::TableSetupColumn("Value");
	ImGui::TableSetupColumn("Active");
	ImGui::TableSetupColumn("Scope");
	ImGui::TableHeadersRow();
    for (int i = 1; i < MAX_VARS; i++) {
		if (!strncmp(play.var[i].name, "&", 1)) {
			if (play.var[i].scope == 0 && globinfo) { }
			else {
		ImGui::TableNextColumn();
		ImGui::Text("%d", i);
		ImGui::TableNextColumn();
        ImGui::Text(play.var[i].name);
		ImGui::TableNextColumn();
		ImGui::Text("%d", play.var[i].var);
		//ImGui::DragInt("##value", *play.var[i].var);
		ImGui::TableNextColumn();
		ImGui::Text("%d", play.var[i].active);
		ImGui::TableNextColumn();
		ImGui::Text("%d", play.var[i].scope);
		if (i == varedit)
		ImGui::TableSetBgColor(ImGuiTableBgTarget_RowBg0, ImGui::GetColorU32(ImVec4(0.7f, 0.3f, 0.3f, 0.65f)));
		ImGui::TableNextRow();
			}
		}
	
    }
	ImGui::EndTable();
	}
    ImGui::End();
}

if (sfxinfo) {
    ImGui::Begin("Audio Settings", &sfxinfo, ImGuiWindowFlags_AlwaysAutoResize);
	sfxvol = Mix_MasterVolume(-1);
	musvol = Mix_VolumeMusic(-1);
	ImGui::Text("Music decoders: %d", Mix_GetNumMusicDecoders());
	for (int i=0; i < Mix_GetNumMusicDecoders(); i++)
	ImGui::Text("%s", Mix_GetMusicDecoder(i));
	ImGui::Separator();
	if (Mix_GetSoundFonts() != NULL) {
		ImGui::Text("SoundFont in use: %s", Mix_GetSoundFonts());
	}
	else {
	ImGui::Text("SoundFont not in use");
	ImGui::InputText("Path to SoundFont", sfbuf, IM_ARRAYSIZE(sfbuf)); 
	ImGui::SameLine();
	if (ImGui::Button("Set"))
	{
	Mix_SetSoundFonts(sfbuf);
	//strcpy("", sfbuf);
	}
	}
	ImGui::SliderInt("mod order", &modorder, 0, 99);
	if (ImGui::Button("Set Mod Order")) {
	#if SDL_MIXER_MINOR_VERSION < 6
	log_error("Your SDL Mixer version is too old to use this feature");
	#else
	Mix_ModMusicJumpToOrder(modorder);
	#endif
	}

	ImGui::Separator();
	if (ImGui::SliderInt("SFX Volume", &sfxvol, 0, MIX_MAX_VOLUME))
	Mix_MasterVolume(sfxvol);
	if (ImGui::SliderInt("Music Volume", &musvol, 0, MIX_MAX_VOLUME))
	Mix_VolumeMusic(musvol);
	ImGui::Separator();
	if (something_playing()) {
		if (ImGui::Button("Halt BGM"))
		bgm_quit();
	}
	if (ImGui::Button("Pause BGM"))
		PauseMidi();
	ImGui::SameLine();
	if (ImGui::Button("Resume BGM"))
		ResumeMidi();
	ImGui::SameLine();
	if (ImGui::Button("Rewind BGM"))
		Mix_RewindMusic();
	ImGui::SameLine();
	if (ImGui::Button("Halt all SFX"))
		Mix_HaltChannel(-1);
	ImGui::Separator();
	//ImGui::Text("SFX Channels in use:");
	//int i;
	//for (i; i< 20; i++) {
	//	if (get_channel(i))
	//	ImGui::Text("%s", i);
	//}
	ImGui::End();
}

if (sysinfo) {
	ImGui::Begin("System Information", &sysinfo, ImGuiWindowFlags_AlwaysAutoResize);
	ImGui::Text("SDL Revision: %s", SDL_GetRevision());
	ImGui::Text("Platform: %s", SDL_GetPlatform());
	ImGui::Text("Video driver: %s", SDL_GetCurrentVideoDriver());
	ImGui::Text("Audio driver: %s", SDL_GetCurrentAudioDriver());
	//ImGui::Text("Mixer ver: %d", Mix_Linked_Version());
	ImGui::Text("System RAM: %iMiB", SDL_GetSystemRAM());
	ImGui::End();
}

if (metrics) {
	ImGui::Begin("Metrics Graphs", &metrics, ImGuiWindowFlags_AlwaysAutoResize);
	ImGui::Text("Todo");
	ImGui::End();
}

if (mapsquares) {
	ImGui::Begin("Map Squares", &mapsquares, ImGuiWindowFlags_AlwaysAutoResize);
	if (ImGui::BeginTable("table3", 32, ImGuiTableFlags_Borders))
{
    for (int item = 1; item < 769; item++)
    {
        ImGui::TableNextColumn();
		if (item == *pplayer_map)
		ImGui::TextColored(ImVec4(0,1,0,1), "%i", g_dmod.map.loc[item]);
		else
        ImGui::Text("%i", g_dmod.map.loc[item]);
		if (ImGui::IsItemHovered())
                ImGui::SetTooltip("Screen: %i, Indoor: %i, Music: %i", item, g_dmod.map.indoor[item], g_dmod.map.music[item]);
		if (ImGui::BeginPopupContextWindow()) {
			if (ImGui::MenuItem("Custom", NULL)) dswitch = -1;
			ImGui::EndPopup();
		}
    }
    ImGui::EndTable();
}
ImGui::End();
}

if (maptiles) {
	ImGui::Begin("Tilescreens", &maptiles);
	if (ImGui::SliderInt("Screen", &ts, 1, 41)) {
	texture1 = NULL;
	texture1 = SDL_CreateTextureFromSurface(SDL_GetRenderer(g_display->window), g_dmod.bgTilesets.slots[ts]->screenshot());
	}
	ImGui::Image(texture1, ImVec2((int)g_dmod.bgTilesets.slots[ts]->w, g_dmod.bgTilesets.slots[ts]->h));
	ImVec2 canvas_p0 = ImGui::GetCursorScreenPos();
	ImVec2 canvas_sz = ImGui::GetContentRegionAvail(); 
	ImDrawList* draw_list = ImGui::GetWindowDrawList();
	ImVec2 canvas_p1 = ImVec2(canvas_p0.x + canvas_sz.x, canvas_p0.y + canvas_sz.y);
	//for (int i = 1; i < 96; i++) {
	//	
	//	ImGui::Text("%i", cur_ed_screen.t[i].square_full_idx0);
	//}
	ImGui::End();
}

if (mapsprites) {
	ImGui::Begin("Sprites", &mapsprites);
		int seq_no = 75;
		SDL_Texture *texture = SDL_CreateTextureFromSurface(SDL_GetRenderer(g_display->window), GFX_k[seq[seq_no].frame[1]].k->screenshot());
		ImGui::Image(texture, ImVec2((int)GFX_k[seq[seq_no].frame[1]].k->w, GFX_k[seq[seq_no].frame[1]].k->h));
	ImGui::End();
}

//To make it pause when console is shown and relevant setting is on
if (console_active == 0 && debug_conpause) {
	debug_paused = 0;
}  

//Stolen from freedinkedit, toggled in display options, requested by drone1400. Runs really slow in GL mode
if (drawhard) {
    int x1, y1;
	for (x1 = 0; x1 < 600; x1++)
		for (y1 = 0; y1 < 400; y1++) {
			if (screen_hitmap[x1][y1] == 1) {
				{
					SDL_Rect GFX_box_crap;
					GFX_box_crap.x = x1 + playl;
					GFX_box_crap.y = y1;
					GFX_box_crap.w = 1;
					GFX_box_crap.h = 1;
					IOGFX_backbuffer->fillRect(&GFX_box_crap, GFX_ref_pal[1].r,
											GFX_ref_pal[1].g,
											GFX_ref_pal[1].b);
				}
			}

			if (screen_hitmap[x1][y1] == 2) {
				{
					SDL_Rect GFX_box_crap;
					GFX_box_crap.x = x1 + playl;
					GFX_box_crap.y = y1;
					GFX_box_crap.w = 1;
					GFX_box_crap.h = 1;
					IOGFX_backbuffer->fillRect(
							&GFX_box_crap, GFX_ref_pal[128].r,
							GFX_ref_pal[128].g, GFX_ref_pal[128].b);
				}
			}

			if (screen_hitmap[x1][y1] == 3) {
				{
					SDL_Rect GFX_box_crap;
					GFX_box_crap.x = x1 + playl;
					GFX_box_crap.y = y1;
					GFX_box_crap.w = 1;
					GFX_box_crap.h = 1;
					IOGFX_backbuffer->fillRect(&GFX_box_crap, GFX_ref_pal[45].r,
											GFX_ref_pal[45].g,
											GFX_ref_pal[45].b);
				}
			}

			if (screen_hitmap[x1][y1] > 100) {

				if (cur_ed_screen.sprite[(screen_hitmap[x1][y1]) - 100]
							.is_warp == 1) {
					{
						SDL_Rect GFX_box_crap;
						GFX_box_crap.x = x1 + playl;
						GFX_box_crap.y = y1;
						GFX_box_crap.w = 1;
						GFX_box_crap.h = 1;
						IOGFX_backbuffer->fillRect(
								&GFX_box_crap, GFX_ref_pal[20].r,
								GFX_ref_pal[20].g, GFX_ref_pal[20].b);
					}
				} else {
					{
						SDL_Rect GFX_box_crap;
						GFX_box_crap.x = x1 + playl;
						GFX_box_crap.y = y1;
						GFX_box_crap.w = 1;
						GFX_box_crap.h = 1;
						IOGFX_backbuffer->fillRect(
								&GFX_box_crap, GFX_ref_pal[23].r,
								GFX_ref_pal[23].g, GFX_ref_pal[23].b);
					}
				}
			}
		}

}

if (spoutline && (spr[spriedit].active == 1)) {
	rect box;
	rect_copy(&box, &k[getpic(spriedit)].hardbox);
	SDL_Rect r = {box.left + spr[spriedit].x, box.top + spr[spriedit].y, box.right - box.left,
									box.bottom - box.top};
						IOGFX_backbuffer->fillRect(&r, 255, 100, 0);


}


}



}