diff --git a/images/style-mission.css b/images/style-mission.css index 63514226f45b4e81da8f0006e1e798c8f2c586d0..7a19cadb8dc9359eb150b320e7793fcc1ee73cc8 100644 --- a/images/style-mission.css +++ b/images/style-mission.css @@ -338,6 +338,7 @@ QProgressBar { padding: 2px; color: #DDDDDF; background-color: #111118; + height: 10px; } QProgressBar:horizontal { @@ -398,3 +399,28 @@ QDialog { QTabBar::tab:selected { border: 2px solid #379AC3; } + +QLabel { + background-color: transparent; +} + +QLabel#toolBarNameLabel { + font: bold 16px; + color: #3C7B9E; +} + +QLabel#toolBarModeLabel { + font: 12px; +} + +QLabel#toolBarStateLabel { + font: 12px; + color: #3C7B9E; +} + +QLabel#toolBarMessageLabel { + font: 12px; + font-style: italic; + color: #3C7B9E; +} + diff --git a/src/ui/MainWindow.cc b/src/ui/MainWindow.cc index 44eab9e50193672acc33f399718fa5a386fe3e2f..81d6c89d995f431650bc85e0e470961c73c61dd9 100644 --- a/src/ui/MainWindow.cc +++ b/src/ui/MainWindow.cc @@ -127,6 +127,15 @@ MainWindow::MainWindow(QWidget *parent): centerStack = new QStackedWidget(this); setCentralWidget(centerStack); + // Load Toolbar + toolBar = new QGCToolBar(this); + this->addToolBar(toolBar); + // Add actions + toolBar->addPerspectiveChangeAction(ui.actionOperatorsView); + toolBar->addPerspectiveChangeAction(ui.actionEngineersView); + toolBar->addPerspectiveChangeAction(ui.actionPilotsView); + toolBar->addPerspectiveChangeAction(ui.actionUnconnectedView); + buildCommonWidgets(); connectCommonWidgets(); @@ -181,14 +190,6 @@ MainWindow::MainWindow(QWidget *parent): fgLink = new QGCFlightGearLink(); fgLink->connectSimulation(); - // Load Toolbar - toolBar = new QGCToolBar(this); - this->addToolBar(toolBar); - // Add actions - toolBar->addPerspectiveChangeAction(ui.actionOperatorsView); - toolBar->addPerspectiveChangeAction(ui.actionEngineersView); - toolBar->addPerspectiveChangeAction(ui.actionPilotsView); - // Connect link if (autoReconnect) { @@ -408,7 +409,9 @@ void MainWindow::buildCommonWidgets() if (!logPlayerDockWidget) { logPlayerDockWidget = new QDockWidget(tr("MAVLink Log Player"), this); - logPlayerDockWidget->setWidget( new QGCMAVLinkLogPlayer(mavlink, this) ); + logPlayer = new QGCMAVLinkLogPlayer(mavlink, this); + toolBar->setLogPlayer(logPlayer); + logPlayerDockWidget->setWidget(logPlayer); logPlayerDockWidget->setObjectName("MAVLINK_LOG_PLAYER_DOCKWIDGET"); addTool(logPlayerDockWidget, tr("MAVLink Log Replay"), Qt::RightDockWidgetArea); } diff --git a/src/ui/MainWindow.h b/src/ui/MainWindow.h index 4795a25a99a652e983352b7de96052d3d9b8795a..c6b34f157f789e2115dd5dfe2e6e6fb8a5a66b83 100644 --- a/src/ui/MainWindow.h +++ b/src/ui/MainWindow.h @@ -75,6 +75,7 @@ This file is part of the QGROUNDCONTROL project #include "SlugsPadCameraControl.h" #include "UASControlParameters.h" #include "QGCFlightGearLink.h" +#include "QGCMAVLinkLogPlayer.h" class QGCMapTool; @@ -210,6 +211,17 @@ public slots: */ void showCentralWidget(); +public: + QGCMAVLinkLogPlayer* getLogPlayer() + { + return logPlayer; + } + + MAVLinkProtocol* getMAVLink() + { + return mavlink; + } + protected: MainWindow(QWidget *parent = 0); @@ -342,6 +354,7 @@ protected: QPointer toolBar; + QGCMAVLinkLogPlayer* logPlayer; // Popup widgets JoystickWidget* joystickWidget; diff --git a/src/ui/QGCMAVLinkLogPlayer.cc b/src/ui/QGCMAVLinkLogPlayer.cc index 3ba61fb1181ae31739b348837226fc5586398f49..e49b1f0e81f25e35b606b5a055fc66c79c375926 100644 --- a/src/ui/QGCMAVLinkLogPlayer.cc +++ b/src/ui/QGCMAVLinkLogPlayer.cc @@ -20,6 +20,7 @@ QGCMAVLinkLogPlayer::QGCMAVLinkLogPlayer(MAVLinkProtocol* mavlink, QWidget *pare loopCounter(0), mavlinkLogFormat(true), binaryBaudRate(57600), + isPlaying(false), ui(new Ui::QGCMAVLinkLogPlayer) { ui->setupUi(this); @@ -33,8 +34,7 @@ QGCMAVLinkLogPlayer::QGCMAVLinkLogPlayer(MAVLinkProtocol* mavlink, QWidget *pare // Setup buttons connect(ui->selectFileButton, SIGNAL(clicked()), this, SLOT(selectLogFile())); - connect(ui->pauseButton, SIGNAL(clicked()), this, SLOT(pause())); - connect(ui->playButton, SIGNAL(clicked()), this, SLOT(play())); + connect(ui->playButton, SIGNAL(clicked()), this, SLOT(playPauseToggle())); connect(ui->speedSlider, SIGNAL(valueChanged(int)), this, SLOT(setAccelerationFactorInt(int))); connect(ui->positionSlider, SIGNAL(valueChanged(int)), this, SLOT(jumpToSliderVal(int))); connect(ui->positionSlider, SIGNAL(sliderPressed()), this, SLOT(pause())); @@ -49,12 +49,37 @@ QGCMAVLinkLogPlayer::~QGCMAVLinkLogPlayer() delete ui; } +void QGCMAVLinkLogPlayer::playPause(bool enabled) +{ + if (enabled) + { + play(); + } + else + { + pause(); + } +} + +void QGCMAVLinkLogPlayer::playPauseToggle() +{ + if (isPlaying) + { + pause(); + } + else + { + play(); + } +} + void QGCMAVLinkLogPlayer::play() { - if (logFile.isOpen()) { - ui->pauseButton->setChecked(false); + if (logFile.isOpen()) + { ui->selectFileButton->setEnabled(false); - if (logLink) { + if (logLink) + { logLink->disconnect(); LinkManager::instance()->removeLink(logLink); delete logLink; @@ -62,9 +87,12 @@ void QGCMAVLinkLogPlayer::play() logLink = new MAVLinkSimulationLink(""); // Start timer - if (mavlinkLogFormat) { + if (mavlinkLogFormat) + { loopTimer.start(1); - } else { + } + else + { // Read len bytes at a time int len = 100; // Calculate the number of times to read 100 bytes per second @@ -73,7 +101,11 @@ void QGCMAVLinkLogPlayer::play() int interval = 1000 / ((binaryBaudRate / 10) / len); loopTimer.start(interval*accelerationFactor); } - } else { + isPlaying = true; + ui->playButton->setIcon(QIcon(":images/actions/media-playback-pause.svg")); + } + else + { ui->playButton->setChecked(false); QMessageBox msgBox; msgBox.setIcon(QMessageBox::Information); @@ -87,10 +119,12 @@ void QGCMAVLinkLogPlayer::play() void QGCMAVLinkLogPlayer::pause() { + isPlaying = false; loopTimer.stop(); - ui->playButton->setChecked(false); + ui->playButton->setIcon(QIcon(":images/actions/media-playback-start.svg")); ui->selectFileButton->setEnabled(true); - if (logLink) { + if (logLink) + { logLink->disconnect(); LinkManager::instance()->removeLink(logLink); delete logLink; @@ -101,34 +135,39 @@ void QGCMAVLinkLogPlayer::pause() bool QGCMAVLinkLogPlayer::reset(int packetIndex) { // Reset only for valid values - if (packetIndex >= 0 && packetIndex <= logFile.size() - (packetLen+timeLen)) { - + const unsigned int packetSize = timeLen + packetLen; + if (packetIndex >= 0 && packetIndex*packetSize <= logFile.size() - packetSize) + { bool result = true; pause(); loopCounter = 0; logFile.reset(); - if (!logFile.seek(packetIndex*(timeLen + packetLen))) { + + if (!logFile.seek(packetIndex*packetSize)) + { // Fallback: Start from scratch logFile.reset(); ui->logStatsLabel->setText(tr("Changing packet index failed, back to start.")); result = false; } - ui->pauseButton->setChecked(true); + ui->playButton->setIcon(QIcon(":images/actions/media-playback-start.svg")); ui->positionSlider->blockSignals(true); - int sliderVal = (packetIndex / (double)(logFile.size()/(packetLen+timeLen))) * (ui->positionSlider->maximum() - ui->positionSlider->minimum()); + int sliderVal = (packetIndex / (double)(logFile.size()/packetSize)) * (ui->positionSlider->maximum() - ui->positionSlider->minimum()); ui->positionSlider->setValue(sliderVal); ui->positionSlider->blockSignals(false); startTime = 0; return result; - } else { + } + else + { return false; } } void QGCMAVLinkLogPlayer::selectLogFile() { - QString fileName = QFileDialog::getOpenFileName(this, tr("Specify MAVLink log file name"), QDesktopServices::storageLocation(QDesktopServices::DesktopLocation), tr("MAVLink or Binary Logfile (*.mavlink *.bin)")); + QString fileName = QFileDialog::getOpenFileName(this, tr("Specify MAVLink log file name"), QDesktopServices::storageLocation(QDesktopServices::DesktopLocation), tr("MAVLink or Binary Logfile (*.mavlink *.bin *.log)")); loadLogFile(fileName); } @@ -141,14 +180,18 @@ void QGCMAVLinkLogPlayer::setAccelerationFactorInt(int factor) float f = factor+1.0f; f -= 50.0f; - if (f < 0.0f) { + if (f < 0.0f) + { accelerationFactor = 1.0f / (-f/2.0f); - } else { + } + else + { accelerationFactor = 1+(f/2.0f); } // Update timer interval - if (!mavlinkLogFormat) { + if (!mavlinkLogFormat) + { // Read len bytes at a time int len = 100; // Calculate the number of times to read 100 bytes per second @@ -167,22 +210,27 @@ void QGCMAVLinkLogPlayer::setAccelerationFactorInt(int factor) void QGCMAVLinkLogPlayer::loadLogFile(const QString& file) { // Check if logging is still enabled - if (mavlink->loggingEnabled()) { + if (mavlink->loggingEnabled()) + { mavlink->enableLogging(false); MainWindow::instance()->showInfoMessage(tr("MAVLink Logging Stopped during Replay"), tr("MAVLink logging has been stopped during the log replay. To re-enable logging, use the link properties in the communication menu.")); } // Ensure that the playback process is stopped - if (logFile.isOpen()) { + if (logFile.isOpen()) + { pause(); logFile.close(); } logFile.setFileName(file); - if (!logFile.open(QFile::ReadOnly)) { + if (!logFile.open(QFile::ReadOnly)) + { MainWindow::instance()->showCriticalMessage(tr("The selected logfile is unreadable"), tr("Please make sure that the file %1 is readable or select a different file").arg(file)); logFile.setFileName(""); - } else { + } + else + { QFileInfo logFileInfo(file); logFile.reset(); startTime = 0; @@ -191,7 +239,8 @@ void QGCMAVLinkLogPlayer::loadLogFile(const QString& file) // Select if binary or MAVLink log format is used mavlinkLogFormat = file.endsWith(".mavlink"); - if (mavlinkLogFormat) { + if (mavlinkLogFormat) + { // Get the time interval from the logfile QByteArray timestamp = logFile.read(timeLen); @@ -216,17 +265,21 @@ void QGCMAVLinkLogPlayer::loadLogFile(const QString& file) QString timelabel = tr("%1h:%2m:%3s").arg(hours, 2).arg(minutes, 2).arg(seconds, 2); ui->logStatsLabel->setText(tr("%2 MB, %3 packets, %4").arg(logFileInfo.size()/1000000.0f, 0, 'f', 2).arg(logFileInfo.size()/(MAVLINK_MAX_PACKET_LEN+sizeof(quint64))).arg(timelabel)); - } else { + } + else + { // Load in binary mode // Set baud rate if any present QStringList parts = logFileInfo.baseName().split("_"); - if (parts.count() > 1) { + if (parts.count() > 1) + { bool ok; int rate = parts.last().toInt(&ok); // 9600 baud to 100 MBit - if (ok && (rate > 9600 && rate < 100000000)) { + if (ok && (rate > 9600 && rate < 100000000)) + { // Accept this as valid baudrate binaryBaudRate = rate; } @@ -256,8 +309,10 @@ void QGCMAVLinkLogPlayer::jumpToSliderVal(int slidervalue) int packetIndex = (packetCount - 1) * (slidervalue / (double)(ui->positionSlider->maximum() - ui->positionSlider->minimum())); // Do only accept valid jumps - if (reset(packetIndex)) { - if (mavlinkLogFormat) { + if (reset(packetIndex)) + { + if (mavlinkLogFormat) + { ui->logStatsLabel->setText(tr("Jumped to packet %1").arg(packetIndex)); } } @@ -273,15 +328,18 @@ void QGCMAVLinkLogPlayer::jumpToSliderVal(int slidervalue) */ void QGCMAVLinkLogPlayer::logLoop() { - if (mavlinkLogFormat) { + if (mavlinkLogFormat) + { bool ok; // First check initialization - if (startTime == 0) { + if (startTime == 0) + { QByteArray startBytes = logFile.read(timeLen); // Check if the correct number of bytes could be read - if (startBytes.length() != timeLen) { + if (startBytes.length() != timeLen) + { ui->logStatsLabel->setText(tr("Error reading first %1 bytes").arg(timeLen)); MainWindow::instance()->showCriticalMessage(tr("Failed loading MAVLink Logfile"), tr("Error reading first %1 bytes from logfile. Got %2 instead of %1 bytes. Is the logfile readable?").arg(timeLen).arg(startBytes.length())); reset(); @@ -296,7 +354,8 @@ void QGCMAVLinkLogPlayer::logLoop() //qDebug() << "START TIME: " << startTime; // Check if these bytes could be correctly decoded - if (!ok) { + if (!ok) + { ui->logStatsLabel->setText(tr("Error decoding first timestamp, aborting.")); MainWindow::instance()->showCriticalMessage(tr("Failed loading MAVLink Logfile"), tr("Could not load initial timestamp from file %1. Is the file corrupted?").arg(logFile.fileName())); reset(); @@ -313,7 +372,8 @@ void QGCMAVLinkLogPlayer::logLoop() emit bytesReady(logLink, packet); // Check if reached end of file before reading next timestamp - if (chunk.length() < timeLen+packetLen || logFile.atEnd()) { + if (chunk.length() < timeLen+packetLen || logFile.atEnd()) + { // Reached end of file reset(); @@ -329,12 +389,15 @@ void QGCMAVLinkLogPlayer::logLoop() // This is the timestamp of the next packet quint64 time = *((quint64*)(rawTime.constData())); ok = true; - if (!ok) { + if (!ok) + { // Convert it to 64bit number QString status = tr("Time conversion error during log replay. Continuing.."); ui->logStatsLabel->setText(status); MainWindow::instance()->showStatusMessage(status); - } else { + } + else + { // Normal processing, passed all checks // start timer to match time offset between // this and next packet @@ -350,13 +413,18 @@ void QGCMAVLinkLogPlayer::logLoop() //qDebug() << "nextExecutionTime:" << nextExecutionTime << "QGC START TIME:" << currentStartTime << "LOG START TIME:" << startTime; - if (nextExecutionTime < 2) { + if (nextExecutionTime < 2) + { logLoop(); - } else { + } + else + { loopTimer.start(nextExecutionTime); } } - } else { + } + else + { // Binary format - read at fixed rate const int len = 100; QByteArray chunk = logFile.read(len); @@ -365,7 +433,8 @@ void QGCMAVLinkLogPlayer::logLoop() emit bytesReady(logLink, chunk); // Check if reached end of file before reading next timestamp - if (chunk.length() < len || logFile.atEnd()) { + if (chunk.length() < len || logFile.atEnd()) + { // Reached end of file reset(); @@ -380,7 +449,8 @@ void QGCMAVLinkLogPlayer::logLoop() // Update status label // Update progress bar - if (loopCounter % 40 == 0) { + if (loopCounter % 40 == 0) + { QFileInfo logFileInfo(logFile); int progress = (ui->positionSlider->maximum()-ui->positionSlider->minimum())*(logFile.pos()/static_cast(logFileInfo.size())); //qDebug() << "Progress:" << progress; @@ -394,7 +464,8 @@ void QGCMAVLinkLogPlayer::logLoop() void QGCMAVLinkLogPlayer::changeEvent(QEvent *e) { QWidget::changeEvent(e); - switch (e->type()) { + switch (e->type()) + { case QEvent::LanguageChange: ui->retranslateUi(this); break; diff --git a/src/ui/QGCMAVLinkLogPlayer.h b/src/ui/QGCMAVLinkLogPlayer.h index f79a02f3e6d57c194edbdf2da1dd3b6357eee65b..56ce8022e5f2d017a410c28a868cadd57e0b7681 100644 --- a/src/ui/QGCMAVLinkLogPlayer.h +++ b/src/ui/QGCMAVLinkLogPlayer.h @@ -29,6 +29,10 @@ public: ~QGCMAVLinkLogPlayer(); public slots: + /** @brief Toggle between play and pause */ + void playPauseToggle(); + /** @brief Play / pause the log */ + void playPause(bool play); /** @brief Replay the logfile */ void play(); /** @brief Pause the logfile */ @@ -64,6 +68,7 @@ protected: int loopCounter; bool mavlinkLogFormat; int binaryBaudRate; + bool isPlaying; static const int packetLen = MAVLINK_MAX_PACKET_LEN; static const int timeLen = sizeof(quint64); void changeEvent(QEvent *e); diff --git a/src/ui/QGCMAVLinkLogPlayer.ui b/src/ui/QGCMAVLinkLogPlayer.ui index 3dd76b807acb03aba7672eda073a68d854a01f53..48427ca3c8b2e3e7bc475d94b08afe06f7d103c4 100644 --- a/src/ui/QGCMAVLinkLogPlayer.ui +++ b/src/ui/QGCMAVLinkLogPlayer.ui @@ -75,32 +75,6 @@ - - - - Pause the logfile - - - Pause the logfile - - - Pause the logfile - - - ... - - - - :/images/actions/media-playback-pause.svg:/images/actions/media-playback-pause.svg - - - true - - - true - - - @@ -117,7 +91,23 @@ - + + + + 10000 + + + 100 + + + false + + + Qt::Horizontal + + + + Start to replay the logfile @@ -132,7 +122,7 @@ ... - + :/images/actions/media-playback-start.svg:/images/actions/media-playback-start.svg @@ -140,26 +130,10 @@ - - - - 10000 - - - 100 - - - false - - - Qt::Horizontal - - - - + diff --git a/src/ui/QGCToolBar.cc b/src/ui/QGCToolBar.cc index e041c5b6eaaba0dd22955f8fd75fb6fc7b73189e..daac752ee24084e2bf4e934ce4db83e45b9cefff 100644 --- a/src/ui/QGCToolBar.cc +++ b/src/ui/QGCToolBar.cc @@ -25,6 +25,7 @@ This file is part of the QGROUNDCONTROL project #include #include "QGCToolBar.h" #include "UASManager.h" +#include "MainWindow.h" QGCToolBar::QGCToolBar(QWidget *parent) : QToolBar(parent), @@ -33,14 +34,93 @@ QGCToolBar::QGCToolBar(QWidget *parent) : mav(NULL) { setObjectName("QGC_TOOLBAR"); - createCustomWidgets(); + + toggleLoggingAction = new QAction(QIcon(":"), "Logging", this); + toggleLoggingAction->setCheckable(true); + logReplayAction = new QAction(QIcon(":"), "Replay", this); + logReplayAction->setCheckable(true); + + addSeparator(); + + addAction(toggleLoggingAction); + addAction(logReplayAction); + + // CREATE TOOLBAR ITEMS + // Add internal actions + // Add MAV widget + symbolButton = new QToolButton(this); + toolBarNameLabel = new QLabel("------", this); + toolBarModeLabel = new QLabel("------", this); + toolBarModeLabel->setStyleSheet("QLabel { margin: 0px 4px; font: 16px; color: #3C7B9E; }"); + toolBarStateLabel = new QLabel("------", this); + toolBarStateLabel->setStyleSheet("QLabel { margin: 0px 4px; font: 16px; color: #FEC654; }"); + toolBarWpLabel = new QLabel("---", this); + toolBarDistLabel = new QLabel("--- ---- m", this); + toolBarMessageLabel = new QLabel("No system messages.", this); + toolBarBatteryBar = new QProgressBar(this); + toolBarBatteryBar->setStyleSheet("QProgressBar:horizontal { margin: 0px 8px; border: 1px solid #4A4A4F; border-radius: 4px; text-align: center; padding: 2px; color: #111111; background-color: #111118; height: 10px; } QProgressBar:horizontal QLabel { font-size: 9px; color: #111111; } QProgressBar::chunk { background-color: green; }"); + toolBarBatteryBar->setMinimum(0); + toolBarBatteryBar->setMaximum(100); + toolBarBatteryBar->setMaximumWidth(200); + //symbolButton->setIcon(":"); + symbolButton->setStyleSheet("QWidget { background-color: #050508; color: #DDDDDF; background-clip: border; } QToolButton { font-weight: bold; font-size: 12px; border: 0px solid #999999; border-radius: 5px; min-width:22px; max-width: 22px; min-height: 22px; max-height: 22px; padding: 0px; margin: 0px 0px 0px 20px; background-color: none; }"); + addWidget(symbolButton); + addWidget(toolBarNameLabel); + addWidget(toolBarModeLabel); + addWidget(toolBarStateLabel); + addWidget(toolBarBatteryBar); + addWidget(toolBarWpLabel); + addWidget(toolBarDistLabel); + addWidget(toolBarMessageLabel); + //addWidget(new QSpacerItem(20, 0, QSizePolicy::Expanding)); + + // DONE INITIALIZING BUTTONS + setActiveUAS(UASManager::instance()->getActiveUAS()); connect(UASManager::instance(), SIGNAL(activeUASSet(UASInterface*)), this, SLOT(setActiveUAS(UASInterface*))); } +void QGCToolBar::setLogPlayer(QGCMAVLinkLogPlayer* player) +{ + connect(toggleLoggingAction, SIGNAL(triggered(bool)), player, SLOT(playPause(bool))); + connect(logReplayAction, SIGNAL(triggered(bool)), this, SLOT(logging(bool))); +} + +void QGCToolBar::logging(bool enabled) +{ + // Stop logging in any case + MainWindow::instance()->getMAVLink()->enableLogging(false); + if (enabled) + { + QString fileName = QFileDialog::getSaveFileName(this, tr("Specify MAVLink log file name"), QDesktopServices::storageLocation(QDesktopServices::DesktopLocation), tr("MAVLink Logfile (*.mavlink *.log *.bin);;")); + + if (!fileName.endsWith(".mavlink")) + { + fileName.append(".mavlink"); + } + + QFileInfo file(fileName); + if (file.exists() && !file.isWritable()) + { + QMessageBox msgBox; + msgBox.setIcon(QMessageBox::Critical); + msgBox.setText(tr("The selected logfile is not writable")); + msgBox.setInformativeText(tr("Please make sure that the file %1 is writable or select a different file").arg(fileName)); + msgBox.setStandardButtons(QMessageBox::Ok); + msgBox.setDefaultButton(QMessageBox::Ok); + msgBox.exec(); + } + else + { + MainWindow::instance()->getMAVLink()->setLogfileName(fileName); + MainWindow::instance()->getMAVLink()->enableLogging(true); + } + } +} + void QGCToolBar::addPerspectiveChangeAction(QAction* action) { - addAction(action); + insertAction(toggleLoggingAction, action); } void QGCToolBar::setActiveUAS(UASInterface* active) @@ -56,6 +136,7 @@ void QGCToolBar::setActiveUAS(UASInterface* active) disconnect(mav, SIGNAL(nameChanged(QString)), this, SLOT(updateName(QString))); disconnect(mav, SIGNAL(systemTypeSet(UASInterface*,uint)), this, SLOT(setSystemType(UASInterface*,uint))); disconnect(mav, SIGNAL(textMessageReceived(int,int,int,QString)), this, SLOT(receiveTextMessage(int,int,int,QString))); + disconnect(mav, SIGNAL(batteryChanged(UASInterface*,double,double,int)), this, SLOT(updateBatteryRemaining(UASInterface*,double,double,int))); } // Connect new system @@ -65,61 +146,46 @@ void QGCToolBar::setActiveUAS(UASInterface* active) connect(active, SIGNAL(nameChanged(QString)), this, SLOT(updateName(QString))); connect(active, SIGNAL(systemTypeSet(UASInterface*,uint)), this, SLOT(setSystemType(UASInterface*,uint))); connect(active, SIGNAL(textMessageReceived(int,int,int,QString)), this, SLOT(receiveTextMessage(int,int,int,QString))); + connect(active, SIGNAL(batteryChanged(UASInterface*,double,double,int)), this, SLOT(updateBatteryRemaining(UASInterface*,double,double,int))); // Update all values once - nameLabel->setText(mav->getUASName()); - modeLabel->setText(mav->getShortMode()); - stateLabel->setText(mav->getShortState()); + toolBarNameLabel->setText(mav->getUASName()); + toolBarNameLabel->setStyleSheet(QString("QLabel { font: bold 16px; color: %1; }").arg(mav->getColor().name())); + symbolButton->setStyleSheet(QString("QWidget { background-color: %1; color: #DDDDDF; background-clip: border; } QToolButton { font-weight: bold; font-size: 12px; border: 0px solid #999999; border-radius: 5px; min-width:22px; max-width: 22px; min-height: 22px; max-height: 22px; padding: 0px; margin: 0px 4px 0px 20px; background-color: none; }").arg(mav->getColor().name())); +// toolBarModeLabel->setStyleSheet("QLabel { font: 16px; color: #3C7B9E; }"); +// toolBarStateLabel->setStyleSheet("QLabel { font: 16px; color: #FEC654; }"); + toolBarModeLabel->setText(mav->getShortMode()); + toolBarStateLabel->setText(mav->getShortState()); setSystemType(mav, mav->getSystemType()); } void QGCToolBar::createCustomWidgets() { - // Add internal actions - // Add MAV widget - symbolButton = new QToolButton(this); - nameLabel = new QLabel("------", this); - modeLabel = new QLabel("------", this); - stateLabel = new QLabel("------", this); - wpLabel = new QLabel("---", this); - distlabel = new QLabel("--- ---- m", this); - messageLabel = new QLabel("No system messages.", this); - //symbolButton->setIcon(":"); - symbolButton->setStyleSheet("QWidget { background-color: #050508; color: #DDDDDF; background-clip: border; } QToolButton { font-weight: bold; font-size: 12px; border: 0px solid #999999; border-radius: 5px; min-width:22px; max-width: 22px; min-height: 22px; max-height: 22px; padding: 0px; margin: 0px; background-color: none; }"); - addWidget(symbolButton); - addWidget(nameLabel); - addWidget(modeLabel); - addWidget(stateLabel); - addWidget(wpLabel); - addWidget(distlabel); - addWidget(messageLabel); - toggleLoggingAction = new QAction(QIcon(":"), "Start Logging", this); - logReplayAction = new QAction(QIcon(":"), "Start Replay", this); - - //addAction(toggleLoggingAction); - //addAction(logReplayAction); +} - addSeparator(); +void QGCToolBar::updateBatteryRemaining(UASInterface* uas, double voltage, double percent, int seconds) +{ + toolBarBatteryBar->setValue(percent); } void QGCToolBar::updateState(UASInterface* system, QString name, QString description) { Q_UNUSED(system); Q_UNUSED(description); - stateLabel->setText(tr(" State: %1").arg(name)); + toolBarStateLabel->setText(tr("%1").arg(name)); } void QGCToolBar::updateMode(int system, QString name, QString description) { Q_UNUSED(system); Q_UNUSED(description); - modeLabel->setText(tr(" Mode: %1").arg(name)); + toolBarModeLabel->setText(tr("%1").arg(name)); } void QGCToolBar::updateName(const QString& name) { - nameLabel->setText(name); + toolBarNameLabel->setText(name); } /** @@ -163,7 +229,7 @@ void QGCToolBar::receiveTextMessage(int uasid, int componentid, int severity, QS Q_UNUSED(uasid); Q_UNUSED(componentid); Q_UNUSED(severity); - messageLabel->setText(text); + toolBarMessageLabel->setText(text); } QGCToolBar::~QGCToolBar() diff --git a/src/ui/QGCToolBar.h b/src/ui/QGCToolBar.h index cf054ca468102c3a2ce2166e7ca20ffa82ac2689..94ac8ece8a61bec00b008cbcde84a1f939035612 100644 --- a/src/ui/QGCToolBar.h +++ b/src/ui/QGCToolBar.h @@ -28,14 +28,16 @@ This file is part of the QGROUNDCONTROL project #include #include #include +#include #include "UASInterface.h" +#include "QGCMAVLinkLogPlayer.h" class QGCToolBar : public QToolBar { Q_OBJECT public: - explicit QGCToolBar(QWidget *parent = 0); + explicit QGCToolBar(QWidget* parent = 0); void addPerspectiveChangeAction(QAction* action); ~QGCToolBar(); @@ -52,6 +54,12 @@ public slots: void setSystemType(UASInterface* uas, unsigned int systemType); /** @brief Received system text message */ void receiveTextMessage(int uasid, int componentid, int severity, QString text); + /** @brief Start / stop logging */ + void logging(bool enabled); + /** @brief Set log playing component */ + void setLogPlayer(QGCMAVLinkLogPlayer* player); + /** @brief Update battery charge state */ + void updateBatteryRemaining(UASInterface* uas, double voltage, double percent, int seconds); protected: void createCustomWidgets(); @@ -60,12 +68,13 @@ protected: QAction* logReplayAction; UASInterface* mav; QToolButton* symbolButton; - QLabel* nameLabel; - QLabel* modeLabel; - QLabel* stateLabel; - QLabel* wpLabel; - QLabel* distlabel; - QLabel* messageLabel; + QLabel* toolBarNameLabel; + QLabel* toolBarModeLabel; + QLabel* toolBarStateLabel; + QLabel* toolBarWpLabel; + QLabel* toolBarDistLabel; + QLabel* toolBarMessageLabel; + QProgressBar* toolBarBatteryBar; }; #endif // QGCTOOLBAR_H