#include "gui.h"
#include "ui_gui.h"
#include <QMouseEvent>
#include <QFileDialog>
#include <QtConcurrent/QtConcurrent>
#include <QMessageBox>

#include <LotroDat.h>
using namespace LOTRO_DAT;

GUI::GUI(QWidget *parent) :
    QMainWindow(parent, Qt::Window | Qt::FramelessWindowHint),
    ui(new Ui::GUI)
{
    state = "free";
    ui->setupUi(this);
    ui->Progress->hide();

    setWindowTitle("Gi1dor's font restorator");
    setWindowIcon(QIcon(":/data/icon.ico"));

    connect(this, SIGNAL(update_percent(int)), this, SLOT(on_update_percent(int)));
    connect(this, SIGNAL(update_label(QString)), this, SLOT(on_update_label(QString)));
    connect(this, SIGNAL(patch_finished(QString, bool)), this, SLOT(on_patch_finished(QString, bool)));

}

GUI::~GUI()
{
    delete ui;
}

void GUI::closeEvent(QCloseEvent *e){
    if (state != "free")
        e->ignore();
}

void GUI::mouseMoveEvent( QMouseEvent* e ) {
    if( e->buttons() | Qt::LeftButton ) {
        QPoint pt=mapFromGlobal(QCursor::pos());
        QWidget* child=childAt(pt);
        if (child == 0) {
            setGeometry(pos().x() + ( e->x() - dx ), pos().y() + ( e->y() - dy ), width(), height());
            return;
        }
        QString cname = child->metaObject()->className();
        if (cname != "QPushButton" && cname != "QComboBox"){ // отключаем перетягивание при наведение на активные элементы
            setGeometry(pos().x() + ( e->x() - dx ), pos().y() + ( e->y() - dy ), width(), height());
        } else {
            dx = e->x();
            dy = e->y();
        }
    }
}

void GUI::mousePressEvent( QMouseEvent* e ) {
    if( e->button() == Qt::LeftButton ) {
        dx = e->x();
        dy = e->y();
        setCursor( Qt::OpenHandCursor );
    }
}

void GUI::mouseReleaseEvent( QMouseEvent* e ) {
    if( e->button() == Qt::LeftButton ) {
        setCursor( Qt::ArrowCursor );
        dx = e->x();
        dy = e->y();
    }
}

void GUI::on_close_btn_clicked()
{
    if (state == "free")
        QApplication::exit(0);
}

void GUI::on_fileDialogButton_clicked()
{
    datFilePath = QFileDialog::getOpenFileName(0, "Открыть .dat файл", "", "client_local_English.dat");
}

void GUI::on_performAction_clicked()
{
    ui->Progress->show();
    ui->performAction->hide();
    QFuture<void> future = QtConcurrent::run([=]() {
        startPatching();
    });
}

void GUI::startPatching() {
    state = "busy";
    DatFile file;
    emit update_percent(30);
    emit update_label("Открываем .dat файл...");

    if (file.InitDatFile(datFilePath.toStdString(), 0) < 0) {
        emit patch_finished("Неудача! Не могу открыть файл " + datFilePath
                            + ". Проверьте, что путь правильный и выключены лаунчер игры и русификатор!"
                            , false);
        return;
    }

    emit update_label("Открываем патч...");
    emit update_percent(70);

    Database patch;
    if (!patch.InitDatabase("kfbIUYBKrjhsb.kbd")) {
        emit patch_finished("Неудача! Не могу открыть патч шрифтов!", false);
        return;
    }

    emit update_label("Проводим обновление...");
    file.PatchAllDatabase(&patch);

    emit update_percent(90);
    emit update_label("Завершаем обновление...");
    file.CloseDatFile();

    emit patch_finished("Успех! Проверьте в игре, что шрифты успешно восстановились!", true);
}

void GUI::on_patch_finished(QString result, bool ok) {
    ui->Progress->hide();
    ui->performAction->show();
    state = "free";
    message.setText(result);
    message.setIcon(ok ? QMessageBox::Information : QMessageBox::Critical);
    message.show();
}

void GUI::on_update_percent(int newPercent) {
    ui->progressBar->setValue(newPercent);
}

void GUI::on_update_label(QString label) {
    ui->processLabel->setText(label);
}
