Commit bc33da52 authored by pixhawk's avatar pixhawk

Added true audio output

parent 124997d0
File added
# Include general settings for MAVGround # Include general settings for MAVGround
include(mavground.pri) include(mavground.pri)
# Include serial port library # Include serial port library
include(src/lib/qextserialport/qextserialport.pri) include(src/lib/qextserialport/qextserialport.pri)
# Include QWT plotting library # Include QWT plotting library
include(src/lib/qwt/qwt.pri) include(src/lib/qwt/qwt.pri)
# Include FLITE audio synthesizer library # Include FLITE audio synthesizer library
#include(src/lib/flite/flite.pri) # include(src/lib/flite/flite.pri)
# Include QMapControl map library
# Include QMapControl map library include(lib/QMapControl/QMapControl.pri)
include(lib/QMapControl/QMapControl.pri) DEPENDPATH += . \
DEPENDPATH += . \ lib/QMapControl \
lib/QMapControl \ lib/QMapControl/src
lib/QMapControl/src INCLUDEPATH += . \
INCLUDEPATH += . \ lib/QMapControl \
lib/QMapControl \ ../mavlink/src \
../mavlink/src mavlink/src \
src/mavlink
# Input
FORMS += src/ui/MainWindow.ui \ # Input
src/ui/CommSettings.ui \ FORMS += src/ui/MainWindow.ui \
src/ui/SerialSettings.ui \ src/ui/CommSettings.ui \
src/ui/UASControl.ui \ src/ui/SerialSettings.ui \
src/ui/UASList.ui \ src/ui/UASControl.ui \
src/ui/UASInfo.ui \ src/ui/UASList.ui \
src/ui/LineChart.ui \ src/ui/UASInfo.ui \
src/ui/UASView.ui \ src/ui/LineChart.ui \
src/ui/ParameterInterface.ui \ src/ui/UASView.ui \
src/ui/WaypointList.ui \ src/ui/ParameterInterface.ui \
src/ui/WaypointView.ui \ src/ui/WaypointList.ui \
src/ui/ObjectDetectionView.ui \ src/ui/WaypointView.ui \
src/ui/JoystickWidget.ui \ src/ui/ObjectDetectionView.ui \
src/ui/DebugConsole.ui \ src/ui/JoystickWidget.ui \
src/ui/MapWidget.ui \ src/ui/DebugConsole.ui \
src/ui/XMLCommProtocolWidget.ui \ src/ui/MapWidget.ui \
src/ui/HDDisplay.ui \ src/ui/XMLCommProtocolWidget.ui \
src/ui/MAVLinkSettingsWidget.ui \ src/ui/HDDisplay.ui \
src/ui/AudioOutputWidget.ui src/ui/MAVLinkSettingsWidget.ui \
INCLUDEPATH += src \ src/ui/AudioOutputWidget.ui
src/ui \ INCLUDEPATH += src \
src/ui/linechart \ src/ui \
src/ui/uas \ src/ui/linechart \
src/ui/map \ src/ui/uas \
src/uas \ src/ui/map \
src/comm \ src/uas \
include/ui \ src/comm \
src/input \ include/ui \
src/lib/qmapcontrol \ src/input \
src/ui/mavlink src/lib/qmapcontrol \
HEADERS += src/MG.h \ src/ui/mavlink
src/Core.h \ HEADERS += src/MG.h \
src/uas/UASInterface.h \ src/Core.h \
src/uas/UAS.h \ src/uas/UASInterface.h \
src/uas/UASManager.h \ src/uas/UAS.h \
src/comm/LinkManager.h \ src/uas/UASManager.h \
src/comm/LinkInterface.h \ src/comm/LinkManager.h \
src/comm/SerialLinkInterface.h \ src/comm/LinkInterface.h \
src/comm/SerialLink.h \ src/comm/SerialLinkInterface.h \
src/comm/SerialSimulationLink.h \ src/comm/SerialLink.h \
src/comm/ProtocolInterface.h \ src/comm/SerialSimulationLink.h \
src/comm/MAVLinkProtocol.h \ src/comm/ProtocolInterface.h \
src/comm/AS4Protocol.h \ src/comm/MAVLinkProtocol.h \
src/ui/CommConfigurationWindow.h \ src/comm/AS4Protocol.h \
src/ui/SerialConfigurationWindow.h \ src/ui/CommConfigurationWindow.h \
src/ui/MainWindow.h \ src/ui/SerialConfigurationWindow.h \
src/ui/uas/UASControlWidget.h \ src/ui/MainWindow.h \
src/ui/uas/UASListWidget.h \ src/ui/uas/UASControlWidget.h \
src/ui/uas/UASInfoWidget.h \ src/ui/uas/UASListWidget.h \
src/ui/HUD.h \ src/ui/uas/UASInfoWidget.h \
src/ui/linechart/LinechartWidget.h \ src/ui/HUD.h \
src/ui/linechart/LinechartContainer.h \ src/ui/linechart/LinechartWidget.h \
src/ui/linechart/LinechartPlot.h \ src/ui/linechart/LinechartContainer.h \
src/ui/linechart/Scrollbar.h \ src/ui/linechart/LinechartPlot.h \
src/ui/linechart/ScrollZoomer.h \ src/ui/linechart/Scrollbar.h \
src/configuration.h \ src/ui/linechart/ScrollZoomer.h \
src/ui/uas/UASView.h \ src/configuration.h \
src/ui/CameraView.h \ src/ui/uas/UASView.h \
src/comm/MAVLinkSimulationLink.h \ src/ui/CameraView.h \
src/comm/UDPLink.h \ src/comm/MAVLinkSimulationLink.h \
src/ui/ParameterInterface.h \ src/comm/UDPLink.h \
src/ui/WaypointList.h \ src/ui/ParameterInterface.h \
src/Waypoint.h \ src/ui/WaypointList.h \
src/ui/WaypointView.h \ src/Waypoint.h \
src/ui/ObjectDetectionView.h \ src/ui/WaypointView.h \
src/input/JoystickInput.h \ src/ui/ObjectDetectionView.h \
src/ui/JoystickWidget.h \ src/input/JoystickInput.h \
src/ui/PFD.h \ src/ui/JoystickWidget.h \
src/ui/GaugePanel.h \ src/ui/PFD.h \
src/ui/DebugConsole.h \ src/ui/GaugePanel.h \
src/ui/MapWidget.h \ src/ui/DebugConsole.h \
src/ui/XMLCommProtocolWidget.h \ src/ui/MapWidget.h \
src/ui/mavlink/DomItem.h \ src/ui/XMLCommProtocolWidget.h \
src/ui/mavlink/DomModel.h \ src/ui/mavlink/DomItem.h \
src/comm/MAVLinkXMLParser.h \ src/ui/mavlink/DomModel.h \
src/ui/HDDisplay.h \ src/comm/MAVLinkXMLParser.h \
src/ui/MAVLinkSettingsWidget.h \ src/ui/HDDisplay.h \
src/ui/AudioOutputWidget.h \ src/ui/MAVLinkSettingsWidget.h \
src/AudioOutput.h \ src/ui/AudioOutputWidget.h \
src/LogCompressor.h \ src/GAudioOutput.h \
src/comm/ViconTarsusProtocol.h \ src/LogCompressor.h
src/comm/TarsusField.h \ SOURCES += src/main.cc \
src/comm/TarsusFieldDescriptor.h \ src/Core.cc \
src/comm/TarsusFieldTriplet.h \ src/uas/UASManager.cc \
src/comm/TarsusRigidBody.h \ src/uas/UAS.cc \
src/comm/TarsusStream.h src/comm/LinkManager.cc \
SOURCES += src/main.cc \ src/comm/SerialLink.cc \
src/Core.cc \ src/comm/SerialSimulationLink.cc \
src/uas/UASManager.cc \ src/comm/MAVLinkProtocol.cc \
src/uas/UAS.cc \ src/comm/AS4Protocol.cc \
src/comm/LinkManager.cc \ src/ui/CommConfigurationWindow.cc \
src/comm/SerialLink.cc \ src/ui/SerialConfigurationWindow.cc \
src/comm/SerialSimulationLink.cc \ src/ui/MainWindow.cc \
src/comm/MAVLinkProtocol.cc \ src/ui/uas/UASControlWidget.cc \
src/comm/AS4Protocol.cc \ src/ui/uas/UASListWidget.cc \
src/ui/CommConfigurationWindow.cc \ src/ui/uas/UASInfoWidget.cc \
src/ui/SerialConfigurationWindow.cc \ src/ui/HUD.cc \
src/ui/MainWindow.cc \ src/ui/linechart/LinechartWidget.cc \
src/ui/uas/UASControlWidget.cc \ src/ui/linechart/LinechartContainer.cc \
src/ui/uas/UASListWidget.cc \ src/ui/linechart/LinechartPlot.cc \
src/ui/uas/UASInfoWidget.cc \ src/ui/linechart/Scrollbar.cc \
src/ui/HUD.cc \ src/ui/linechart/ScrollZoomer.cc \
src/ui/linechart/LinechartWidget.cc \ src/ui/uas/UASView.cc \
src/ui/linechart/LinechartContainer.cc \ src/ui/CameraView.cc \
src/ui/linechart/LinechartPlot.cc \ src/comm/MAVLinkSimulationLink.cc \
src/ui/linechart/Scrollbar.cc \ src/comm/UDPLink.cc \
src/ui/linechart/ScrollZoomer.cc \ src/ui/ParameterInterface.cc \
src/ui/uas/UASView.cc \ src/ui/WaypointList.cc \
src/ui/CameraView.cc \ src/Waypoint.cc \
src/comm/MAVLinkSimulationLink.cc \ src/ui/WaypointView.cc \
src/comm/UDPLink.cc \ src/ui/ObjectDetectionView.cc \
src/ui/ParameterInterface.cc \ src/input/JoystickInput.cc \
src/ui/WaypointList.cc \ src/ui/JoystickWidget.cc \
src/Waypoint.cc \ src/ui/PFD.cc \
src/ui/WaypointView.cc \ src/ui/GaugePanel.cc \
src/ui/ObjectDetectionView.cc \ src/ui/DebugConsole.cc \
src/input/JoystickInput.cc \ src/ui/MapWidget.cc \
src/ui/JoystickWidget.cc \ src/ui/XMLCommProtocolWidget.cc \
src/ui/PFD.cc \ src/ui/mavlink/DomItem.cc \
src/ui/GaugePanel.cc \ src/ui/mavlink/DomModel.cc \
src/ui/DebugConsole.cc \ src/comm/MAVLinkXMLParser.cc \
src/ui/MapWidget.cc \ src/ui/HDDisplay.cc \
src/ui/XMLCommProtocolWidget.cc \ src/ui/MAVLinkSettingsWidget.cc \
src/ui/mavlink/DomItem.cc \ src/ui/AudioOutputWidget.cc \
src/ui/mavlink/DomModel.cc \ src/GAudioOutput.cc \
src/comm/MAVLinkXMLParser.cc \ src/LogCompressor.cc
src/ui/HDDisplay.cc \ RESOURCES = mavground.qrc
src/ui/MAVLinkSettingsWidget.cc \
src/ui/AudioOutputWidget.cc \
src/AudioOutput.cc \
src/LogCompressor.cc \
src/comm/ViconTarsusProtocol.cc
RESOURCES = mavground.qrc
<RCC> <RCC>
<qresource prefix="/"> <qresource prefix="/" >
<file>images/control/launch.svg</file> <file>images/control/launch.svg</file>
<file>images/status/dialog-error.svg</file> <file>images/status/dialog-error.svg</file>
<file>images/status/dialog-warning.svg</file> <file>images/status/dialog-warning.svg</file>
...@@ -76,8 +76,10 @@ ...@@ -76,8 +76,10 @@
<file>images/status/audio-volume-low.svg</file> <file>images/status/audio-volume-low.svg</file>
<file>images/status/audio-volume-high.svg</file> <file>images/status/audio-volume-high.svg</file>
<file>images/style-mission.css</file> <file>images/style-mission.css</file>
<file>images/splash.png</file>
<file>audio/alert.wav</file>
</qresource> </qresource>
<qresource prefix="/general"> <qresource prefix="/general" >
<file alias="vera.ttf">images/Vera.ttf</file> <file alias="vera.ttf" >images/Vera.ttf</file>
</qresource> </qresource>
</RCC> </RCC>
#include "AudioOutput.h"
#include <flite.h>
#include <phonon/mediaobject.h>
#include <QTemporaryFile>
#include <QDebug>
extern "C" {
#include <cmu_us_awb/voxdefs.h>
//#include <cmu_us_slt/voxdefs.h>
//cst_voice *REGISTER_VOX(const char *voxdir);
//void UNREGISTER_VOX(cst_voice *vox);
cst_voice *register_cmu_us_awb(const char *voxdir);
void unregister_cmu_us_awb(cst_voice *vox);
cst_voice *register_cmu_us_slt(const char *voxdir);
void unregister_cmu_us_slt(cst_voice *vox);
cst_voice *register_cmu_us_rms(const char *voxdir);
void unregister_cmu_us_rms(cst_voice *vox);
};
AudioOutput::AudioOutput(QString voice, QObject* parent) : QObject(parent),
voice(NULL),
voiceIndex(0)
{
#ifndef _WIN32
flite_init();
#endif
switch (voiceIndex)
{
case 0:
selectFemaleVoice();
break;
case 1:
selectMaleVoice();
break;
default:
selectNeutralVoice();
break;
}
/*
// List available voices
QStringList voices = listVoices();
foreach (QString s, voices)
{
qDebug() << "VOICE: " << s;
}
if (voice.length() > 0)
{
//this->voice = flite_voice_select(voice.toStdString().c_str());
}
else
{
// Take default voice
//this->voice = flite_voice_select("awb");
}
*/
}
bool AudioOutput::say(QString text, int severity)
{
// Only give speech output on Linux and MacOS
#ifndef _WIN32
QTemporaryFile file;
file.setFileTemplate("XXXXXX.wav");
if (file.open())
{
cst_wave* wav = flite_text_to_wave(text.toStdString().c_str(), this->voice);
// file.fileName() returns the unique file name
cst_wave_save(wav, file.fileName().toStdString().c_str(), "riff");
Phonon::MediaObject *music =
Phonon::createPlayer(Phonon::MusicCategory,
Phonon::MediaSource(file.fileName().toStdString().c_str()));
music->play();
qDebug() << "Synthesized: " << text << ", tmp file:" << file.fileName().toStdString().c_str();
}
#else
qDebug() << "Synthesized: " << text << ", NO OUTPUT SUPPORT ON WINDOWS!";
#endif
return true;
}
bool AudioOutput::alert(QString text)
{
// Play alert sound
// Say alert message
return say(text, 2);
}
bool AudioOutput::startEmergency()
{
return false;
}
bool AudioOutput::stopEmergency()
{
return false;
}
void AudioOutput::selectFemaleVoice()
{
#ifndef _WIN32
this->voice = register_cmu_us_slt(NULL);
#endif
}
void AudioOutput::selectMaleVoice()
{
#ifndef _WIN32
this->voice = register_cmu_us_rms(NULL);
#endif
}
void AudioOutput::selectNeutralVoice()
{
#ifndef _WIN32
this->voice = register_cmu_us_awb(NULL);
#endif
}
#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */
QStringList AudioOutput::listVoices(void)
{
cst_voice *voice;
const cst_val *v;
QStringList l;
#ifndef _WIN32
/*
printf("Voices available: ");
for (v=flite_voice_list; v; v=val_cdr(v))
{
voice = val_voice(val_car(v));
QString s;
s.sprintf("%s",voice->name);
printf("%s",voice->name);
l.append(s);
}
printf("\n");
*/
#endif
return l;
}
#ifdef __cplusplus
}
#endif /* __cplusplus */
#ifndef AUDIOOUTPUT_H
#define AUDIOOUTPUT_H
#include <QObject>
#include <QStringList>
#include <flite.h>
class AudioOutput : public QObject
{
Q_OBJECT
public:
AudioOutput(QString voice="", QObject* parent=NULL);
/** @brief List available voices */
QStringList listVoices(void);
public slots:
/** @brief Say this text if current output priority matches */
bool say(QString text, int severity);
/** @brief Play alert sound */
bool alert(QString text);
/** @brief Start emergency sound */
bool startEmergency();
/** @brief Stop emergency sound */
bool stopEmergency();
/** @brief Select female voice */
void selectFemaleVoice();
/** @brief Select male voice */
void selectMaleVoice();
/** @brief Select neutral voice */
void selectNeutralVoice();
protected:
cst_voice* voice;
int voiceIndex;
};
#endif // AUDIOOUTPUT_H
...@@ -23,7 +23,7 @@ This file is part of the PIXHAWK project ...@@ -23,7 +23,7 @@ This file is part of the PIXHAWK project
/** /**
* @file * @file
* @brief Main class * @brief Implementation of main class
* *
* @author Lorenz Meier <mavteam@student.ethz.ch> * @author Lorenz Meier <mavteam@student.ethz.ch>
* *
...@@ -43,7 +43,7 @@ This file is part of the PIXHAWK project ...@@ -43,7 +43,7 @@ This file is part of the PIXHAWK project
#include <Core.h> #include <Core.h>
#include <MG.h> #include <MG.h>
#include <MainWindow.h> #include <MainWindow.h>
#include "AudioOutput.h" #include "GAudioOutput.h"
/** /**
...@@ -56,7 +56,7 @@ This file is part of the PIXHAWK project ...@@ -56,7 +56,7 @@ This file is part of the PIXHAWK project
* @param argv The string array of parameters * @param argv The string array of parameters
**/ **/
MGCore::MGCore(int &argc, char* argv[]) : QApplication(argc, argv) Core::Core(int &argc, char* argv[]) : QApplication(argc, argv)
{ {
this->setApplicationName("OpenMAV Ground Control Station"); this->setApplicationName("OpenMAV Ground Control Station");
this->setApplicationVersion("v. 0.0.5"); this->setApplicationVersion("v. 0.0.5");
...@@ -69,12 +69,12 @@ MGCore::MGCore(int &argc, char* argv[]) : QApplication(argc, argv) ...@@ -69,12 +69,12 @@ MGCore::MGCore(int &argc, char* argv[]) : QApplication(argc, argv)
QFontDatabase fontDatabase = QFontDatabase(); QFontDatabase fontDatabase = QFontDatabase();
const QString fontFileName = ":/general/vera.ttf"; ///< Font file is part of the QRC file and compiled into the app const QString fontFileName = ":/general/vera.ttf"; ///< Font file is part of the QRC file and compiled into the app
const QString fontFamilyName = "Bitstream Vera Sans"; const QString fontFamilyName = "Bitstream Vera Sans";
if(!QFile::exists(fontFileName)) printf("ERROR! font file: %s DOES NOT EXIST!", fontFileName); //if(!QFile::exists(fontFileName)) //printf("ERROR! font file: %s DOES NOT EXIST!", fontFileName);
fontDatabase.addApplicationFont(fontFileName); fontDatabase.addApplicationFont(fontFileName);
setFont(fontDatabase.font(fontFamilyName, "Roman", 12)); setFont(fontDatabase.font(fontFamilyName, "Roman", 12));
// Show splash screen // Show splash screen
QPixmap splashImage(MG::DIR::getIconDirectory() + "/groundstation-splash.png"); QPixmap splashImage(":images/splash.png");
QSplashScreen* splashScreen = new QSplashScreen(splashImage, Qt::WindowStaysOnTopHint); QSplashScreen* splashScreen = new QSplashScreen(splashImage, Qt::WindowStaysOnTopHint);
splashScreen->show(); splashScreen->show();
...@@ -87,11 +87,10 @@ MGCore::MGCore(int &argc, char* argv[]) : QApplication(argc, argv) ...@@ -87,11 +87,10 @@ MGCore::MGCore(int &argc, char* argv[]) : QApplication(argc, argv)
startUASManager(); startUASManager();
// Start audio output // Start audio output
AudioOutput* audio = new AudioOutput(); GAudioOutput::instance()->say("Ground Control Station started", 1);
audio->say("Ground Control Station started", 1);
tarsus = new ViconTarsusProtocol(); //tarsus = new ViconTarsusProtocol();
tarsus->start(); //tarsus->start();
// Start the user interface // Start the user interface
splashScreen->showMessage(tr("Starting User Interface")); splashScreen->showMessage(tr("Starting User Interface"));
...@@ -107,7 +106,7 @@ MGCore::MGCore(int &argc, char* argv[]) : QApplication(argc, argv) ...@@ -107,7 +106,7 @@ MGCore::MGCore(int &argc, char* argv[]) : QApplication(argc, argv)
* @brief Destructor for the groundstation. It destroys all loaded instances. * @brief Destructor for the groundstation. It destroys all loaded instances.
* *
**/ **/
MGCore::~MGCore() Core::~Core()
{ {
// Delete singletons // Delete singletons
delete LinkManager::instance(); delete LinkManager::instance();
...@@ -120,7 +119,7 @@ MGCore::~MGCore() ...@@ -120,7 +119,7 @@ MGCore::~MGCore()
* The link manager keeps track of all communication links and provides the global * The link manager keeps track of all communication links and provides the global
* packet queue. It is the main communication hub * packet queue. It is the main communication hub
**/ **/
void MGCore::startLinkManager() void Core::startLinkManager()
{ {
LinkManager::instance(); LinkManager::instance();
} }
...@@ -129,7 +128,7 @@ void MGCore::startLinkManager() ...@@ -129,7 +128,7 @@ void MGCore::startLinkManager()
* @brief Start the Unmanned Air System Manager * @brief Start the Unmanned Air System Manager
* *
**/ **/
void MGCore::startUASManager() void Core::startUASManager()
{ {
UASManager::instance(); UASManager::instance();
} }
...@@ -137,10 +136,10 @@ void MGCore::startUASManager() ...@@ -137,10 +136,10 @@ void MGCore::startUASManager()
/** /**
* @brief Start and show the user interface. * @brief Start and show the user interface.
**/ **/
void MGCore::startUI() void Core::startUI()
{ {
// Start UI // Start UI
mainWindow = new MGMainWindow(); mainWindow = new MainWindow();
// Make UI visible // Make UI visible
mainWindow->show(); mainWindow->show();
} }
......
...@@ -30,15 +30,15 @@ This file is part of the PIXHAWK project ...@@ -30,15 +30,15 @@ This file is part of the PIXHAWK project
*/ */
#ifndef _MGCORE_H_ #ifndef _CORE_H_
#define _MGCORE_H_ #define _CORE_H_
#include <QApplication> #include <QApplication>
#include "MainWindow.h" #include "MainWindow.h"
#include "UASManager.h" #include "UASManager.h"
#include "LinkManager.h" #include "LinkManager.h"
#include "ViconTarsusProtocol.h" /*#include "ViconTarsusProtocol.h" */
/** /**
* @brief The main application and management class. * @brief The main application and management class.
...@@ -47,13 +47,13 @@ This file is part of the PIXHAWK project ...@@ -47,13 +47,13 @@ This file is part of the PIXHAWK project
* the central management unit of the groundstation application. * the central management unit of the groundstation application.
* *
**/ **/
class MGCore : public QApplication class Core : public QApplication
{ {
Q_OBJECT Q_OBJECT
public: public:
MGCore(int &argc, char* argv[]); Core(int &argc, char* argv[]);
~MGCore(); ~Core();
protected: protected:
void startLinkManager(); void startLinkManager();
...@@ -68,9 +68,9 @@ protected: ...@@ -68,9 +68,9 @@ protected:
void startUI(); void startUI();
private: private:
MGMainWindow* mainWindow; MainWindow* mainWindow;
ViconTarsusProtocol* tarsus; //ViconTarsusProtocol* tarsus;
}; };
#endif // _MGCORE_H_ #endif /* _CORE_H_ */
/*=====================================================================
PIXHAWK Micro Air Vehicle Flying Robotics Toolkit
(c) 2009, 2010 PIXHAWK PROJECT <http://pixhawk.ethz.ch>
This file is part of the PIXHAWK project
PIXHAWK is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
PIXHAWK is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with PIXHAWK. If not, see <http://www.gnu.org/licenses/>.
======================================================================*/
/**
* @file
* @brief Implementation of audio output
*
* @author Lorenz Meier <mavteam@student.ethz.ch>
*
*/
#include <QApplication>
#include "GAudioOutput.h"
#include "MG.h"
#include <flite.h>
#include <Phonon>
#include <QTemporaryFile>
#include <QDebug>
extern "C" {
#include <cmu_us_awb/voxdefs.h>
//#include <cmu_us_slt/voxdefs.h>
//cst_voice *REGISTER_VOX(const char *voxdir);
//void UNREGISTER_VOX(cst_voice *vox);
cst_voice *register_cmu_us_awb(const char *voxdir);
void unregister_cmu_us_awb(cst_voice *vox);
cst_voice *register_cmu_us_slt(const char *voxdir);
void unregister_cmu_us_slt(cst_voice *vox);
cst_voice *register_cmu_us_rms(const char *voxdir);
void unregister_cmu_us_rms(cst_voice *vox);
};
/**
* This class follows the singleton design pattern
* @see http://en.wikipedia.org/wiki/Singleton_pattern
* A call to this function thus returns the only instance of this object
* the call can occur at any place in the code, no reference to the
* GAudioOutput object has to be passed.
*/
GAudioOutput* GAudioOutput::instance()
{
static GAudioOutput* _instance = 0;
if(_instance == 0) {
_instance = new GAudioOutput();
// Set the application as parent to ensure that this object
// will be destroyed when the main application exits
_instance->setParent(qApp);
}
return _instance;
}
GAudioOutput::GAudioOutput(QObject* parent) : QObject(parent),
voice(NULL),
voiceIndex(0),
emergency(false)
{
#ifndef _WIN32
flite_init();
m_media = new Phonon::MediaObject(this);
Phonon::AudioOutput *audioOutput = new Phonon::AudioOutput(Phonon::MusicCategory, this);
createPath(m_media, audioOutput);
emergencyTimer = new QTimer();
connect(emergencyTimer, SIGNAL(timeout()), this, SLOT(beep()));
#endif
switch (voiceIndex)
{
case 0:
selectFemaleVoice();
break;
case 1:
selectMaleVoice();
break;
default:
selectNeutralVoice();
break;
}
/*
// List available voices
QStringList voices = listVoices();
foreach (QString s, voices)
{
qDebug() << "VOICE: " << s;
}
if (voice.length() > 0)
{
//this->voice = flite_voice_select(voice.toStdString().c_str());
}
else
{
// Take default voice
//this->voice = flite_voice_select("awb");
}
*/
}
bool GAudioOutput::say(QString text, int severity)
{
bool res = false;
if (!emergency)
{
// Only give speech output on Linux and MacOS
#ifndef _WIN32
QTemporaryFile file;
file.setFileTemplate("XXXXXX.wav");
if (file.open())
{
cst_wave* wav = flite_text_to_wave(text.toStdString().c_str(), this->voice);
// file.fileName() returns the unique file name
cst_wave_save(wav, file.fileName().toStdString().c_str(), "riff");
m_media->setCurrentSource(Phonon::MediaSource(file.fileName().toStdString().c_str()));
qDebug() << "TYPE:" << m_media->currentSource().type();
m_media->play();
qDebug() << "Synthesized: " << text << ", tmp file:" << file.fileName().toStdString().c_str();
res = true;
}
#else
qDebug() << "Synthesized: " << text << ", NO OUTPUT SUPPORT ON WINDOWS!";
#endif
}
return res;
}
/**
* @param text This message will be played after the alert beep
*/
bool GAudioOutput::alert(QString text)
{
if (!emergency)
{
// Play alert sound
m_media->setCurrentSource(Phonon::MediaSource(QString("alert.wav").toStdString().c_str()));
qDebug() << "FILENAME:" << m_media->currentSource().fileName();
qDebug() << "TYPE:" << m_media->currentSource().type();
qDebug() << QString("alert.wav").toStdString().c_str();
m_media->play();
m_media->setCurrentSource(Phonon::MediaSource(QString("alert.wav").toStdString().c_str()));
m_media->play();
// Say alert message
return true;//say(text, 2);
}
else
{
return false;
}
}
/**
* The emergency sound will be played continously during the emergency.
* call stopEmergency() to disable it again. No speech synthesis or other
* audio output is available during the emergency.
*
* @return true if the emergency could be started, false else
*/
bool GAudioOutput::startEmergency()
{
if (!emergency)
{
emergency = true;
emergencyTimer->start(1600);
}
return true;
}
/**
* Stops the continous emergency sound. Use startEmergency() to start
* the emergency sound.
*
* @return true if the emergency could be stopped, false else
*/
bool GAudioOutput::stopEmergency()
{
if (emergency)
{
emergency = false;
emergencyTimer->stop();
}
return true;
}
void GAudioOutput::beep()
{
m_media->setCurrentSource(Phonon::MediaSource(QString("alert.wav").toStdString().c_str()));
m_media->play();
}
void GAudioOutput::selectFemaleVoice()
{
#ifndef _WIN32
this->voice = register_cmu_us_slt(NULL);
#endif
}
void GAudioOutput::selectMaleVoice()
{
#ifndef _WIN32
this->voice = register_cmu_us_rms(NULL);
#endif
}
void GAudioOutput::selectNeutralVoice()
{
#ifndef _WIN32
this->voice = register_cmu_us_awb(NULL);
#endif
}
#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */
QStringList GAudioOutput::listVoices(void)
{
cst_voice *voice;
const cst_val *v;
QStringList l;
#ifndef _WIN32
/*
printf("Voices available: ");
for (v=flite_voice_list; v; v=val_cdr(v))
{
voice = val_voice(val_car(v));
QString s;
s.sprintf("%s",voice->name);
printf("%s",voice->name);
l.append(s);
}
printf("\n");
*/
#endif
return l;
}
#ifdef __cplusplus
}
#endif /* __cplusplus */
/*=====================================================================
PIXHAWK Micro Air Vehicle Flying Robotics Toolkit
(c) 2009, 2010 PIXHAWK PROJECT <http://pixhawk.ethz.ch>
This file is part of the PIXHAWK project
PIXHAWK is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
PIXHAWK is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with PIXHAWK. If not, see <http://www.gnu.org/licenses/>.
======================================================================*/
/**
* @file
* @brief Definition of audio output
*
* @author Lorenz Meier <mavteam@student.ethz.ch>
*
*/
#ifndef GAUDIOOUTPUT_H
#define GAUDIOOUTPUT_H
#include <QObject>
#include <QTimer>
#include <QStringList>
#include <flite.h>
#include <Phonon>
/**
* @brief Audio Output (speech synthesizer and "beep" output)
* This class follows the singleton design pattern
* @see http://en.wikipedia.org/wiki/Singleton_pattern
*/
class GAudioOutput : public QObject
{
Q_OBJECT
public:
/** @brief Get the singleton instance */
static GAudioOutput* GAudioOutput::instance();
/** @brief List available voices */
QStringList listVoices(void);
public slots:
/** @brief Say this text if current output priority matches */
bool say(QString text, int severity=1);
/** @brief Play alert sound */
bool alert(QString text);
/** @brief Start emergency sound */
bool startEmergency();
/** @brief Stop emergency sound */
bool stopEmergency();
/** @brief Select female voice */
void selectFemaleVoice();
/** @brief Select male voice */
void selectMaleVoice();
/** @brief Select neutral voice */
void selectNeutralVoice();
/** @brief Play emergency sound */
void beep();
protected:
cst_voice* voice; ///< The flite voice object
int voiceIndex; ///< The index of the flite voice to use (awb, slt, rms)
Phonon::MediaObject* m_media; ///< The output object for audio
Phonon::AudioOutput* m_audioOutput;
bool emergency; ///< Emergency status flag
QTimer* emergencyTimer;
private:
GAudioOutput(QObject* parent=NULL);
};
#endif // AUDIOOUTPUT_H
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
PIXHAWK Micro Air Vehicle Flying Robotics Toolkit PIXHAWK Micro Air Vehicle Flying Robotics Toolkit
(c) 2009 PIXHAWK PROJECT <http://pixhawk.ethz.ch> (c) 2009, 2010 PIXHAWK PROJECT <http://pixhawk.ethz.ch>
This file is part of the PIXHAWK project This file is part of the PIXHAWK project
......
...@@ -57,20 +57,9 @@ MAVLinkSimulationLink::MAVLinkSimulationLink(QString readFile, QString writeFile ...@@ -57,20 +57,9 @@ MAVLinkSimulationLink::MAVLinkSimulationLink(QString readFile, QString writeFile
readyBytes(0), readyBytes(0),
timeOffset(0) timeOffset(0)
{ {
this->id = getNextLinkId();
LinkManager::instance()->add(this);
this->rate = rate; this->rate = rate;
_isConnected = false; _isConnected = false;
if (readFile != "")
{
this->name = "Simulation: " + readFile;
}
else
{
this->name = "MAVLink simulation link";
}
// Comments on the variables can be found in the header file // Comments on the variables can be found in the header file
simulationFile = new QFile(readFile, this); simulationFile = new QFile(readFile, this);
...@@ -81,10 +70,20 @@ MAVLinkSimulationLink::MAVLinkSimulationLink(QString readFile, QString writeFile ...@@ -81,10 +70,20 @@ MAVLinkSimulationLink::MAVLinkSimulationLink(QString readFile, QString writeFile
receiveFile = new QFile(writeFile, this); receiveFile = new QFile(writeFile, this);
lastSent = MG::TIME::getGroundTimeNow(); lastSent = MG::TIME::getGroundTimeNow();
if (simulationFile->exists())
{
this->name = "Simulation: " + QFileInfo(simulationFile->fileName()).fileName();
}
else
{
this->name = "MAVLink simulation link";
}
// Initialize the pseudo-random number generator // Initialize the pseudo-random number generator
srand(QTime::currentTime().msec()); srand(QTime::currentTime().msec());
maxTimeNoise = 0; maxTimeNoise = 0;
this->id = getNextLinkId();
LinkManager::instance()->add(this);
} }
MAVLinkSimulationLink::~MAVLinkSimulationLink() MAVLinkSimulationLink::~MAVLinkSimulationLink()
...@@ -390,6 +389,32 @@ void MAVLinkSimulationLink::mainloop() ...@@ -390,6 +389,32 @@ void MAVLinkSimulationLink::mainloop()
memcpy(stream+streampointer,buffer, bufferlength); memcpy(stream+streampointer,buffer, bufferlength);
streampointer += bufferlength; streampointer += bufferlength;
/*
// HEARTBEAT VEHICLE 2
// Pack message and get size of encoded byte string
messageSize = message_heartbeat_pack(42, componentId, &msg, MAV_FIXED_WING);
// Allocate buffer with packet data
bufferlength = message_to_send_buffer(buffer, &msg);
//add data into datastream
memcpy(stream+streampointer,buffer, bufferlength);
streampointer += bufferlength;
// STATUS VEHICLE 2
sys_status_t status2;
status2.mode = MAV_MODE_LOCKED;
status2.vbat = voltage;
status2.status = MAV_STATE_STANDBY;
// Pack message and get size of encoded byte string
messageSize = message_sys_status_encode(systemId, componentId, &msg, &status);
// Allocate buffer with packet data
bufferlength = message_to_send_buffer(buffer, &msg);
//add data into datastream
memcpy(stream+streampointer,buffer, bufferlength);
streampointer += bufferlength;
*/
//qDebug() << "BOOT" << "BUF LEN" << bufferlength << "POINTER" << streampointer; //qDebug() << "BOOT" << "BUF LEN" << bufferlength << "POINTER" << streampointer;
// AUX STATUS // AUX STATUS
......
...@@ -48,9 +48,7 @@ UDPLink::UDPLink(QHostAddress host, quint16 port) ...@@ -48,9 +48,7 @@ UDPLink::UDPLink(QHostAddress host, quint16 port)
// Set unique ID and add link to the list of links // Set unique ID and add link to the list of links
this->id = getNextLinkId(); this->id = getNextLinkId();
this->name = tr("UDP link ") + QString::number(getId());
name = tr("UDP link ") + QString::number(getId()) + tr(" (unconfigured)");
LinkManager::instance()->add(this); LinkManager::instance()->add(this);
} }
......
...@@ -43,6 +43,6 @@ This file is part of the PIXHAWK project ...@@ -43,6 +43,6 @@ This file is part of the PIXHAWK project
int main(int argc, char *argv[]) int main(int argc, char *argv[])
{ {
MGCore core(argc, argv); Core core(argc, argv);
return core.exec(); return core.exec();
} }
...@@ -39,6 +39,7 @@ This file is part of the PIXHAWK project ...@@ -39,6 +39,7 @@ This file is part of the PIXHAWK project
#include "LinkInterface.h" #include "LinkInterface.h"
#include "UASManager.h" #include "UASManager.h"
#include "MG.h" #include "MG.h"
#include "GAudioOutput.h"
#include "mavlink.h" #include "mavlink.h"
UAS::UAS(int id=0) : UAS::UAS(int id=0) :
...@@ -47,19 +48,21 @@ UAS::UAS(int id=0) : ...@@ -47,19 +48,21 @@ UAS::UAS(int id=0) :
name(""), name(""),
links(new QList<LinkInterface*>()), links(new QList<LinkInterface*>()),
thrustSum(0), thrustSum(0),
thrustMax(10),
startVoltage(0), startVoltage(0),
manualRollAngle(0), currentVoltage(0.0f),
manualPitchAngle(0), lpVoltage(0.0f),
manualYawAngle(0), mode(MAV_MODE_UNINIT),
manualThrust(0), status(MAV_STATE_UNINIT),
onboardTimeOffset(0),
controlRollManual(true), controlRollManual(true),
controlPitchManual(true), controlPitchManual(true),
controlYawManual(true), controlYawManual(true),
currentVoltage(0.0f),
controlThrustManual(true), controlThrustManual(true),
lpVoltage(0.0f), manualRollAngle(0),
mode(MAV_MODE_UNINIT), manualPitchAngle(0),
onboardTimeOffset(0) manualYawAngle(0),
manualThrust(0)
{ {
uasId = id; uasId = id;
setBattery(LIPOLY, 3); setBattery(LIPOLY, 3);
...@@ -94,7 +97,6 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message) ...@@ -94,7 +97,6 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message)
QString uasState; QString uasState;
QString stateDescription; QString stateDescription;
QString patternPath; QString patternPath;
bool uasIsAuto;
switch (message.msgid) switch (message.msgid)
{ {
case MAVLINK_MSG_ID_HEARTBEAT: case MAVLINK_MSG_ID_HEARTBEAT:
...@@ -107,8 +109,6 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message) ...@@ -107,8 +109,6 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message)
} }
break; break;
case MAVLINK_MSG_ID_BOOT: case MAVLINK_MSG_ID_BOOT:
//std::cerr << "Boot detected, software v." << std::dec << message_boot_get_version(message.payload) << " time: " << MG::TIME::getGroundTimeNow() << std::endl;
//emit valueChanged(uasId, "Software version", message_boot_get_version(message.payload), MG::TIME::getGroundTimeNow());
getStatusForCode((int)MAV_STATE_BOOT, uasState, stateDescription); getStatusForCode((int)MAV_STATE_BOOT, uasState, stateDescription);
emit statusChanged(this, uasState, stateDescription); emit statusChanged(this, uasState, stateDescription);
onboardTimeOffset = 0; // Reset offset measurement onboardTimeOffset = 0; // Reset offset measurement
...@@ -117,37 +117,56 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message) ...@@ -117,37 +117,56 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message)
{ {
sys_status_t state; sys_status_t state;
message_sys_status_decode(&message, &state); message_sys_status_decode(&message, &state);
getStatusForCode((int)state.status, uasState, stateDescription);
emit statusChanged(this, uasState, stateDescription);
QString mode; QString audiostring = "System " + QString::number(this->getUASID());
QString stateAudio = "";
QString modeAudio = "";
bool statechanged = false;
bool modechanged = false;
switch (state.mode) if (state.status != this->status)
{ {
case MAV_MODE_LOCKED: statechanged = true;
mode = "MAV_MODE_LOCKED"; this->status = state.status;
break; getStatusForCode((int)state.status, uasState, stateDescription);
case MAV_MODE_MANUAL: emit statusChanged(this, uasState, stateDescription);
mode = "MAV_MODE_MANUAL"; stateAudio = "changed status to " + uasState;
break;
case MAV_MODE_AUTO:
mode = "MAV_MODE_AUTO";
break;
case MAV_MODE_TEST1:
mode = "MAV_MODE_TEST1";
break;
case MAV_MODE_TEST2:
mode = "MAV_MODE_TEST2";
break;
case MAV_MODE_TEST3:
mode = "MAV_MODE_TEST3";
break;
default:
mode = "MAV_MODE_UNINIT";
break;
} }
emit modeChanged(this->getUASID(), mode, ""); if (static_cast<int>(this->mode) != static_cast<int>(state.mode))
{
modechanged = true;
this->mode = state.mode;
QString mode;
switch (state.mode)
{
case MAV_MODE_LOCKED:
mode = "LOCKED MODE";
break;
case MAV_MODE_MANUAL:
mode = "MANUAL MODE";
break;
case MAV_MODE_AUTO:
mode = "AUTO MODE";
break;
case MAV_MODE_TEST1:
mode = "TEST1 MODE";
break;
case MAV_MODE_TEST2:
mode = "TEST2 MODE";
break;
case MAV_MODE_TEST3:
mode = "TEST3 MODE";
break;
default:
mode = "UNINIT MODE";
break;
}
emit modeChanged(this->getUASID(), mode, "");
modeAudio = " is now in " + mode;
}
currentVoltage = state.vbat; currentVoltage = state.vbat;
filterVoltage(currentVoltage); filterVoltage(currentVoltage);
if (startVoltage == 0) startVoltage = currentVoltage; if (startVoltage == 0) startVoltage = currentVoltage;
...@@ -155,6 +174,27 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message) ...@@ -155,6 +174,27 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message)
//qDebug() << "Voltage: " << currentVoltage << " Chargelevel: " << getChargeLevel() << " Time remaining " << timeRemaining; //qDebug() << "Voltage: " << currentVoltage << " Chargelevel: " << getChargeLevel() << " Time remaining " << timeRemaining;
emit batteryChanged(this, filterVoltage(), getChargeLevel(), timeRemaining); emit batteryChanged(this, filterVoltage(), getChargeLevel(), timeRemaining);
emit voltageChanged(message.sysid, state.vbat/1000.0f); emit voltageChanged(message.sysid, state.vbat/1000.0f);
// Output audio
if (modechanged && statechanged)
{
// Output both messages
audiostring += modeAudio + " and " + stateAudio;
}
else
{
// Output the one message
audiostring += modeAudio + stateAudio;
}
if (state.status == (int)MAV_STATE_CRITICAL || state.status == (int)MAV_STATE_EMERGENCY)
{
GAudioOutput::instance()->startEmergency();
}
else if (modechanged || statechanged)
{
GAudioOutput::instance()->stopEmergency();
GAudioOutput::instance()->say(audiostring);
}
} }
break; break;
case MAVLINK_MSG_ID_RAW_IMU: case MAVLINK_MSG_ID_RAW_IMU:
...@@ -212,40 +252,14 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message) ...@@ -212,40 +252,14 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message)
emit attitudeChanged(this, message_attitude_get_roll(&message), message_attitude_get_pitch(&message), message_attitude_get_yaw(&message), time); emit attitudeChanged(this, message_attitude_get_roll(&message), message_attitude_get_pitch(&message), message_attitude_get_yaw(&message), time);
} }
break; break;
//case MAVLINK_MSG_ID_DEBUG:
// emit valueChanged(uasId, QString("debug ") + QString::number(message_debug_get_index(message.payload)), message_debug_get_value(message.payload), MG::TIME::getGroundTimeNow());
// break;
/* /*
case MAVLINK_MSG_ID_DEBUG: case MAVLINK_MSG_ID_WP:
emit valueChanged(uasId, QString("debug ") + QString::number(message_debug_get_index(message.payload)), message_debug_get_value(message.payload), MG::TIME::getGroundTimeNow());
break;
case MAVLINK_MSG_ID_MODE:
{
switch(static_cast<int>(message_mode_get_mode(message.payload)))
{
case (int)MAV_MODE_MANUAL:
{
uasIsAuto = false;
}
break;
case (int)MAV_MODE_AUTO:
{
uasIsAuto = true;
}
break;
default:
{
uasIsAuto = false;
}
break;
}
emit autoModeChanged(mode);
emit valueChanged(uasId, "auto mode", static_cast<int>(message_mode_get_mode(message.payload)), MG::TIME::getGroundTimeNow());
//qDebug() << "UAS MODE CHANGED TO AUTO, UAS MODE CHANGED TO AUTO, UAS MODE CHANGED TO AUTO, UAS MODE CHANGED TO AUTO, UAS MODE CHANGED TO AUTO, UAS MODE CHANGED TO AUTO, UAS MODE CHANGED TO AUTO:" << uasIsAuto;
}
break;
case MAVLINK_MSG_ID_EMITWAYPT:
emit waypointUpdated(this->getUASID(), message_emitwaypoint_get_id(message.payload), message_emitwaypoint_get_x(message.payload), message_emitwaypoint_get_y(message.payload), message_emitwaypoint_get_z(message.payload), message_emitwaypoint_get_yaw(message.payload), (message_emitwaypoint_get_autocontinue(message.payload) == 1 ? true : false), (message_emitwaypoint_get_active(message.payload) == 1 ? true : false)); emit waypointUpdated(this->getUASID(), message_emitwaypoint_get_id(message.payload), message_emitwaypoint_get_x(message.payload), message_emitwaypoint_get_y(message.payload), message_emitwaypoint_get_z(message.payload), message_emitwaypoint_get_yaw(message.payload), (message_emitwaypoint_get_autocontinue(message.payload) == 1 ? true : false), (message_emitwaypoint_get_active(message.payload) == 1 ? true : false));
break; break;
case MAVLINK_MSG_ID_GOTOWAYPT: case MAVLINK_MSG_ID_SET_POSITION:
emit valueChanged(uasId, "WP X", message_gotowaypoint_get_x(message.payload), MG::TIME::getGroundTimeNow()); emit valueChanged(uasId, "WP X", message_gotowaypoint_get_x(message.payload), MG::TIME::getGroundTimeNow());
emit valueChanged(uasId, "WP Y", message_gotowaypoint_get_y(message.payload), MG::TIME::getGroundTimeNow()); emit valueChanged(uasId, "WP Y", message_gotowaypoint_get_y(message.payload), MG::TIME::getGroundTimeNow());
emit valueChanged(uasId, "WP Z", message_gotowaypoint_get_z(message.payload), MG::TIME::getGroundTimeNow()); emit valueChanged(uasId, "WP Z", message_gotowaypoint_get_z(message.payload), MG::TIME::getGroundTimeNow());
...@@ -258,41 +272,19 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message) ...@@ -258,41 +272,19 @@ void UAS::receiveMessage(LinkInterface* link, mavlink_message_t message)
qDebug() << "WAYPOINT REACHED"; qDebug() << "WAYPOINT REACHED";
emit waypointReached(this, message_wp_reached_get_id(message.payload)); emit waypointReached(this, message_wp_reached_get_id(message.payload));
break; break;
case MAVLINK_MSG_ID_DETECTION: case MAVLINK_MSG_ID_OBJ_DETECTED:
patternPath = QString(message_detection_get_patternpath(message.payload)); //patternPath = QString(message_detection_get_patternpath(message.payload));
//qDebug() << "OBJECT DETECTED"; //qDebug() << "OBJECT DETECTED";
emit detectionReceived(uasId, patternPath, 0, 0, 0, 0, 0, 0, 0, 0, message_detection_get_confidence(message.payload), (message_detection_get_detected(message.payload) == 1 ? true : false )); //emit detectionReceived(uasId, patternPath, 0, 0, 0, 0, 0, 0, 0, 0, message_detection_get_confidence(message.payload), (message_detection_get_detected(message.payload) == 1 ? true : false ));
break; break;
*/
default: default:
std::cerr << "Unable to decode message from system " << std::dec << static_cast<int>(message.acid) << " with message id:" << static_cast<int>(message.msgid) << std::endl; GAudioOutput::instance()->say("COMM ERROR: UNABLE TO DECODE MESSAGE WITH ID" + QString::number(message.msgid) + "FROM SYSTEM " + QString::number(message.sysid));
std::cerr << "Unable to decode message from system " << std::dec << static_cast<int>(message.sysid) << " with message id:" << static_cast<int>(message.msgid) << std::endl;
//qDebug() << std::cerr << "Unable to decode message from system " << std::dec << static_cast<int>(message.acid) << " with message id:" << static_cast<int>(message.msgid) << std::endl; //qDebug() << std::cerr << "Unable to decode message from system " << std::dec << static_cast<int>(message.acid) << " with message id:" << static_cast<int>(message.msgid) << std::endl;
break; break;
*/
} }
} }
// virtual void attitudeChanged(int uasId, double roll, double pitch, double yaw, quint64 usec);
// virtual void localPositionChanged(int uasId, double x, double y, double z, quint64 usec);
// virtual void globalPositionChanged(int uasId, double lon, double lat, double alt, quint64 usec);
// virtual void actuatorsChanged(int uasId, double actuator1, double actuator2, double actuator3, double actuator4, double actuator5);
// virtual void voltageChanged(int uasId, double voltage);
}
void UAS::setAutoMode(bool autoMode)
{
mavlink_message_t msg;
if (autoMode)
{
message_set_mode_pack(MG::SYSTEM::ID, MG::SYSTEM::COMPID, &msg, getUASID(), (unsigned char)MAV_MODE_AUTO);
mode = MAV_MODE_AUTO;
sendMessage(msg);
}
else
{
message_set_mode_pack(MG::SYSTEM::ID, MG::SYSTEM::COMPID, &msg, getUASID(), (unsigned char)MAV_MODE_MANUAL);
mode = MAV_MODE_MANUAL;
sendMessage(msg);
}
} }
void UAS::setMode(int mode) void UAS::setMode(int mode)
...@@ -501,10 +493,10 @@ void UAS::receiveButton(int buttonIndex) ...@@ -501,10 +493,10 @@ void UAS::receiveButton(int buttonIndex)
switch (buttonIndex) switch (buttonIndex)
{ {
case 0: case 0:
setAutoMode(false);
break; break;
case 1: case 1:
setAutoMode(true);
break; break;
default: default:
...@@ -631,7 +623,7 @@ void UAS::shutdown() ...@@ -631,7 +623,7 @@ void UAS::shutdown()
/** /**
* @return The name of this system as string in human-readable form * @return The name of this system as string in human-readable form
*/ */
QString UAS::getUASName() QString UAS::getUASName(void)
{ {
QString result; QString result;
if (name == "") if (name == "")
......
/*===================================================================== /*=====================================================================
PIXHAWK Micro Air Vehicle Flying Robotics Toolkit PIXHAWK Micro Air Vehicle Flying Robotics Toolkit
Please see our website at <http://pixhawk.ethz.ch>
(c) 2009, 2010 PIXHAWK PROJECT <http://pixhawk.ethz.ch> (c) 2009, 2010 PIXHAWK PROJECT <http://pixhawk.ethz.ch>
...@@ -33,7 +32,6 @@ This file is part of the PIXHAWK project ...@@ -33,7 +32,6 @@ This file is part of the PIXHAWK project
#ifndef _UAS_H_ #ifndef _UAS_H_
#define _UAS_H_ #define _UAS_H_
#include <QDebug>
#include "UASInterface.h" #include "UASInterface.h"
#include "MG.h" #include "MG.h"
#include <mavlink.h> #include <mavlink.h>
...@@ -67,7 +65,7 @@ public: ...@@ -67,7 +65,7 @@ public:
/* MANAGEMENT */ /* MANAGEMENT */
/** @brief The name of the robot */ /** @brief The name of the robot */
QString getUASName(); QString getUASName(void);
/** @brief Get the unique system id */ /** @brief Get the unique system id */
int getUASID(); int getUASID();
/** @brief The time interval the robot is switched on */ /** @brief The time interval the robot is switched on */
...@@ -83,13 +81,13 @@ public: ...@@ -83,13 +81,13 @@ public:
protected: protected:
int type; int type;
quint64 startTime; ///< The time the UAS was switched on quint64 startTime; ///< The time the UAS was switched on
CommStatus commStatus; ///< Communication status CommStatus commStatus; ///< Communication status
int uasId; ///< Unique system ID int uasId; ///< Unique system ID
QString name; ///< Human-friendly name of the vehicle, e.g. bravo QString name; ///< Human-friendly name of the vehicle, e.g. bravo
QList<LinkInterface*>* links; ///< List of links this UAS can be reached by QList<LinkInterface*>* links; ///< List of links this UAS can be reached by
BatteryType batteryType; ///< The battery type BatteryType batteryType; ///< The battery type
int cells; ///< Number of cells int cells; ///< Number of cells
QList<double> actuatorValues; QList<double> actuatorValues;
QList<QString> actuatorNames; QList<QString> actuatorNames;
...@@ -97,27 +95,30 @@ protected: ...@@ -97,27 +95,30 @@ protected:
QList<double> motorValues; QList<double> motorValues;
QList<QString> motorNames; QList<QString> motorNames;
double thrustSum; ///< Sum of forward/up thrust of all thrust actuators double thrustSum; ///< Sum of forward/up thrust of all thrust actuators, in Newtons
double thrustMax; ///< Maximum forward/up thrust of this vehicle, in Newtons
// Battery stats // Battery stats
double fullVoltage; ///< Voltage of the fully charged battery (100%) double fullVoltage; ///< Voltage of the fully charged battery (100%)
double emptyVoltage; ///< Voltage of the empty battery (0%) double emptyVoltage; ///< Voltage of the empty battery (0%)
double startVoltage; ///< Voltage at system start double startVoltage; ///< Voltage at system start
double currentVoltage; ///< Voltage currently measured double currentVoltage; ///< Voltage currently measured
float lpVoltage; ///< Low-pass filtered voltage float lpVoltage; ///< Low-pass filtered voltage
int timeRemaining; ///< Remaining time calculated based on previous and current int timeRemaining; ///< Remaining time calculated based on previous and current
double manualRollAngle; ///< Roll angle set by human pilot (radians) int mode; ///< The current mode of the MAV
double manualPitchAngle; ///< Pitch angle set by human pilot (radians) int status; ///< The current status of the MAV
double manualYawAngle; ///< Yaw angle set by human pilot (radians)
double manualThrust; ///< Thrust set by human pilot (radians)
bool controlRollManual; ///< status flag, true if roll is controlled manually
bool controlPitchManual; ///< status flag, true if pitch is controlled manually
bool controlYawManual; ///< status flag, true if yaw is controlled manually
bool controlThrustManual;///< status flag, true if thrust is controlled manually
int mode; ///< The current mode of the MAV
quint64 onboardTimeOffset; quint64 onboardTimeOffset;
bool controlRollManual; ///< status flag, true if roll is controlled manually
bool controlPitchManual; ///< status flag, true if pitch is controlled manually
bool controlYawManual; ///< status flag, true if yaw is controlled manually
bool controlThrustManual; ///< status flag, true if thrust is controlled manually
double manualRollAngle; ///< Roll angle set by human pilot (radians)
double manualPitchAngle; ///< Pitch angle set by human pilot (radians)
double manualYawAngle; ///< Yaw angle set by human pilot (radians)
double manualThrust; ///< Thrust set by human pilot (radians)
/** @brief Set the current battery type */ /** @brief Set the current battery type */
void setBattery(BatteryType type, int cells); void setBattery(BatteryType type, int cells);
/** @brief Estimate how much flight time is remaining */ /** @brief Estimate how much flight time is remaining */
...@@ -147,8 +148,6 @@ public slots: ...@@ -147,8 +148,6 @@ public slots:
/** @brief Shut the system cleanly down. Will shut down any onboard computers **/ /** @brief Shut the system cleanly down. Will shut down any onboard computers **/
void shutdown(); void shutdown();
/** @brief Set the auto mode. **/
void setAutoMode(bool autoMode);
void requestWaypoints(); void requestWaypoints();
void clearWaypointList(); void clearWaypointList();
/** @brief Enable the motors */ /** @brief Enable the motors */
...@@ -161,9 +160,7 @@ public slots: ...@@ -161,9 +160,7 @@ public slots:
/** @brief Receive a button pressed event from an input device, e.g. joystick */ /** @brief Receive a button pressed event from an input device, e.g. joystick */
void receiveButton(int buttonIndex); void receiveButton(int buttonIndex);
/** /** @brief Add a link associated with this robot */
* @brief Add a link associated with this robot
*/
void addLink(LinkInterface* link); void addLink(LinkInterface* link);
/** @brief Receive a message from one of the communication links. */ /** @brief Receive a message from one of the communication links. */
......
...@@ -110,8 +110,7 @@ public: ...@@ -110,8 +110,7 @@ public:
{ {
///> Color map for plots, includes 20 colors ///> Color map for plots, includes 20 colors
///> Map will start from beginning when the first 20 colors are exceeded ///> Map will start from beginning when the first 20 colors are exceeded
colors.append(QColor(242,255,128));
colors.append(QColor(230,126,23));
colors.append(QColor(203,254,121)); colors.append(QColor(203,254,121));
colors.append(QColor(231,72,28)); colors.append(QColor(231,72,28));
colors.append(QColor(161,252,116)); colors.append(QColor(161,252,116));
...@@ -129,6 +128,8 @@ public: ...@@ -129,6 +128,8 @@ public:
colors.append(QColor(81,183,244)); colors.append(QColor(81,183,244));
colors.append(QColor(104,64,240)); colors.append(QColor(104,64,240));
colors.append(QColor(75,133,243)); colors.append(QColor(75,133,243));
colors.append(QColor(242,255,128));
colors.append(QColor(230,126,23));
nextColor++; nextColor++;
} }
return colors[nextColor++]; return colors[nextColor++];
...@@ -153,12 +154,7 @@ public slots: ...@@ -153,12 +154,7 @@ public slots:
virtual void halt() = 0; virtual void halt() = 0;
/** @brief Start/continue the current robot action */ /** @brief Start/continue the current robot action */
virtual void go() = 0; virtual void go() = 0;
/** @brief Set robot into auto mode /** @brief Set the current mode of operation */
*
* @param autoMode true for autonomous operation, false for manual control
*/
virtual void setAutoMode(bool autoMode) = 0;
virtual void setMode(int mode) = 0; virtual void setMode(int mode) = 0;
/** Stops the robot system. If it is an MAV, the robot starts the emergency landing procedure **/ /** Stops the robot system. If it is an MAV, the robot starts the emergency landing procedure **/
virtual void emergencySTOP() = 0; virtual void emergencySTOP() = 0;
......
...@@ -23,7 +23,7 @@ This file is part of the PIXHAWK project ...@@ -23,7 +23,7 @@ This file is part of the PIXHAWK project
/** /**
* @file * @file
* @brief Central manager for all connected aerial vehicles * @brief Implementation of central manager for all connected aerial vehicles
* @author Lorenz Meier <mavteam@student.ethz.ch> * @author Lorenz Meier <mavteam@student.ethz.ch>
* *
*/ */
...@@ -41,8 +41,8 @@ UASManager* UASManager::instance() { ...@@ -41,8 +41,8 @@ UASManager* UASManager::instance() {
if(_instance == 0) { if(_instance == 0) {
_instance = new UASManager(); _instance = new UASManager();
/* Set the application as parent to ensure that this object // Set the application as parent to ensure that this object
* will be destroyed when the main application exits */ // will be destroyed when the main application exits
_instance->setParent(qApp); _instance->setParent(qApp);
} }
return _instance; return _instance;
...@@ -144,12 +144,6 @@ bool UASManager::shutdownActiveUAS() ...@@ -144,12 +144,6 @@ bool UASManager::shutdownActiveUAS()
return (activeUAS); return (activeUAS);
} }
bool UASManager::setActiveUASAuto(bool autoMode)
{
if (getActiveUAS()) activeUAS->setAutoMode(autoMode);
return (activeUAS);
}
void UASManager::configureActiveUAS() void UASManager::configureActiveUAS()
{ {
UASInterface* actUAS = getActiveUAS(); UASInterface* actUAS = getActiveUAS();
...@@ -165,14 +159,17 @@ UASInterface* UASManager::getUASForId(int id) ...@@ -165,14 +159,17 @@ UASInterface* UASManager::getUASForId(int id)
return systems.value(id, NULL); return systems.value(id, NULL);
} }
void UASManager::setActiveUAS(UASInterface* UAS) void UASManager::setActiveUAS(UASInterface* uas)
{ {
activeUASMutex.lock(); if (uas != NULL)
activeUAS = UAS; {
activeUASMutex.unlock(); activeUASMutex.lock();
activeUAS = uas;
activeUASMutex.unlock();
qDebug() << __FILE__ << ":" << __LINE__ << " ACTIVE UAS SET TO: " << UAS->getUASName(); qDebug() << __FILE__ << ":" << __LINE__ << " ACTIVE UAS SET TO: " << uas->getUASName();
emit activeUASSet(UAS); emit activeUASSet(uas);
}
} }
...@@ -23,7 +23,7 @@ This file is part of the PIXHAWK project ...@@ -23,7 +23,7 @@ This file is part of the PIXHAWK project
/** /**
* @file * @file
* @brief Central manager for all connected aerial vehicles * @brief Definition of central manager for all connected aerial vehicles
* @author Lorenz Meier <mavteam@student.ethz.ch> * @author Lorenz Meier <mavteam@student.ethz.ch>
* *
*/ */
...@@ -153,10 +153,9 @@ public slots: ...@@ -153,10 +153,9 @@ public slots:
*/ */
void configureActiveUAS(); void configureActiveUAS();
/** @brief Shut down the onboard operating system down */
bool shutdownActiveUAS(); bool shutdownActiveUAS();
bool setActiveUASAuto(bool autoMode);
protected: protected:
UASManager(); UASManager();
...@@ -164,9 +163,6 @@ protected: ...@@ -164,9 +163,6 @@ protected:
UASInterface* activeUAS; UASInterface* activeUAS;
QMutex activeUASMutex; QMutex activeUASMutex;
private:
static UASManager* _instance;
signals: signals:
void UASCreated(UASInterface* UAS); void UASCreated(UASInterface* UAS);
void activeUASSet(UASInterface* UAS); void activeUASSet(UASInterface* UAS);
......
...@@ -108,10 +108,14 @@ DebugConsole::~DebugConsole() ...@@ -108,10 +108,14 @@ DebugConsole::~DebugConsole()
delete m_ui; delete m_ui;
} }
/**
* Add a link to the debug console output
*/
void DebugConsole::addLink(LinkInterface* link) void DebugConsole::addLink(LinkInterface* link)
{ {
// Add link to link list // Add link to link list
links.insert(link->getId(), link); links.insert(link->getId(), link);
m_ui->linkComboBox->insertItem(link->getId(), link->getName()); m_ui->linkComboBox->insertItem(link->getId(), link->getName());
// Set new item as current // Set new item as current
m_ui->linkComboBox->setCurrentIndex(qMax(0, links.size() - 1)); m_ui->linkComboBox->setCurrentIndex(qMax(0, links.size() - 1));
......
...@@ -45,6 +45,7 @@ This file is part of the PIXHAWK project ...@@ -45,6 +45,7 @@ This file is part of the PIXHAWK project
#include "WaypointList.h" #include "WaypointList.h"
#include "MainWindow.h" #include "MainWindow.h"
#include "JoystickWidget.h" #include "JoystickWidget.h"
#include "GAudioOutput.h"
#include "LogCompressor.h" #include "LogCompressor.h"
...@@ -56,7 +57,7 @@ This file is part of the PIXHAWK project ...@@ -56,7 +57,7 @@ This file is part of the PIXHAWK project
* *
* @see QMainWindow::show() * @see QMainWindow::show()
**/ **/
MGMainWindow::MGMainWindow(QWidget *parent) : QMainWindow(parent) MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent)
{ {
// Quick hack // Quick hack
...@@ -167,20 +168,20 @@ MGMainWindow::MGMainWindow(QWidget *parent) : QMainWindow(parent) ...@@ -167,20 +168,20 @@ MGMainWindow::MGMainWindow(QWidget *parent) : QMainWindow(parent)
udpLink->connect(); udpLink->connect();
simulationLink = new MAVLinkSimulationLink(MG::DIR::getSupportFilesDirectory() + "/demo-log.txt"); simulationLink = new MAVLinkSimulationLink(MG::DIR::getSupportFilesDirectory() + "/demo-log.txt");
connect(simulationLink, SIGNAL(valueChanged(int,QString,double,quint64)), linechart, SLOT(appendData(int,QString,double,quint64))); //connect(simulationLink, SIGNAL(valueChanged(int,QString,double,quint64)), linechart, SLOT(appendData(int,QString,double,quint64)));
LinkManager::instance()->addProtocol(simulationLink, mavlink); LinkManager::instance()->addProtocol(simulationLink, mavlink);
//CommConfigurationWindow* simulationWidget = new CommConfigurationWindow(simulationLink, mavlink, this); //CommConfigurationWindow* simulationWidget = new CommConfigurationWindow(simulationLink, mavlink, this);
//ui.menuNetwork->addAction(commWidget->getAction()); //ui.menuNetwork->addAction(commWidget->getAction());
simulationLink->connect(); simulationLink->connect();
} }
MGMainWindow::~MGMainWindow() MainWindow::~MainWindow()
{ {
delete statusBar; delete statusBar;
statusBar = NULL; statusBar = NULL;
} }
QStatusBar* MGMainWindow::createStatusBar() QStatusBar* MainWindow::createStatusBar()
{ {
QStatusBar* bar = new QStatusBar(); QStatusBar* bar = new QStatusBar();
/* Add status fields and messages */ /* Add status fields and messages */
...@@ -189,7 +190,7 @@ QStatusBar* MGMainWindow::createStatusBar() ...@@ -189,7 +190,7 @@ QStatusBar* MGMainWindow::createStatusBar()
return bar; return bar;
} }
void MGMainWindow::startVideoCapture() void MainWindow::startVideoCapture()
{ {
QString format = "bmp"; QString format = "bmp";
QString initialPath = QDir::currentPath() + tr("/untitled.") + format; QString initialPath = QDir::currentPath() + tr("/untitled.") + format;
...@@ -205,14 +206,14 @@ void MGMainWindow::startVideoCapture() ...@@ -205,14 +206,14 @@ void MGMainWindow::startVideoCapture()
connect(videoTimer, SIGNAL(timeout()), this, SLOT(saveScreen())); connect(videoTimer, SIGNAL(timeout()), this, SLOT(saveScreen()));
} }
void MGMainWindow::stopVideoCapture() void MainWindow::stopVideoCapture()
{ {
videoTimer->stop(); videoTimer->stop();
// TODO Convert raw images to PNG // TODO Convert raw images to PNG
} }
void MGMainWindow::saveScreen() void MainWindow::saveScreen()
{ {
QPixmap window = QPixmap::grabWindow(this->winId()); QPixmap window = QPixmap::grabWindow(this->winId());
QString format = "bmp"; QString format = "bmp";
...@@ -223,7 +224,7 @@ void MGMainWindow::saveScreen() ...@@ -223,7 +224,7 @@ void MGMainWindow::saveScreen()
} }
} }
void MGMainWindow::reloadStylesheet() void MainWindow::reloadStylesheet()
{ {
// Load style sheet // Load style sheet
//QFile styleSheet(MG::DIR::getSupportFilesDirectory() + "/images/style-mission.css"); //QFile styleSheet(MG::DIR::getSupportFilesDirectory() + "/images/style-mission.css");
...@@ -237,17 +238,17 @@ void MGMainWindow::reloadStylesheet() ...@@ -237,17 +238,17 @@ void MGMainWindow::reloadStylesheet()
} }
} }
void MGMainWindow::showStatusMessage(const QString& status, int timeout) void MainWindow::showStatusMessage(const QString& status, int timeout)
{ {
statusBar->showMessage(status, timeout); statusBar->showMessage(status, timeout);
} }
void MGMainWindow::setLastAction(QString status) void MainWindow::setLastAction(QString status)
{ {
showStatusMessage(status, 5); showStatusMessage(status, 5);
} }
void MGMainWindow::setLinkStatus(QString status) void MainWindow::setLinkStatus(QString status)
{ {
showStatusMessage(status, 15); showStatusMessage(status, 15);
} }
...@@ -256,7 +257,7 @@ void MGMainWindow::setLinkStatus(QString status) ...@@ -256,7 +257,7 @@ void MGMainWindow::setLinkStatus(QString status)
* @brief Create all actions associated to the main window * @brief Create all actions associated to the main window
* *
**/ **/
void MGMainWindow::connectActions() void MainWindow::connectActions()
{ {
// Connect actions from ui // Connect actions from ui
connect(ui.actionAdd_Link, SIGNAL(triggered()), this, SLOT(addLink())); connect(ui.actionAdd_Link, SIGNAL(triggered()), this, SLOT(addLink()));
...@@ -283,12 +284,12 @@ void MGMainWindow::connectActions() ...@@ -283,12 +284,12 @@ void MGMainWindow::connectActions()
connect(ui.actionJoystickSettings, SIGNAL(triggered()), this, SLOT(configure())); connect(ui.actionJoystickSettings, SIGNAL(triggered()), this, SLOT(configure()));
} }
void MGMainWindow::configure() void MainWindow::configure()
{ {
joystickWidget = new JoystickWidget(joystick, this); joystickWidget = new JoystickWidget(joystick, this);
} }
void MGMainWindow::addLink() void MainWindow::addLink()
{ {
SerialLink* link = new SerialLink(); SerialLink* link = new SerialLink();
// TODO This should be only done in the dialog itself // TODO This should be only done in the dialog itself
...@@ -304,13 +305,19 @@ void MGMainWindow::addLink() ...@@ -304,13 +305,19 @@ void MGMainWindow::addLink()
// TODO Implement the link removal! // TODO Implement the link removal!
} }
void MGMainWindow::UASCreated(UASInterface* uas) void MainWindow::UASCreated(UASInterface* uas)
{ {
// Connect the UAS to the full user interface // Connect the UAS to the full user interface
ui.menuConnected_Systems->addAction(QIcon(":/actions/linechart.svg"), tr("View ") + uas->getUASName(), uas, SLOT(setSelected())); ui.menuConnected_Systems->addAction(QIcon(":/images/mavs/generic.svg"), tr("View ") + uas->getUASName(), uas, SLOT(setSelected()));
// Line chart // Line chart
connect(uas, SIGNAL(valueChanged(int,QString,double,quint64)), linechart, SLOT(appendData(int,QString,double,quint64)), Qt::QueuedConnection); // FIXME DO THIS ONLY FOR THE FIRST CONNECTED SYSTEM
static bool sysPresent = false;
if (!sysPresent)
{
connect(uas, SIGNAL(valueChanged(int,QString,double,quint64)), linechart, SLOT(appendData(int,QString,double,quint64)), Qt::QueuedConnection);
sysPresent = true;
}
// Health / System status indicator // Health / System status indicator
info->addUAS(uas); info->addUAS(uas);
...@@ -326,12 +333,12 @@ void MGMainWindow::UASCreated(UASInterface* uas) ...@@ -326,12 +333,12 @@ void MGMainWindow::UASCreated(UASInterface* uas)
reloadStylesheet(); reloadStylesheet();
} }
void MGMainWindow::clearView() void MainWindow::clearView()
{ {
// Halt HUD // Halt HUD
hud->stop(); hud->stop();
/*headDown1->stop(); headDown1->stop();
headDown2->stop();*/ headDown2->stop();
// Remove all dock widgets // Remove all dock widgets
QList<QObject*> list = this->children(); QList<QObject*> list = this->children();
...@@ -352,9 +359,10 @@ void MGMainWindow::clearView() ...@@ -352,9 +359,10 @@ void MGMainWindow::clearView()
} }
} }
void MGMainWindow::loadPilotView() void MainWindow::loadPilotView()
{ {
clearView(); clearView();
GAudioOutput::instance()->say("Switched to Pilot View");
// HEAD UP DISPLAY // HEAD UP DISPLAY
centerStack->setCurrentWidget(hud); centerStack->setCurrentWidget(hud);
...@@ -376,10 +384,12 @@ void MGMainWindow::loadPilotView() ...@@ -376,10 +384,12 @@ void MGMainWindow::loadPilotView()
this->show(); this->show();
} }
void MGMainWindow::loadOperatorView() void MainWindow::loadOperatorView()
{ {
clearView(); clearView();
GAudioOutput::instance()->say("Switched to Operator View");
// LINE CHART // LINE CHART
centerStack->setCurrentWidget(map); centerStack->setCurrentWidget(map);
...@@ -416,10 +426,12 @@ void MGMainWindow::loadOperatorView() ...@@ -416,10 +426,12 @@ void MGMainWindow::loadOperatorView()
this->show(); this->show();
} }
void MGMainWindow::loadSettingsView() void MainWindow::loadSettingsView()
{ {
clearView(); clearView();
GAudioOutput::instance()->say("Switched to Settings View");
// LINE CHART // LINE CHART
centerStack->setCurrentWidget(linechart); centerStack->setCurrentWidget(linechart);
...@@ -434,11 +446,13 @@ void MGMainWindow::loadSettingsView() ...@@ -434,11 +446,13 @@ void MGMainWindow::loadSettingsView()
addDockWidget(Qt::RightDockWidgetArea, container6); addDockWidget(Qt::RightDockWidgetArea, container6);
} }
void MGMainWindow::loadEngineerView() void MainWindow::loadEngineerView()
{ {
clearView(); clearView();
// Engineer view, used in EMAV2009 // Engineer view, used in EMAV2009
GAudioOutput::instance()->say("Switched to Engineer View");
// LINE CHART // LINE CHART
centerStack->setCurrentWidget(linechart); centerStack->setCurrentWidget(linechart);
...@@ -470,7 +484,7 @@ void MGMainWindow::loadEngineerView() ...@@ -470,7 +484,7 @@ void MGMainWindow::loadEngineerView()
this->show(); this->show();
} }
void MGMainWindow::loadWidgets() void MainWindow::loadWidgets()
{ {
loadOperatorView(); loadOperatorView();
//loadEngineerView(); //loadEngineerView();
...@@ -478,32 +492,32 @@ void MGMainWindow::loadWidgets() ...@@ -478,32 +492,32 @@ void MGMainWindow::loadWidgets()
} }
/* /*
void MGMainWindow::removeCommConfAct(QAction* action) void MainWindow::removeCommConfAct(QAction* action)
{ {
ui.menuNetwork->removeAction(action); ui.menuNetwork->removeAction(action);
}*/ }*/
//void MGMainWindow::startUAS() //void MainWindow::startUAS()
//{ //{
// UASManager::instance()->getActiveUAS()->launch(); // UASManager::instance()->getActiveUAS()->launch();
//} //}
// //
//void MGMainWindow::returnUAS() //void MainWindow::returnUAS()
//{ //{
// UASManager::instance()->getActiveUAS()->home(); // UASManager::instance()->getActiveUAS()->home();
//} //}
// //
//void MGMainWindow::stopUAS() //void MainWindow::stopUAS()
//{ //{
// UASManager::instance()->getActiveUAS()->emergencySTOP(); // UASManager::instance()->getActiveUAS()->emergencySTOP();
//} //}
// //
//void MGMainWindow::killUAS() //void MainWindow::killUAS()
//{ //{
// UASManager::instance()->getActiveUAS()->emergencyKILL(); // UASManager::instance()->getActiveUAS()->emergencyKILL();
//} //}
void MGMainWindow::runTests() void MainWindow::runTests()
{ {
// TODO Remove after debugging: Add fake data // TODO Remove after debugging: Add fake data
static double testvalue = 0.0f; static double testvalue = 0.0f;
......
...@@ -67,12 +67,12 @@ This file is part of the PIXHAWK project ...@@ -67,12 +67,12 @@ This file is part of the PIXHAWK project
* @brief Main Application Window * @brief Main Application Window
* *
**/ **/
class MGMainWindow : public QMainWindow { class MainWindow : public QMainWindow {
Q_OBJECT Q_OBJECT
public: public:
MGMainWindow(QWidget *parent = 0); MainWindow(QWidget *parent = 0);
~MGMainWindow(); ~MainWindow();
UASControlWidget* control; UASControlWidget* control;
LinechartWidget* linechart; LinechartWidget* linechart;
...@@ -161,7 +161,7 @@ protected: ...@@ -161,7 +161,7 @@ protected:
QTimer* videoTimer; QTimer* videoTimer;
private: private:
Ui::MGMainWindow ui; Ui::MainWindow ui;
}; };
#endif /* _MAINWINDOW_H_ */ #endif /* _MAINWINDOW_H_ */
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0"> <ui version="4.0">
<class>MGMainWindow</class> <class>MainWindow</class>
<widget class="QMainWindow" name="MGMainWindow"> <widget class="QMainWindow" name="MainWindow">
<property name="geometry"> <property name="geometry">
<rect> <rect>
<x>0</x> <x>0</x>
...@@ -241,7 +241,7 @@ ...@@ -241,7 +241,7 @@
<connection> <connection>
<sender>actionExit</sender> <sender>actionExit</sender>
<signal>triggered()</signal> <signal>triggered()</signal>
<receiver>MGMainWindow</receiver> <receiver>MainWindow</receiver>
<slot>close()</slot> <slot>close()</slot>
<hints> <hints>
<hint type="sourcelabel"> <hint type="sourcelabel">
......
...@@ -29,14 +29,55 @@ ...@@ -29,14 +29,55 @@
<string>QWidget#colorIcon {} <string>QWidget#colorIcon {}
QWidget { QWidget {
background-color: #252528; background-color: none;
color: #DDDDDF; color: #DDDDDF;
border-color: #EEEEEE; border-color: #EEEEEE;
background-clip: margin; background-clip: margin;
} }
QLabel#nameLabel {
font: bold 16px;
color: #3C7B9E;
}
QLabel#modeLabel {
font: 12px;
}
QLabel#stateLabel {
font: 12px;
}
QLabel#gpsLabel {
font: 8px;
}
QLabel#positionLabel {
font: 8px;
}
QLabel#timeElapsedLabel {
font: 8px;
}
QLabel#groundDistanceLabel {
font: 8px;
}
QLabel#speedLabel {
font: 8px;
}
QLabel#timeRemainingLabel {
font: 8px;
}
QLabel#waypointLabel {
font: 24px;
}
QGroupBox { QGroupBox {
border: 1px solid #EEEEEE; border: 1px solid #4A4A4F;
border-radius: 5px; border-radius: 5px;
padding: 0px 0px 0px 0px; padding: 0px 0px 0px 0px;
margin: 0px; margin: 0px;
...@@ -67,6 +108,19 @@ QToolButton { ...@@ -67,6 +108,19 @@ QToolButton {
background-color: none; background-color: none;
} }
QToolButton#typeButton {
font-weight: bold;
font-size: 12px;
border: 2px solid #999999;
border-radius: 5px;
min-width:44px;
max-width: 44px;
min-height: 44px;
max-height: 44px;
padding: 0px;
background-color: none;
}
QPushButton { QPushButton {
font-weight: bold; font-weight: bold;
font-size: 12px; font-size: 12px;
...@@ -84,41 +138,38 @@ QPushButton:pressed { ...@@ -84,41 +138,38 @@ QPushButton:pressed {
background-color: qlineargradient(x1: 0, y1: 0, x2: 0, y2: 1, stop: 0 #444444, stop: 1 #555555); background-color: qlineargradient(x1: 0, y1: 0, x2: 0, y2: 1, stop: 0 #444444, stop: 1 #555555);
} }
QPushButton#landButton { QPushButton#abortButton {
color: #000000;
background: qlineargradient(x1:0, y1:0, x2:0, y2:1, background: qlineargradient(x1:0, y1:0, x2:0, y2:1,
stop:0 #ffee01, stop:1 #ae8f00) url(&quot;ICONDIR/control/emergency-button.png&quot;); stop:0 #ffee01, stop:1 #ae8f00);
} }
QPushButton:pressed#landButton { QPushButton:pressed#abortButton {
color: #000000;
background: qlineargradient(x1:0, y1:0, x2:0, y2:1, background: qlineargradient(x1:0, y1:0, x2:0, y2:1,
stop:0 #bbaa00, stop:1 #a05b00) url(&quot;ICONDIR/control/emergency-button.png&quot;); stop:0 #bbaa00, stop:1 #a05b00);
} }
QPushButton#killButton { QPushButton#killButton {
color: #000000;
background: qlineargradient(x1:0, y1:0, x2:0, y2:1, background: qlineargradient(x1:0, y1:0, x2:0, y2:1,
stop:0 #ffb917, stop:1 #b37300) url(&quot;ICONDIR/control/emergency-button.png&quot;); stop:0 #ffb917, stop:1 #b37300);
} }
QPushButton:pressed#killButton { QPushButton:pressed#killButton {
color: #000000;
background: qlineargradient(x1:0, y1:0, x2:0, y2:1, background: qlineargradient(x1:0, y1:0, x2:0, y2:1,
stop:0 #bb8500, stop:1 #903000) url(&quot;ICONDIR/control/emergency-button.png&quot;); stop:0 #bb8500, stop:1 #903000);
} }
QProgressBar { QProgressBar {
border: 1px solid white; border: 1px solid #4A4A4F;
border-radius: 4px; border-radius: 4px;
text-align: center; text-align: center;
padding: 2px; padding: 2px;
color: white; color: #DDDDDF;
background-color: #111111; background-color: #111118;
} }
QProgressBar:horizontal { QProgressBar:horizontal {
height: 12px; height: 10px;
} }
QProgressBar QLabel { QProgressBar QLabel {
...@@ -180,14 +231,14 @@ QProgressBar::chunk#thrustBar { ...@@ -180,14 +231,14 @@ QProgressBar::chunk#thrustBar {
<widget class="QToolButton" name="typeButton"> <widget class="QToolButton" name="typeButton">
<property name="minimumSize"> <property name="minimumSize">
<size> <size>
<width>46</width> <width>48</width>
<height>46</height> <height>48</height>
</size> </size>
</property> </property>
<property name="maximumSize"> <property name="maximumSize">
<size> <size>
<width>46</width> <width>48</width>
<height>46</height> <height>48</height>
</size> </size>
</property> </property>
<property name="baseSize"> <property name="baseSize">
...@@ -234,8 +285,9 @@ QProgressBar::chunk#thrustBar { ...@@ -234,8 +285,9 @@ QProgressBar::chunk#thrustBar {
</property> </property>
<property name="font"> <property name="font">
<font> <font>
<pointsize>14</pointsize> <pointsize>-1</pointsize>
<weight>75</weight> <weight>75</weight>
<italic>false</italic>
<bold>true</bold> <bold>true</bold>
</font> </font>
</property> </property>
...@@ -254,8 +306,9 @@ QProgressBar::chunk#thrustBar { ...@@ -254,8 +306,9 @@ QProgressBar::chunk#thrustBar {
</property> </property>
<property name="font"> <property name="font">
<font> <font>
<pointsize>14</pointsize> <pointsize>-1</pointsize>
<weight>50</weight> <weight>50</weight>
<italic>false</italic>
<bold>false</bold> <bold>false</bold>
</font> </font>
</property> </property>
...@@ -268,7 +321,10 @@ QProgressBar::chunk#thrustBar { ...@@ -268,7 +321,10 @@ QProgressBar::chunk#thrustBar {
<widget class="QLabel" name="timeRemainingLabel"> <widget class="QLabel" name="timeRemainingLabel">
<property name="font"> <property name="font">
<font> <font>
<pointsize>8</pointsize> <pointsize>-1</pointsize>
<weight>50</weight>
<italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
...@@ -280,7 +336,10 @@ QProgressBar::chunk#thrustBar { ...@@ -280,7 +336,10 @@ QProgressBar::chunk#thrustBar {
<widget class="QLabel" name="timeElapsedLabel"> <widget class="QLabel" name="timeElapsedLabel">
<property name="font"> <property name="font">
<font> <font>
<pointsize>8</pointsize> <pointsize>-1</pointsize>
<weight>50</weight>
<italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
...@@ -304,7 +363,10 @@ QProgressBar::chunk#thrustBar { ...@@ -304,7 +363,10 @@ QProgressBar::chunk#thrustBar {
<widget class="QLabel" name="groundDistanceLabel"> <widget class="QLabel" name="groundDistanceLabel">
<property name="font"> <property name="font">
<font> <font>
<pointsize>8</pointsize> <pointsize>-1</pointsize>
<weight>50</weight>
<italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
...@@ -313,14 +375,17 @@ QProgressBar::chunk#thrustBar { ...@@ -313,14 +375,17 @@ QProgressBar::chunk#thrustBar {
</widget> </widget>
</item> </item>
<item row="4" column="4" colspan="2"> <item row="4" column="4" colspan="2">
<widget class="QLabel" name="altitudeLabel"> <widget class="QLabel" name="speedLabel">
<property name="font"> <property name="font">
<font> <font>
<pointsize>8</pointsize> <pointsize>-1</pointsize>
<weight>50</weight>
<italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
<string>00.00 m</string> <string>00.0 m/s</string>
</property> </property>
</widget> </widget>
</item> </item>
...@@ -380,9 +445,10 @@ QProgressBar::chunk#thrustBar { ...@@ -380,9 +445,10 @@ QProgressBar::chunk#thrustBar {
<widget class="QLabel" name="stateLabel"> <widget class="QLabel" name="stateLabel">
<property name="font"> <property name="font">
<font> <font>
<pointsize>10</pointsize> <pointsize>-1</pointsize>
<weight>75</weight> <weight>50</weight>
<bold>true</bold> <italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
...@@ -394,14 +460,18 @@ QProgressBar::chunk#thrustBar { ...@@ -394,14 +460,18 @@ QProgressBar::chunk#thrustBar {
<widget class="QLabel" name="waypointLabel"> <widget class="QLabel" name="waypointLabel">
<property name="font"> <property name="font">
<font> <font>
<pointsize>20</pointsize> <pointsize>-1</pointsize>
<weight>75</weight> <weight>50</weight>
<bold>true</bold> <italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
<string>WPX</string> <string>WPX</string>
</property> </property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set>
</property>
</widget> </widget>
</item> </item>
<item row="2" column="6"> <item row="2" column="6">
...@@ -420,7 +490,10 @@ QProgressBar::chunk#thrustBar { ...@@ -420,7 +490,10 @@ QProgressBar::chunk#thrustBar {
</property> </property>
<property name="font"> <property name="font">
<font> <font>
<pointsize>8</pointsize> <pointsize>-1</pointsize>
<weight>50</weight>
<italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
...@@ -444,7 +517,10 @@ QProgressBar::chunk#thrustBar { ...@@ -444,7 +517,10 @@ QProgressBar::chunk#thrustBar {
</property> </property>
<property name="font"> <property name="font">
<font> <font>
<pointsize>8</pointsize> <pointsize>-1</pointsize>
<weight>50</weight>
<italic>false</italic>
<bold>false</bold>
</font> </font>
</property> </property>
<property name="text"> <property name="text">
...@@ -530,7 +606,7 @@ QProgressBar::chunk#thrustBar { ...@@ -530,7 +606,7 @@ QProgressBar::chunk#thrustBar {
</widget> </widget>
</item> </item>
<item> <item>
<widget class="QPushButton" name="returnButton"> <widget class="QPushButton" name="landButton">
<property name="minimumSize"> <property name="minimumSize">
<size> <size>
<width>18</width> <width>18</width>
...@@ -553,12 +629,12 @@ QProgressBar::chunk#thrustBar { ...@@ -553,12 +629,12 @@ QProgressBar::chunk#thrustBar {
</property> </property>
<property name="icon"> <property name="icon">
<iconset resource="../../mavground.qrc"> <iconset resource="../../mavground.qrc">
<normaloff>:/images/actions/go-home.svg</normaloff>:/images/actions/go-home.svg</iconset> <normaloff>:/images/actions/system-log-out.svg</normaloff>:/images/actions/system-log-out.svg</iconset>
</property> </property>
</widget> </widget>
</item> </item>
<item> <item>
<widget class="QPushButton" name="landButton"> <widget class="QPushButton" name="abortButton">
<property name="minimumSize"> <property name="minimumSize">
<size> <size>
<width>18</width> <width>18</width>
......
...@@ -73,8 +73,8 @@ UASView::UASView(UASInterface* uas, QWidget *parent) : ...@@ -73,8 +73,8 @@ UASView::UASView(UASInterface* uas, QWidget *parent) :
connect(m_ui->liftoffButton, SIGNAL(clicked()), uas, SLOT(launch())); connect(m_ui->liftoffButton, SIGNAL(clicked()), uas, SLOT(launch()));
connect(m_ui->haltButton, SIGNAL(clicked()), uas, SLOT(halt())); connect(m_ui->haltButton, SIGNAL(clicked()), uas, SLOT(halt()));
connect(m_ui->continueButton, SIGNAL(clicked()), uas, SLOT(go())); connect(m_ui->continueButton, SIGNAL(clicked()), uas, SLOT(go()));
connect(m_ui->returnButton, SIGNAL(clicked()), uas, SLOT(home())); connect(m_ui->landButton, SIGNAL(clicked()), uas, SLOT(home()));
connect(m_ui->landButton, SIGNAL(clicked()), uas, SLOT(emergencySTOP())); connect(m_ui->abortButton, SIGNAL(clicked()), uas, SLOT(emergencySTOP()));
connect(m_ui->killButton, SIGNAL(clicked()), uas, SLOT(emergencyKILL())); connect(m_ui->killButton, SIGNAL(clicked()), uas, SLOT(emergencyKILL()));
connect(m_ui->shutdownButton, SIGNAL(clicked()), uas, SLOT(shutdown())); connect(m_ui->shutdownButton, SIGNAL(clicked()), uas, SLOT(shutdown()));
...@@ -95,6 +95,15 @@ UASView::UASView(UASInterface* uas, QWidget *parent) : ...@@ -95,6 +95,15 @@ UASView::UASView(UASInterface* uas, QWidget *parent) :
//m_ui->speedBar->setMinimum(0); //m_ui->speedBar->setMinimum(0);
//m_ui->speedBar->setMaximum(15); //m_ui->speedBar->setMaximum(15);
// UAS color
QColor uasColor = uas->getColor();
uasColor = uasColor.darker(475);
QString colorstyle;
colorstyle = colorstyle.sprintf("QGroupBox { border: 2px solid #4A4A4F; border-radius: 5px; padding: 0px; margin: 0px; background-color: #%02X%02X%02X;}",
uasColor.red(), uasColor.green(), uasColor.blue());
m_ui->groupBox->setStyleSheet(colorstyle);
//m_ui->groupBox->setAutoFillBackground(true);
// Heartbeat fade // Heartbeat fade
refreshTimer = new QTimer(this); refreshTimer = new QTimer(this);
...@@ -107,6 +116,11 @@ UASView::~UASView() ...@@ -107,6 +116,11 @@ UASView::~UASView()
delete m_ui; delete m_ui;
} }
void UASView::setUASasActive(bool)
{
UASManager::instance()->setActiveUAS(this->uas);
}
void UASView::updateMode(int sysId, QString status, QString description) void UASView::updateMode(int sysId, QString status, QString description)
{ {
if (sysId == this->uas->getUASID()) m_ui->modeLabel->setText(status); if (sysId == this->uas->getUASID()) m_ui->modeLabel->setText(status);
...@@ -182,13 +196,6 @@ void UASView::setSystemType(UASInterface* uas, unsigned int systemType) ...@@ -182,13 +196,6 @@ void UASView::setSystemType(UASInterface* uas, unsigned int systemType)
break; break;
} }
} }
// MAV_GENERIC = 0,
// MAV_FIXED_WING,
// MAV_QUADROTOR,
// MAV_COAXIAL,
// MAV_HELICOPTER,
// MAV_GROUND,
// OCU
} }
void UASView::updateLocalPosition(UASInterface* uas, double x, double y, double z, quint64 usec) void UASView::updateLocalPosition(UASInterface* uas, double x, double y, double z, quint64 usec)
......
...@@ -67,6 +67,8 @@ public slots: ...@@ -67,6 +67,8 @@ public slots:
void selectWaypoint(int uasId, int id); void selectWaypoint(int uasId, int id);
/** @brief Set the current system type */ /** @brief Set the current system type */
void setSystemType(UASInterface* uas, unsigned int systemType); void setSystemType(UASInterface* uas, unsigned int systemType);
/** @brief Set the current UAS as the globally active system */
void setUASasActive(bool);
protected: protected:
void changeEvent(QEvent *e); void changeEvent(QEvent *e);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment