RecordControlApplication/Widget.cpp

332 lines
9.9 KiB
C++
Raw Normal View History

2024-01-18 15:41:43 +08:00
#include "Widget.h"
#include "Channel.h"
#include "Config.h"
#include "TcpServer.h"
#include "ui_Widget.h"
#include <QDebug>
#include <QDir>
#include <QScrollBar>
extern char* VideoPath;
extern QList<Channel*> channelList;
extern Widget::Widget(QWidget* parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
menu = new Menu(this);
menu->hide();
progressBar = new ProgressBar(this);
progressBar->hide();
2024-01-18 15:41:43 +08:00
// set window background transparent
QPalette pal = palette();
pal.setBrush(QPalette::Base, Qt::transparent);
setPalette(pal);
setAttribute(Qt::WA_TranslucentBackground, true);
// set list no scroll bar
ui->listWidget->horizontalScrollBar()->hide();
ui->listWidget->verticalScrollBar()->hide();
ui->listWidget->hide();
// serial port
initSerialPort();
// init command map
initCommandMap();
// get playback position each 0.5s
progressTimer = new QTimer();
progressTimer->setInterval(500);
connect(progressTimer, SIGNAL(timeout()), this, SLOT(onProgressTimeout()));
for (Channel* chn : channelList) {
connect(chn, SIGNAL(playEnd()), this, SLOT(onPlayEnd()));
connect(chn, SIGNAL(signalInputed(QString, int, int)), this, SLOT(onSignalInputed(QString, int, int)));
}
2024-01-18 15:41:43 +08:00
}
Widget::~Widget()
{
serialPort->close();
delete ui;
}
/**
* @brief open serial port and link the signals and slots
*/
void Widget::initSerialPort()
{
// timer used to reopen serial port
timer = new QTimer();
timer->setInterval(3000);
2024-01-18 15:41:43 +08:00
timer->stop();
// serialport
serialPort = new QSerialPort();
serialPort->setPortName("ttyAMA2");
serialPort->setBaudRate(QSerialPort::Baud115200);
serialPort->setDataBits(QSerialPort::Data8);
serialPort->setParity(QSerialPort::NoParity);
serialPort->setStopBits(QSerialPort::OneStop);
serialPort->setFlowControl(QSerialPort::NoFlowControl);
if (serialPort->open(QIODevice::ReadWrite)) {
qDebug() << "open serial port: /dev/ttyAMA2 success";
} else {
qDebug() << "open serial port: /dev/ttyAMA2 failed, ready to retry...";
timer->start();
}
connect(serialPort, SIGNAL(error(QSerialPort::SerialPortError)), this, SLOT(onSerialError(QSerialPort::SerialPortError)));
connect(serialPort, SIGNAL(readyRead()), this, SLOT(onReadyRead()));
}
/**
* @brief get the video list of current channel, and show
*/
void Widget::showPlayList()
{
// find the videos in dictionary "/root/usb/video"
QString dirPath = QString("%1/%2").arg(VideoPath).arg(curSelectChannel);
QStringList files = this->getFileList(dirPath);
2024-01-18 15:41:43 +08:00
ui->listWidget->clear();
// append fileList to qlistwidget and show
for (QString& file : files) {
2024-01-18 15:41:43 +08:00
QListWidgetItem* item = new QListWidgetItem(file);
ui->listWidget->addItem(item);
}
ui->listWidget->show();
ui->listWidget->setCurrentRow(0);
}
/**
* @brief try to reopen serial port
*/
void Widget::onTimeout()
{
timer->stop();
bool ret = serialPort->open(QIODevice::ReadWrite);
// if open failed, then start timer and reopen
if (!ret) {
qDebug() << "reopen serial port: /dev/ttyAMA2 success";
timer->start();
} else {
qDebug() << "reopen serial port: /dev/ttyAMA2 failed, ready to retry...";
}
}
void Widget::onProgressTimeout()
{
Channel* chn = Config::findChannelByName(curSelectChannel);
int pos = chn->file->invoke("getPosition").toInt() / 1000;
progressBar->setCurrent(pos);
}
/**
* @brief call it when input hdmi signal
* @param name
* @param width
* @param height
*/
void Widget::onSignalInputed(QString name, int width, int height)
{
if (name == "HDMI-A") {
this->setFixedSize(QSize(width, height));
qDebug() << QString("set windows size: %1x%2").arg(width).arg(height);
}
}
2024-01-18 15:41:43 +08:00
/**
* @brief handling error
* @param error
*/
void Widget::onSerialError(QSerialPort::SerialPortError error)
{
if (error == QSerialPort::ResourceError) {
qDebug() << "serial port break, try to reopen";
serialPort->close();
timer->start();
}
}
/**
* @brief map command from string to int
*/
void Widget::initCommandMap()
{
commandMap.insert("A1", Playback);
commandMap.insert("A2", Next);
commandMap.insert("A3", Previous);
commandMap.insert("A4", Forward);
commandMap.insert("A5", Back);
commandMap.insert("A6", Pause);
commandMap.insert("A7", Return);
commandMap.insert("A8", Enter);
}
/**
* @brief receive data from serial port, and handle it
*/
void Widget::onReadyRead()
{
serialPort->waitForReadyRead(100);
QString data = serialPort->readLine();
if (!commandMap.contains(data)) {
qDebug() << QString("receive unkown command %1 from serial port: /dev/ttyAMA2").arg(data);
return;
}
Command cmd = commandMap.value(data);
switch (cmd) {
case Playback: {
if (menu->isVisible())
return;
menu->show();
}
case Previous: {
// if show menu, then switch menu select
if (menu->isVisible()) {
menu->setCurChannel("HDMI-A");
}
// if menu hide, then select previous of listwidget
else {
int curRow = ui->listWidget->currentRow();
if (curRow == 0)
curRow = ui->listWidget->count();
ui->listWidget->setCurrentRow(curRow - 1);
}
break;
}
case Next: {
if (menu->isVisible()) {
menu->setCurChannel("HDMI-B");
} else {
int curRow = ui->listWidget->currentRow();
if (curRow == ui->listWidget->count() - 1) {
curRow = -1;
}
ui->listWidget->setCurrentRow(curRow + 1);
}
break;
}
case Forward:
if (isPlayback) {
Channel* chn = Config::findChannelByName(curSelectChannel);
2024-01-18 15:41:43 +08:00
chn->forward();
progressBar->showMax();
2024-01-18 15:41:43 +08:00
}
break;
case Back:
if (isPlayback) {
Channel* chn = Config::findChannelByName(curSelectChannel);
2024-01-18 15:41:43 +08:00
chn->back();
progressBar->showMax();
2024-01-18 15:41:43 +08:00
}
break;
case Pause:
if (isPlayback) {
Channel* chn = Config::findChannelByName(curSelectChannel);
2024-01-18 15:41:43 +08:00
chn->togglePause();
progressBar->showMax();
if (chn->isPause) {
progressBar->setState(ProgressBar::Pause);
} else {
progressBar->setState(ProgressBar::Play);
}
2024-01-18 15:41:43 +08:00
}
break;
case Enter:
// if menu show, then hide menu and show play list
if (menu->isVisible()) {
curSelectChannel = menu->getCurChannel();
2024-01-18 15:41:43 +08:00
menu->hide();
showPlayList();
2024-01-19 09:04:21 +08:00
} else {
// if list widget show, then current channel playback and other channel play live
if (ui->listWidget->isVisible()) {
if (ui->listWidget->count() == 0)
return;
2024-01-19 09:04:21 +08:00
QString fileName = ui->listWidget->currentItem()->text();
Channel* channel = nullptr;
for (int i = 0; i < channelList.count(); i++) {
if (channelList.at(i)->channelName == curSelectChannel) {
2024-01-19 09:04:21 +08:00
channel = channelList.at(i);
}
if (channelList.at(i)->isPlayback) {
channelList.at(i)->startPlayLive();
}
2024-01-18 15:41:43 +08:00
}
2024-01-19 09:04:21 +08:00
if (channel) {
// play back and output hdmi
2024-01-19 09:04:21 +08:00
channel->startPlayback(fileName);
isPlayback = true;
// only show progressbar in HDMI-A(HDMI-OUT0)
if (channel->channelName == "HDMI-A") {
// show progress bar maximize
int duration = channel->getDuration(fileName) / 1000;
progressBar->setDuration(duration);
progressBar->setCurrent(0);
progressBar->show();
progressBar->showMax();
progressBar->setState(ProgressBar::Play);
// if timer is active, then restart timer
if (progressTimer->isActive()) {
progressTimer->stop();
progressTimer->start();
} else {
progressTimer->start();
}
curPlayChannel = curSelectChannel;
curFileName = fileName;
QString dirPath = QString("%1/%2").arg(VideoPath).arg(curPlayChannel);
fileList = this->getFileList(dirPath);
}
2024-01-18 15:41:43 +08:00
}
// ui->listWidget->hide();
2024-01-18 15:41:43 +08:00
}
}
break;
case Return:
if (menu->isVisible()) {
menu->hide();
}
if (isPlayback && !ui->listWidget->isVisible()) {
Channel* chn = Config::findChannelByName(curSelectChannel);
2024-01-18 15:41:43 +08:00
chn->startPlayLive();
progressBar->hide();
} else {
ui->listWidget->hide();
2024-01-18 15:41:43 +08:00
}
break;
default:
break;
}
}
/**
* @brief current play end and then play next video
*/
void Widget::onPlayEnd()
{
int index = fileList.indexOf(curFileName);
// cur video is last one of list, then refresh list
if (index == fileList.length() - 1) {
QString dirPath = QString("%1/%2").arg(VideoPath).arg(curPlayChannel);
this->getFileList(dirPath);
if (index == fileList.length() - 1) {
qDebug() << "no file to play";
return;
}
qDebug() << "refresh current play file list";
}
curFileName = fileList.at(index + 1);
Channel* chn = Config::findChannelByName(curPlayChannel);
if (chn)
chn->startPlayback(curFileName);
}