//
// Created by Bram on 11/12/2024.
//

#include <iostream>
#include "GamePadController.h"

GamePadController::GamePadController() = default;

GamePadController::~GamePadController() {
    for (auto pGameController : m_pGameControllers) {
        SDL_GameControllerClose(pGameController);
    }
}

void GamePadController::Init() {
    const int numJoysticks = SDL_NumJoysticks();
    for (int i = 0; i < numJoysticks; i++) {
        if (SDL_IsGameController(i)) {
            SDL_GameController *pController = SDL_GameControllerOpen(i);
            if (pController) {
                m_pGameControllers.push_back(pController);
                m_GamePads.push_back(GamePad());
            }
        }
    }
}

void GamePadController::Update() {
    //Check for new controllers
    const int numJoysticks = SDL_NumJoysticks();
    if(numJoysticks > m_pGameControllers.size()){
        for (int i = 0; i < numJoysticks; i++) {
            if (SDL_IsGameController(i)) {
                bool bFound = false;
                for (auto pController : m_pGameControllers) {
                    if (SDL_GameControllerGetJoystick(pController) == SDL_JoystickFromInstanceID(i)) {
                        bFound = true;
                        break;
                    }
                }

                if (!bFound) {
                    SDL_GameController *pController = SDL_GameControllerOpen(i);
                    if (pController) {
                        m_pGameControllers.push_back(pController);
                        m_GamePads.push_back(GamePad());

                        std::cout << "New Controller Connected" << std::endl;
                    }
                }
            }
        }
    }

    for (int i = 0; i < m_pGameControllers.size(); ++i) {
        SDL_GameController *pController = m_pGameControllers[i];
        if (!SDL_GameControllerGetAttached(pController)) {
            SDL_GameControllerClose(pController);
            m_pGameControllers.erase(m_pGameControllers.begin() + i);
            m_GamePads.erase(m_GamePads.begin() + i);
            std::cout << "Controller Disconnected" << std::endl;
            --i; // Adjust index after removing the controller
        }
    }


    for (int i = 0; i < m_pGameControllers.size(); i++) {
        SDL_GameController *pController = m_pGameControllers[i];
        GamePad &gamePad = m_GamePads[i];

        for (int j = 0; j < SDL_CONTROLLER_BUTTON_MAX; j++) {
            gamePad.buttons[j] = SDL_GameControllerGetButton(pController, (SDL_GameControllerButton) j);
        }

        for (int j = 0; j < SDL_CONTROLLER_AXIS_MAX; j++) {
            gamePad.axis[j] = SDL_GameControllerGetAxis(pController, (SDL_GameControllerAxis) j);
        }
    }
}

bool GamePadController::IsButtonDown(Controllers controller, int button) const {
    return m_GamePads[controller].buttons[button];
}

bool GamePadController::IsButtonUp(Controllers controller, int button) const {
    return !m_GamePads[controller].buttons[button];
}

float GamePadController::GetAxis(Controllers controller, int axis) const {
    return m_GamePads[controller].axis[axis];
}


