#include "MainWindow.h"

#include <QMessageBox>
#include <QVBoxLayout>
#include <QLabel>
#include <QScreen>
#include <QSettings>
#include <QPainter>

#include "NetClient.h"
#include "TokenRequest.h"

#include "ui_MainWindow.h"

MainWindow* s_instance = nullptr;

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    setWindowFlags(Qt::FramelessWindowHint);
    //setWindowFlags(windowFlags() | Qt::WindowStaysOnTopHint);
    ui->setupUi(this);

    move(0, 0);
    s_instance = this;

    QString settingPath = QApplication::applicationDirPath() + "/PhotoVideoPlayer/setting.ini";
    QSettings settings(settingPath, QSettings::IniFormat);
    m_defualtVideo = settings.value("DefaultVideoName").toString();
    qDebug() << "Default Video Name: " << m_defualtVideo;

    // 读取第二拍照视频名称
    m_photoVideo = settings.value("PhotoVideoName").toString();
    qDebug() << "Second Photo Video Name: " << m_photoVideo;

    int port = settings.value("port", 9529).toInt();
    qDebug() << "port: " << port;
    
    m_showImage = settings.value("showtime", 51).toInt() * 1000;
    qDebug() << "showtime: " << m_showImage;

    m_phototime = settings.value("phototime", 28).toInt() * 1000;
    qDebug() << "phototime: " << m_phototime; 
    
    m_photoOuttime = settings.value("photoouttime", 28).toInt() * 1000;
    qDebug() << "photoouttime: " << m_photoOuttime;

    m_aminationTime = settings.value("amimation", 2).toInt();
    qDebug() << "amimation: " << m_aminationTime;
    
    m_left2right = settings.value("left2right", 1).toInt();
    qDebug() << "left2right: " << m_left2right;

    m_roopPort = settings.value("roopPort", 9531).toInt();
    qDebug() << "roopPort: " << m_roopPort;
    
    m_paperIp = settings.value("paperIp", "127.0.0.1").toString();
    qDebug() << "paperIp: " << m_paperIp;

    m_paperPort = settings.value("paperPort", 9532).toInt();
    qDebug() << "paperPort: " << m_paperPort;

    m_netClient = new NetClient(this);
    if (!m_netClient->Start(port)) {
        QMessageBox::warning(this, tr("error"), tr("config failed"));
        exit(-1);
    }

    zmqClient_.ConnectToServer(QString("%1:%2").arg(m_paperIp).arg(m_paperPort));

    const QString videoPath = QApplication::applicationDirPath() + "/PhotoVideoPlayer/" + m_defualtVideo;

    QWidget* centerWidget = new QWidget(this);
    setCentralWidget(centerWidget);

    QVBoxLayout* layout = new QVBoxLayout(centerWidget);
    layout->setContentsMargins(0, 0, 0, 0);
    m_defaultImage.load(videoPath);
    
    connect(&vlcPlayer_, &VlcMediaPlayer::VideoDataOutput, this, &MainWindow::slotSetOneFrame, Qt::QueuedConnection);
    connect(&vlcPlayer_, &VlcMediaPlayer::Stopped, this, &MainWindow::OnStop);
    connect(&vlcPlayer_, &VlcMediaPlayer::TimeChanged, this, &MainWindow::OnPositionChanged);
    connect(&videoUpdate_, &QTimer::timeout, [this]() {update(); });
    videoUpdate_.start(30);

    m_photoDisplay = new PhotoDisplay(this);
    const QSize size = QApplication::primaryScreen()->availableSize();
    m_photoDisplay->resize(size);

    m_animation = new QPropertyAnimation(m_photoDisplay, "pos", this);
    m_animation->setDuration(m_aminationTime * 1000);
    m_animation->setEasingCurve(QEasingCurve::InOutQuad);
    m_tokenRequest = new TokenRequest(this);
}

MainWindow::~MainWindow() {
    m_netClient->Stop();
    delete ui;
    s_instance = nullptr;
}

MainWindow& MainWindow::Get() {
    return *s_instance;
}

void MainWindow::DisplayPhoto(const QString& fileName) {
    m_photoPath = fileName;
}

void MainWindow::SendHeaderPhoto(const QString& fileName) {
    m_photoHeaderPath = fileName;
}

void MainWindow::Tranform(const QByteArray& message) {
    if (m_trans) {
        zmqClient_.Send(message);
    }
    else {
        m_transMessage.append(message);
    }
}

void MainWindow::PlayDefualtVideo() {
    if (isPhotoing) {
        qDebug() << __FUNCTION__ << "play movie " << isPhotoing;
        return;
    }

    const QString videoPath = QApplication::applicationDirPath() + "/PhotoVideoPlayer/" + m_photoVideo;
    isPhotoing = vlcPlayer_.Play(videoPath);
    qDebug() << __FUNCTION__ << "play movie success:" << isPhotoing << ",path:" << videoPath;

    m_requestImg = false;
    m_photoImg = false;
    m_trans = false;
}


void MainWindow::closeEvent(QCloseEvent* event) {
    m_photoDisplay->close();
}

void MainWindow::mousePressEvent(QMouseEvent* event) {
  //  Play();
}

void MainWindow::keyReleaseEvent(QKeyEvent* event) {
    if (event->key() == Qt::Key_T) {
        setWindowFlags(windowFlags() | Qt::WindowStaysOnTopHint);
        show();
    }
    else if (event->key() == Qt::Key_D) {
        setWindowFlags(windowFlags() & ~Qt::WindowStaysOnTopHint);
        show();
    }
    QMainWindow::keyReleaseEvent(event);
}

void MainWindow::OnPositionChanged(qint64 position) {
    if (position > (m_showImage) && !m_requestImg) {
        m_requestImg = true;
        QPoint start, end;
        if (m_left2right) {
            start = QPoint(-m_photoDisplay->width(), 0);
            end = QPoint((size().width() - m_photoDisplay->width()) / 2, 0);
        } else {
            start = QPoint(width() + m_photoDisplay->width(), 0);
            end = QPoint((size().width() - m_photoDisplay->width()) / 2, 0);
        }
        m_photoDisplay->ShowPhoto(m_photoPath);
        m_animation->setStartValue(start); // 起始位置
        m_animation->setEndValue(end); // 结束位置
        m_animation->stop();
        m_animation->start();
    }

    if (position > (m_phototime) && !m_photoImg) {
        m_netClient->WriteMessage("photo");
        m_photoImg = true;
    }

    if (position > (m_photoOuttime) && !m_trans) {
        for (const auto& trans : m_transMessage) {
           // m_netClient->TransformMessage(trans);
            zmqClient_.Send(trans);
        }
        m_transMessage.clear();
        m_trans = true;
    }
}

void MainWindow::OnStop() {
    m_photoIng = false;
    isPhotoing = false;
    m_photoDisplay->hide();
    m_netClient->WriteMessage("finish");
}

void MainWindow::paintEvent(QPaintEvent* event) {
    QMainWindow::paintEvent(event);

    const QRect& r = rect();
    QPainter painter(this);
    if (!isPhotoing || videoImage_.isNull()) {
        painter.drawPixmap(r, m_defaultImage, m_defaultImage.rect());
        return;
    }

    painter.drawImage(r, videoImage_, videoImage_.rect());
}