#include "StatusInfo.h"

#include "ui_StatusInfo.h"
#include "Utilities.h"
#include <MegaApplication.h>

StatusInfo::StatusInfo(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::StatusInfo)
{
    ui->setupUi(this);

    mIsOverQuota = false;

    mScanningTimer.setSingleShot(false);
    mScanningTimer.setInterval(60);
    mScanningAnimationIndex = 1;
    connect(&mScanningTimer, SIGNAL(timeout()), this, SLOT(scanningAnimationStep()));
    ui->bIconState->setCursor(Qt::ArrowCursor);
}

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

void StatusInfo::setState(TRANSFERS_STATES state)
{
    this->mState = state;

    // By default
    auto iconStateToken = QString::fromUtf8("icon-primary");

    switch (this->mState)
    {
        case TRANSFERS_STATES::STATE_PAUSED:
        {
            if (mScanningTimer.isActive())
            {
                mScanningTimer.stop();
            }

            const QString statusText{tr("Paused")};
            ui->lStatusDesc->setToolTip(statusText);
            ui->lStatusDesc->setText(statusText);

            ui->bIconState->setProperty("state", QString::fromUtf8("paused"));

            break;
        }
        case TRANSFERS_STATES::STATE_UPDATED:
        {
            if (mScanningTimer.isActive())
            {
                mScanningTimer.stop();
            }

            if (mIsOverQuota)
            {
                const QString statusText{tr("Account full")};
                ui->lStatusDesc->setToolTip(statusText);
                ui->lStatusDesc->setText(statusText);

                ui->bIconState->setProperty("state", QString::fromUtf8("over_quota"));
                iconStateToken = QString::fromUtf8("support-error");
            }
            else
            {
                const QString statusText{tr("Up to date")};
                ui->lStatusDesc->setToolTip(statusText);
                ui->lStatusDesc->setText(statusText);

                ui->bIconState->setProperty("state", QString::fromUtf8("up_to_date"));
                iconStateToken = QString::fromUtf8("indicator-green");
            }

            break;
        }
        case TRANSFERS_STATES::STATE_SYNCING:
        {
            if (!mScanningTimer.isActive())
            {
                mScanningAnimationIndex = 1;
                mScanningTimer.start();
            }

            const QString statusText{tr("Syncing…")};
            ui->lStatusDesc->setToolTip(statusText);
            ui->lStatusDesc->setText(statusText);
            break;
        }
        case TRANSFERS_STATES::STATE_WAITING:
        {
            if (!mScanningTimer.isActive())
            {
                mScanningAnimationIndex = 1;
                mScanningTimer.start();
            }

            const QString statusText{tr("Waiting…")};
            ui->lStatusDesc->setToolTip(statusText);
            ui->lStatusDesc->setText(statusText);
            break;
        }
        case TRANSFERS_STATES::STATE_INDEXING:
        {
            if (!mScanningTimer.isActive())
            {
                mScanningAnimationIndex = 1;
                mScanningTimer.start();
            }

            const QString statusText{tr("Scanning…")};
            ui->lStatusDesc->setToolTip(statusText);
            ui->lStatusDesc->setText(statusText);
            break;
        }
        case TRANSFERS_STATES::STATE_TRANSFERRING:
        {
            if (!mScanningTimer.isActive())
            {
                mScanningAnimationIndex = 1;
                mScanningTimer.start();
            }

            const QString statusText{tr("Transferring…")};
            ui->lStatusDesc->setToolTip(statusText);
            ui->lStatusDesc->setText(statusText);
            break;
        }
        case TRANSFERS_STATES::STATE_FAILED:
        {
            if (mScanningTimer.isActive())
            {
                mScanningTimer.stop();
            }

            setFailedText();
            ui->bIconState->setProperty("state", QString::fromUtf8("failed"));
            iconStateToken = QString::fromUtf8("indicator-pink");

            break;
        }
        default:
            break;
    }

    ui->bIconState->setProperty(TOKEN_PROPERTIES::normalOff, iconStateToken);
    ui->bIconState->style()->polish(ui->bIconState);
}

void StatusInfo::update()
{
    switch (this->mState)
    {
    case TRANSFERS_STATES::STATE_FAILED:
    {
        setFailedText();
        break;
    }
    default:
        break;
    }
}

StatusInfo::TRANSFERS_STATES StatusInfo::getState()
{
    return mState;
}

void StatusInfo::setOverQuotaState(bool oq)
{
    mIsOverQuota = oq;
    setState(mState);
}

QIcon StatusInfo::scanningIcon(int index)
{
    return QIcon(QString::fromUtf8(":/activity_indicator_%1.svg").arg(index));
}

void StatusInfo::scanningAnimationStep()
{
    const auto scanningIconImages = 30;
    mScanningAnimationIndex = mScanningAnimationIndex % scanningIconImages;
    ++mScanningAnimationIndex;
    ui->bIconState->setProperty("state", QVariant());
    ui->bIconState->setIcon(scanningIcon(mScanningAnimationIndex));
}

void StatusInfo::setFailedText()
{
    auto transfersFailed(MegaSyncApp->getTransfersModel() ? MegaSyncApp->getTransfersModel()->failedTransfers() : 0);

    const QString statusText{QCoreApplication::translate("TransferManager","Issue found", "", static_cast<int>(transfersFailed))};
    ui->lStatusDesc->setToolTip(statusText);
    ui->lStatusDesc->setText(statusText);
}

bool StatusInfo::event(QEvent* event)
{
    if (event->type() == QEvent::LanguageChange)
    {
        ui->retranslateUi(this);
        setState(mState);
    }
    return QWidget::event(event);
}

void StatusInfo::setPropertyAndPropagateToChildren(const char* name, const QVariant& value)
{
    setProperty(name, value);
    auto children = this->children();
    for (auto child: children)
    {
        if (auto widget = dynamic_cast<QWidget*>(child))
        {
            widget->setProperty(name, value);
            widget->style()->unpolish(widget);
            widget->style()->polish(widget);
        }
    }
    style()->unpolish(this);
    style()->polish(this);
}
