#include "PlayerInputComponent.h"
#include "Player.h"
#include "InputEnums.h"

PlayerInputComponent::PlayerInputComponent(GLFWwindow* Window, Player& PlayerCharacter)
	:	IInputComponent(Window), PlayerCharacter(PlayerCharacter)
{
	glfwSetWindowUserPointer(Window, this);
	glfwSetCursorPosCallback(Window, ProcessMouse);
	glfwSetInputMode(Window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
	bFreeMouse = false;
}

void PlayerInputComponent::Update(float DeltaTime)
{
	ProcessKeyboard(DeltaTime);
}

void PlayerInputComponent::ProcessKeyboard(float DeltaTime)
{
	if (glfwGetKey(Window, GLFW_KEY_ESCAPE) == GLFW_PRESS && !bFreeMouse) {
		//glfwSetWindowShouldClose(Window, true);
		glfwSetInputMode(Window, GLFW_CURSOR, GLFW_CURSOR_NORMAL);
		bFreeMouse = true;
	}

	if (glfwGetKey(Window, GLFW_KEY_E) == GLFW_PRESS)
	{
		PlayerCharacter.Move(FORWARD, DeltaTime);
	}

	if (glfwGetKey(Window, GLFW_KEY_D) == GLFW_PRESS)
	{
		PlayerCharacter.Move(BACKWARD, DeltaTime);
	}

	if (glfwGetKey(Window, GLFW_KEY_S) == GLFW_PRESS)
	{
		PlayerCharacter.Move(LEFT, DeltaTime);
	}

	if (glfwGetKey(Window, GLFW_KEY_F) == GLFW_PRESS)
	{
		PlayerCharacter.Move(RIGHT, DeltaTime);
	}

	if (glfwGetKey(Window, GLFW_KEY_SPACE) == GLFW_PRESS)
	{
		PlayerCharacter.Jump();
	}

	if (glfwGetKey(Window, GLFW_KEY_LEFT_SHIFT) == GLFW_PRESS)
	{
		PlayerCharacter.Sprint();
	}

	if (glfwGetKey(Window, GLFW_KEY_LEFT_SHIFT) == GLFW_RELEASE)
	{
		PlayerCharacter.StopSprint();
	}

	if (glfwGetMouseButton(Window, GLFW_MOUSE_BUTTON_LEFT) == GLFW_PRESS)
	{
		if (bFreeMouse)
		{
			glfwSetInputMode(Window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
			bFirstMouse = true;
			bFreeMouse = false;
		}
	}
}

void PlayerInputComponent::ProcessMouse(GLFWwindow* Window, double xposIn, double yposIn)
{
	PlayerInputComponent* instance = static_cast<PlayerInputComponent*>(glfwGetWindowUserPointer(Window));
	if (!instance)
	{
		std::cout << "Player Input Component not found" << std::endl;
		return;
	}

	//if (glfwGetMouseButton(Window, GLFW_MOUSE_BUTTON_LEFT) == GLFW_PRESS && instance->bFreeMouse)
	//{
	//	glfwSetInputMode(Window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
	//	instance->bFirstMouse = true;
	//	instance->bFreeMouse = false;
	//}

	if (instance->bFreeMouse)
	{
		return;
	}

	//std::cout << "Mouse callback" << std::endl;
	float xpos = static_cast<float>(xposIn);
	float ypos = static_cast<float>(yposIn);

	if (instance->bFirstMouse)
	{
		instance->lastX = xpos;
		instance->lastY = ypos;
		instance->bFirstMouse = false;
	}

	float xoffset = xpos - instance->lastX;
	float yoffset = instance->lastY - ypos;

	instance->lastX = xpos;
	instance->lastY = ypos;

	instance->PlayerCharacter.Look(xoffset, yoffset);
}
