#include "formproject.h"
#include "ui_formproject.h"
#include "projectdao.h"
#include <QMessageBox>
#include <QSqlQueryModel>

formProject::formProject(QWidget *parent)
    : QMainWindow(parent), ui(new Ui::formProject), m_isNew(true)
{
    ui->setupUi(this);
    setupConnections();
    clearForm();

    // Populate state combo
    ui->stateCombo->addItems(ProjectDAO::getStates());
    ui->docTypeCombo->addItems({"PR", "FI", "FC", "OT"});
}

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

void formProject::setupConnections()
{
    connect(ui->saveButton, &QPushButton::clicked, this, &formProject::saveProject);
    connect(ui->addDocButton, &QPushButton::clicked, this, &formProject::addDocument);
    connect(ui->removeDocButton, &QPushButton::clicked, this, &formProject::removeDocument);
    connect(ui->addBudgetButton, &QPushButton::clicked, this, &formProject::addBudgetLine);
    connect(ui->removeBudgetButton, &QPushButton::clicked, this, &formProject::removeBudgetLine);
}

void formProject::setNewMode()
{
    m_isNew = true;
    m_project = Project();
    clearForm();
    ui->codeEdit->setEnabled(true);
    ui->codeEdit->setFocus();
}

void formProject::clearForm()
{
    ui->codeEdit->clear();
    ui->titleEdit->clear();
    ui->customerCodeEdit->clear();
    ui->customerNameEdit->clear();
    ui->startDateEdit->setDate(QDate::currentDate());
    ui->durationDateEdit->setDate(QDate::currentDate().addYears(1));
    ui->stateCombo->setCurrentIndex(0);
    ui->contactEdit->clear();
    ui->address1Edit->clear();
    ui->address2Edit->clear();
    ui->postcodeEdit->clear();
    ui->cityEdit->clear();
    ui->phoneEdit->clear();
    ui->mobileEdit->clear();
    ui->emailEdit->clear();
}

void formProject::loadProject(const QString &code)
{
    m_isNew = false;
    m_project = ProjectDAO::getByCode(code);
    ui->codeEdit->setEnabled(false);
    populateForm();
    refreshDocuments();
    refreshBudget();
    refreshFinancialSummary();
}

void formProject::populateForm()
{
    ui->codeEdit->setText(m_project.code);
    ui->titleEdit->setText(m_project.title);
    ui->customerCodeEdit->setText(m_project.customerCode);
    ui->customerNameEdit->setText(m_project.customerName);
    ui->startDateEdit->setDate(m_project.startDate);
    ui->durationDateEdit->setDate(m_project.duration);
    int stateIdx = ui->stateCombo->findText(m_project.state);
    if (stateIdx >= 0) ui->stateCombo->setCurrentIndex(stateIdx);
    ui->contactEdit->setText(m_project.contact);
    ui->address1Edit->setText(m_project.address1);
    ui->address2Edit->setText(m_project.address2);
    ui->postcodeEdit->setText(m_project.postcode);
    ui->cityEdit->setText(m_project.city);
    ui->phoneEdit->setText(m_project.phone);
    ui->mobileEdit->setText(m_project.mobile);
    ui->emailEdit->setText(m_project.email);
}

void formProject::readForm()
{
    m_project.code = ui->codeEdit->text();
    m_project.title = ui->titleEdit->text();
    m_project.customerCode = ui->customerCodeEdit->text();
    m_project.customerName = ui->customerNameEdit->text();
    m_project.startDate = ui->startDateEdit->date();
    m_project.duration = ui->durationDateEdit->date();
    m_project.state = ui->stateCombo->currentText();
    m_project.contact = ui->contactEdit->text();
    m_project.address1 = ui->address1Edit->text();
    m_project.address2 = ui->address2Edit->text();
    m_project.postcode = ui->postcodeEdit->text();
    m_project.city = ui->cityEdit->text();
    m_project.phone = ui->phoneEdit->text();
    m_project.mobile = ui->mobileEdit->text();
    m_project.email = ui->emailEdit->text();
}

void formProject::saveProject()
{
    readForm();

    if (m_project.code.isEmpty() || m_project.title.isEmpty()) {
        QMessageBox::warning(this, tr("Aviso"), tr("Código y Título son obligatorios."));
        return;
    }

    bool ok;
    if (m_isNew) {
        if (ProjectDAO::exists(m_project.code)) {
            QMessageBox::warning(this, tr("Error"), tr("Ya existe un proyecto con ese código."));
            return;
        }
        ok = ProjectDAO::create(m_project);
    } else {
        ok = ProjectDAO::update(m_project);
    }

    if (ok) {
        QMessageBox::information(this, tr("Éxito"), tr("Proyecto guardado correctamente."));
        m_isNew = false;
        ui->codeEdit->setEnabled(false);
        emit projectSaved();
    } else {
        QMessageBox::critical(this, tr("Error"), tr("No se pudo guardar el proyecto."));
    }
}

void formProject::onStateChanged(int index)
{
    Q_UNUSED(index);
}

// --------------- Documents tab ---------------

void formProject::addDocument()
{
    if (m_project.code.isEmpty()) {
        QMessageBox::warning(this, tr("Aviso"), tr("Guarda el proyecto primero."));
        return;
    }
    QString docType = ui->docTypeCombo->currentText();
    QString docCode = ui->docCodeEdit->text();
    if (docCode.isEmpty()) {
        QMessageBox::warning(this, tr("Aviso"), tr("Introduce el código del documento."));
        return;
    }
    if (ProjectDAO::attachDocument(m_project.code, docType, docCode)) {
        ui->docCodeEdit->clear();
        refreshDocuments();
    } else {
        QMessageBox::critical(this, tr("Error"), tr("No se pudo adjuntar el documento."));
    }
}

void formProject::removeDocument()
{
    QModelIndex idx = ui->documentsTable->currentIndex();
    if (!idx.isValid()) {
        QMessageBox::information(this, tr("Info"), tr("Selecciona un documento."));
        return;
    }
    int row = idx.row();
    int docId = ui->documentsTable->model()->data(ui->documentsTable->model()->index(row, 0)).toInt();
    if (ProjectDAO::removeDocument(docId)) {
        refreshDocuments();
    } else {
        QMessageBox::critical(this, tr("Error"), tr("No se pudo eliminar el documento."));
    }
}

void formProject::refreshDocuments()
{
    QSqlQueryModel *model = new QSqlQueryModel(this);
    QSqlQuery query;
    query.prepare("SELECT ID, DOC_TYPE, DOC_CODE FROM PROJECTDOCUMENT WHERE PROJECT_CODE = ?");
    query.addBindValue(m_project.code);
    query.exec();
    model->setQuery(query);
    model->setHeaderData(0, Qt::Horizontal, tr("ID"));
    model->setHeaderData(1, Qt::Horizontal, tr("Tipo"));
    model->setHeaderData(2, Qt::Horizontal, tr("Código"));
    ui->documentsTable->setModel(model);
    ui->documentsTable->setColumnHidden(0, true);
}

// --------------- Budget tab ---------------

void formProject::addBudgetLine()
{
    if (m_project.code.isEmpty()) {
        QMessageBox::warning(this, tr("Aviso"), tr("Guarda el proyecto primero."));
        return;
    }
    QString concept = ui->budgetConceptEdit->text();
    double amount = ui->budgetAmountSpin->value();
    if (concept.isEmpty() || amount <= 0) {
        QMessageBox::warning(this, tr("Aviso"), tr("Introduce concepto y cantidad."));
        return;
    }
    if (ProjectDAO::addBudgetLine(m_project.code, concept, amount)) {
        ui->budgetConceptEdit->clear();
        ui->budgetAmountSpin->setValue(0);
        refreshBudget();
        refreshFinancialSummary();
    } else {
        QMessageBox::critical(this, tr("Error"), tr("No se pudo añadir la línea de presupuesto."));
    }
}

void formProject::removeBudgetLine()
{
    QModelIndex idx = ui->budgetTable->currentIndex();
    if (!idx.isValid()) {
        QMessageBox::information(this, tr("Info"), tr("Selecciona una línea de presupuesto."));
        return;
    }
    int row = idx.row();
    int budgetId = ui->budgetTable->model()->data(ui->budgetTable->model()->index(row, 0)).toInt();
    if (ProjectDAO::removeBudgetLine(budgetId)) {
        refreshBudget();
        refreshFinancialSummary();
    } else {
        QMessageBox::critical(this, tr("Error"), tr("No se pudo eliminar la línea."));
    }
}

void formProject::refreshBudget()
{
    QSqlQueryModel *model = new QSqlQueryModel(this);
    QSqlQuery query;
    query.prepare("SELECT ID, CONCEPT, AMOUNT FROM PROJECTBUDGET WHERE PROJECT_CODE = ?");
    query.addBindValue(m_project.code);
    query.exec();
    model->setQuery(query);
    model->setHeaderData(0, Qt::Horizontal, tr("ID"));
    model->setHeaderData(1, Qt::Horizontal, tr("Concepto"));
    model->setHeaderData(2, Qt::Horizontal, tr("Cantidad"));
    ui->budgetTable->setModel(model);
    ui->budgetTable->setColumnHidden(0, true);
}

void formProject::refreshFinancialSummary()
{
    QPair<double, double> summary = ProjectDAO::getFinancialSummary(m_project.code);
    ui->totalBudgetLabel->setText(QString::number(summary.first, 'f', 2) + " €");
    ui->totalCostLabel->setText(QString::number(summary.second, 'f', 2) + " €");
    ui->balanceLabel->setText(QString::number(summary.first - summary.second, 'f', 2) + " €");
}