#include "game/modulegame.hpp"

#include "core/jail/jail_audio.hpp"
#include "core/jail/jdraw8.hpp"
#include "core/jail/jfile.hpp"
#include "core/jail/jgame.hpp"
#include "core/jail/jinput.hpp"

ModuleGame::ModuleGame() {
    this->gfx = JD8_LoadSurface(info::pepe_activat ? "frames2.gif" : "frames.gif");
    JG_SetUpdateTicks(10);

    this->sam = new Prota(this->gfx);
    this->mapa = new Mapa(this->gfx, this->sam);
    this->marcador = new Marcador(this->gfx, this->sam);
    if (info::num_piramide == 2) {
        this->bola = new Bola(this->gfx, this->sam);
    } else {
        this->bola = NULL;
    }
    this->momies = NULL;

    this->final = 0;
    this->iniciarMomies();
}

ModuleGame::~ModuleGame(void) {
    JD8_FadeOut();

    if (this->bola != NULL) delete this->bola;
    if (this->momies != NULL) {
        this->momies->clear();
        delete this->momies;
    }
    delete this->marcador;
    delete this->mapa;
    delete this->sam;

    JD8_FreeSurface(this->gfx);
}

int ModuleGame::Go() {
    this->Draw();

    const char* music = info::num_piramide == 3 ? "00000008.ogg" : (info::num_piramide == 2 ? "00000007.ogg" : (info::num_piramide == 6 ? "00000002.ogg" : "00000006.ogg"));
    const char* current_music = JA_GetMusicFilename();
    if ((JA_GetMusicState() != JA_MUSIC_PLAYING) || !(strcmp(music, current_music) == 0)) {
        int size;
        char* buffer = file_getfilebuffer(music, size);
        JA_PlayMusic(JA_LoadMusic((Uint8*)buffer, size, music));
    }

    JD8_FadeToPal(JD8_LoadPalette(info::pepe_activat ? "frames2.gif" : "frames.gif"));

    while (this->final == 0 && !JG_Quitting()) {
        this->Draw();
        this->Update();
    }

    // JS_FadeOutMusic();

    if (this->final == 1) {
        info::num_habitacio++;
        if (info::num_habitacio == 6) {
            info::num_habitacio = 1;
            info::num_piramide++;
        }
        if (info::num_piramide == 6 && info::num_habitacio == 2) info::num_piramide++;
    } else if (this->final == 2) {
        info::num_piramide = 100;
    }

    if (JG_Quitting()) {
        return -1;
    } else {
        if (info::num_habitacio == 1 || info::num_piramide == 100 || info::num_piramide == 7) {
            return 1;
        } else {
            return 0;
        }
    }
}

void ModuleGame::Draw() {
    this->mapa->draw();
    this->marcador->draw();
    this->sam->draw();
    if (this->momies != NULL) this->momies->draw();
    if (this->bola != NULL) this->bola->draw();

    JD8_Flip();
}

void ModuleGame::Update() {
    if (JG_ShouldUpdate()) {
        JI_Update();

        this->final = this->sam->update();
        if (this->momies != NULL && this->momies->update()) {
            Momia* seguent = this->momies->next;
            delete this->momies;
            this->momies = seguent;
            info::momies--;
        }
        if (this->bola != NULL) this->bola->update();
        this->mapa->update();
        if (this->mapa->novaMomia()) {
            if (this->momies != NULL) {
                this->momies->insertar(new Momia(this->gfx, true, 0, 0, this->sam));
                info::momies++;
            } else {
                this->momies = new Momia(this->gfx, true, 0, 0, this->sam);
                info::momies++;
            }
        }

        if (JI_CheatActivated("reviu")) info::vida = 5;
        if (JI_CheatActivated("alone")) {
            if (this->momies != NULL) {
                this->momies->clear();
                delete this->momies;
                this->momies = NULL;
                info::momies = 0;
            }
        }
        if (JI_CheatActivated("obert")) {
            for (int i = 0; i < 16; i++) {
                this->mapa->tombes[i].costat[0] = true;
                this->mapa->tombes[i].costat[1] = true;
                this->mapa->tombes[i].costat[2] = true;
                this->mapa->tombes[i].costat[3] = true;
                this->mapa->comprovaCaixa(i);
            }
        }

        if (JI_KeyPressed(SDL_SCANCODE_ESCAPE)) {
            JG_QuitSignal();
        }
    }
}

void ModuleGame::iniciarMomies() {
    if (info::num_habitacio == 1) {
        info::momies = 1;
    } else {
        info::momies++;
    }
    if (info::num_piramide == 6) info::momies = 8;

    int x = 20;
    int y = 170;
    bool dimonis = info::num_piramide == 6;
    for (int i = 0; i < info::momies; i++) {
        if (this->momies == NULL) {
            this->momies = new Momia(this->gfx, dimonis, x, y, this->sam);
        } else {
            this->momies->insertar(new Momia(this->gfx, dimonis, x, y, this->sam));
        }
        x += 65;
        if (x == 345) {
            x = 20;
            y -= 35;
        }
    }
}
