diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/downloadManager.cpp | 202 | ||||
| -rw-r--r-- | src/downloadmanager.cpp | 214 | ||||
| -rw-r--r-- | src/downloadmanager.h (renamed from src/downloadManager.h) | 42 | ||||
| -rw-r--r-- | src/fbgui.cpp | 127 | ||||
| -rw-r--r-- | src/fbgui.h | 30 | ||||
| -rw-r--r-- | src/fbgui.pro | 34 | ||||
| -rw-r--r-- | src/javascriptinterface.cpp (renamed from src/javascriptInterface.cpp) | 53 | ||||
| -rw-r--r-- | src/javascriptinterface.h (renamed from src/javascriptInterface.h) | 24 | ||||
| -rw-r--r-- | src/logViewer.cpp | 16 | ||||
| -rw-r--r-- | src/logViewer.h | 29 | ||||
| -rw-r--r-- | src/loggerengine.cpp | 67 | ||||
| -rw-r--r-- | src/loggerengine.h | 53 | ||||
| -rw-r--r-- | src/main.cpp | 41 | ||||
| -rw-r--r-- | src/sysinfo.cpp (renamed from src/sysInfo.cpp) | 41 | ||||
| -rw-r--r-- | src/sysinfo.h (renamed from src/sysInfo.h) | 28 | ||||
| -rwxr-xr-x | src/testApp.sh | 2 |
16 files changed, 565 insertions, 438 deletions
diff --git a/src/downloadManager.cpp b/src/downloadManager.cpp deleted file mode 100644 index 1271a8c..0000000 --- a/src/downloadManager.cpp +++ /dev/null @@ -1,202 +0,0 @@ -#include "downloadManager.h" -#include "fbgui.h" -#include <QFileInfo> -#include <QByteArray> - -int downloadManager::downloaded = 0; -// ---------------------------------------------------------------------------------------- -downloadManager::downloadManager() -{ - logView->write(QString("testing @ DM init")); - qnam = new QNetworkAccessManager(); - dip = false; - downloadDir = QDir(downloadPath); - /* check if downloadPath exists, if not create it. */ - if (!downloadDir.exists()){ - if (debug) qDebug() << "Download directory: " << downloadDir.path() << "doesn't exist."; - QDir::current().mkdir(downloadPath); - if (downloadDir.exists() && debug) - qDebug() << "Created download directory: " << downloadDir.path(); - } - else if (debug) qDebug() << "Download directory: " << downloadDir.path() << "exists."; -} -// ---------------------------------------------------------------------------------------- -void downloadManager::downloadFile(QString& filename) -{ - if (debug) qDebug() << "Received downloadFile signal for:" << filename; - QUrl fileUrl; - fileUrl = baseURL.resolved(QUrl(filename)); - if (debug) qDebug() << "fileUrl: " << fileUrl; - this->processDownloadRequest(fileUrl); -} -// ---------------------------------------------------------------------------------------- -void downloadManager::downloadFile(QUrl& fileUrl) -{ - if (debug) qDebug() << "Received downloadFile signal for:" << fileUrl; - this->processDownloadRequest(fileUrl); -} -// ---------------------------------------------------------------------------------------- -void downloadManager::processDownloadRequest(QUrl& url) -{ - if (url.isEmpty()){ - if (debug) qDebug() << "No URL specified for download."; - return; - } - /* if download in progress, enqueue file and return. */ - if (dip) - { - if (debug) qDebug() << "Download in progress! Enqueueing:" << url.toString() - << "(" << dlQ.size() << "in queue)"; - dlQ.enqueue(url); - return; - } - /* no running downloads: enqueue and start next download. */ - dlQ.enqueue(url); - if (debug) qDebug() << "Enqueueing:" << url.toString() << endl; - startNextDownload(); -} -// ---------------------------------------------------------------------------------------- -void downloadManager::startNextDownload() -{ - - if (dlQ.isEmpty()) - { - emit downloadQueueEmpty(); - if (debug) qDebug() << "Download manager ready. (1)"; - return; - } - if (debug) qDebug() << "Starting next download: " << dlQ.head().toString() - << "(" << dlQ.size() << "in queue.)"; - - /* dequeue next URL to download. */ - QUrl url = dlQ.dequeue(); - - /* get temporary filename from URL. */ - QString tmp = url.path(); - tmp.remove(0, tmp.lastIndexOf(QChar('/')) + 1); - - /* check if filename exists on target file system */ - QFileInfo fi(downloadPath + "/" + tmp); - if (fi.exists()){ - QString qs = QString(fi.absoluteFilePath() + ".\%1").arg(downloaded); - outfile.setFileName(qs); - } - else - outfile.setFileName(downloadPath + "/" + tmp); - - if (!outfile.open(QIODevice::WriteOnly)){ - if (debug) qDebug() << "Couldn't open file! Skipping..."; - return; - } - - /* send the request for the file */ - QNetworkRequest request(url); - currentDownload = qnam->get(request); - lastProgress = 0; - currentProgress = 0; - dip = true; - dltime.start(); - QObject::connect(currentDownload, SIGNAL(readyRead()), this, SLOT(downloadReady())); - QObject::connect(currentDownload, SIGNAL(metaDataChanged()), this, SLOT(processMetaInfo())); - QObject::connect(currentDownload, SIGNAL(downloadProgress(qint64, qint64)), - this, SLOT(downloadProgress(qint64, qint64))); - QObject::connect(currentDownload, SIGNAL(finished()), this, SLOT(downloadFinished())); -} -// ---------------------------------------------------------------------------------------- -// Private slots -// ---------------------------------------------------------------------------------------- -void downloadManager::processMetaInfo(){ - /* fetch filesize from header & filename from url (for now) */ - const QByteArray cltag = "Content-Length"; - QByteArray clinfo = currentDownload->rawHeader(cltag); - QFileInfo fi(outfile); - emit downloadInfo(outfile.fileName(), clinfo.toDouble()); -} -// ---------------------------------------------------------------------------------------- -void downloadManager::downloadReady() -{ - /* data ready, save it */ - outfile.write(currentDownload->readAll()); -} -// ---------------------------------------------------------------------------------------- -void downloadManager::downloadProgress(qint64 bytesIn, qint64 bytesTotal) -{ - // "fix" for the weird bytesTotal = -1 initial reading... - if (bytesIn > bytesTotal) - return; - /* calculate current speed */ - double speed = bytesIn * 1000 / dltime.elapsed(); - QString unit; - if (speed < 1024) { - unit = "bytes/sec"; - } - else if (speed < 1024*1024) { - speed /= 1024; - unit = "KB/s"; - } - else { - speed /= 1024*1024; - unit = "MB/s"; - } - /* update progress only if difference higher than the updateInterval setting */ - currentProgress = ((bytesIn * 100) / bytesTotal); - if (currentProgress - lastProgress >= updateInterval){ - lastProgress = currentProgress; - emit updateProgress(currentProgress, speed, unit); - if (debug) qDebug() << "Download progress of " << currentDownload->url().toString() - << ": " << bytesIn << "/" << bytesTotal << "(" << currentProgress << "\%)"; - } - return; -} -// ---------------------------------------------------------------------------------------- -void downloadManager::downloadFinished() -{ - /* check for errors */ - if (currentDownload->error()){ - if (debug) qDebug() << "Download of" << currentDownload->url().toString() - << "failed with status code: " << currentDownload->error(); - currentDownload->deleteLater(); - outfile.remove(); - return; - } - // TODO Handle errors. - if (debug) qDebug() << "NetworkCode: " << currentDownload->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt(); - - /* end download */ - outfile.close(); - currentDownload->deleteLater(); - downloaded++; - dip = false; - if (debug) qDebug() << "Download of " << currentDownload->url().toString() - << "finished. (dlcount = "<< downloaded << ")"; - if (dlQ.isEmpty()){ - emit downloadQueueEmpty(); - if (debug) qDebug() << "Download manager ready. (2)"; - return; - } - startNextDownload(); -} -/* ---------------------------------------------------------------------------------------- -* - ** dead code: Header filename fetching & renaming ** - -const QByteArray cd = "Content-Disposition"; -QByteArray cdc = currentDownload->rawHeader(cd); -int x = cdc.indexOf("filename=\"") + 10; -cdc.remove(0, x).chop(1); -if (!cdc.isEmpty()) - currentTargetFilename = cdc; -else - currentTargetFilename = QString("download.\%1").arg(downloaded); - -QString tmp = outfile.fileName(); -tmp.remove(0, tmp.lastIndexOf(QChar('/')) + 1); -qDebug() << "Trying to rename " << tmp << " to --> " << currentTargetFilename; - -if (outfile.rename(downloadPath + "/" + currentTargetFilename)) { - if (debug) qDebug() << "Renamed file!"; -} -else { - if (debug) qDebug() << "Failure to rename file!"; -} -*/ diff --git a/src/downloadmanager.cpp b/src/downloadmanager.cpp new file mode 100644 index 0000000..47582c8 --- /dev/null +++ b/src/downloadmanager.cpp @@ -0,0 +1,214 @@ +#include "downloadmanager.h" +#include "fbgui.h" + +int DownloadManager::downloaded = 0; +// ---------------------------------------------------------------------------------------- +DownloadManager::DownloadManager(){ + qxtLog->debug() << "Initializing download manager..."; + checkDownloadDirectory(); + qnam = new QNetworkAccessManager(); + dip = false; +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::checkDownloadDirectory() +{ + // check if downloadPath exists, if not create it. + downloadDir = QDir(downloadPath); + if (!downloadDir.exists()){ + qxtLog->debug() << "Download directory: " << downloadDir.path() << " doesn't exist."; + QDir::current().mkdir(downloadPath); + if (downloadDir.exists()){ + qxtLog->debug() << "Created download directory: " << downloadDir.path(); + } + else { + qxtLog->debug() << "Failed to create directory: " << downloadDir.path(); + // try to save to /tmp/fbgui + downloadDir.setPath(QDir::tempPath () + "/fbgui"); + if (!downloadDir.exists()){ + QDir::current().mkdir(QDir::tempPath () + "/fbgui"); + if (!downloadDir.exists()){ + // TODO: dont exit, this shouldn't happen anyway (right?) + qxtLog->debug() << "Fatal, no target for downloads. Exiting..."; + exit(EXIT_FAILURE); + } + } + qxtLog->debug() << "Saving downloads to: " << downloadDir.absolutePath(); + } + } + else qxtLog->debug() << "Download directory: " << downloadDir.path() << " exists."; +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::downloadFile(const QString& filename) +{ + QUrl fileUrl(baseURL.resolved(QUrl(filename))); + this->processDownloadRequest(fileUrl); +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::downloadFile(const QUrl& fileUrl) +{ + this->processDownloadRequest(fileUrl); +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::processDownloadRequest(const QUrl& url) +{ + if (url.isEmpty()){ + qxtLog->debug() << "No URL specified for download."; + return; + } + // if download in progress, enqueue file and return. + if (dip){ + dlQ.enqueue(url); + qxtLog->debug() << "Download in progress! Queued:" << url.toString() + << "(" << dlQ.size() << " in queue)"; + return; + } + // no running downloads: enqueue and start next download. + dlQ.enqueue(url); + qxtLog->debug() << "Enqueueing:" << url.toString(); + startNextDownload(); +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::startNextDownload() +{ + if (dlQ.isEmpty()){ + emit downloadQueueEmpty(); + qxtLog->debug() << "Download manager ready. (1)"; + return; + } + qxtLog->debug() << "Starting next download: " << dlQ.head().toString() + << " (" << dlQ.size() - 1 << " in queue.)"; + + // dequeue next URL to download. + QUrl url = dlQ.dequeue(); + + // get filename from URL. + QString tmp = url.path(); + tmp.remove(0, tmp.lastIndexOf(QChar('/')) + 1); + + // check if filename exists on target file system + if (downloadDir.exists(tmp)){ + qxtLog->debug() << "File already exists: " << downloadDir.absoluteFilePath(tmp); + outfile.setFileName(QString(downloadDir.absolutePath() + "/" + tmp + ".\%1").arg(downloaded)); + } + else + outfile.setFileName(downloadDir.absoluteFilePath(tmp)); + qxtLog->debug() << "Saving to: " << outfile.fileName(); + + // try to open for writing + if (!outfile.open(QIODevice::WriteOnly)){ + qxtLog->debug() << "No write access to " << outfile.fileName() << " . Skipping download..."; + return; + } + + // send the request for the file + QNetworkRequest request(url); + currentDownload = qnam->get(request); + lastProgress = 0; + currentProgress = 0; + dip = true; + dltime.start(); + QObject::connect(currentDownload, SIGNAL(readyRead()), this, SLOT(downloadReady())); + QObject::connect(currentDownload, SIGNAL(metaDataChanged()), this, SLOT(processMetaInfo())); + QObject::connect(currentDownload, SIGNAL(downloadProgress(qint64, qint64)), + this, SLOT(downloadProgress(qint64, qint64))); + QObject::connect(currentDownload, SIGNAL(finished()), this, SLOT(downloadFinished())); +} +// ---------------------------------------------------------------------------------------- +// Private slots to process downloads +// ---------------------------------------------------------------------------------------- +void DownloadManager::processMetaInfo() +{ + // fetch filesize from header & filename from URL (for now) + const QByteArray cltag = "Content-Length"; + QByteArray clinfo = currentDownload->rawHeader(cltag); + QFileInfo fi(outfile); + emit downloadInfo(outfile.fileName(), clinfo.toDouble()); +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::downloadReady() +{ + // data ready, save it + outfile.write(currentDownload->readAll()); +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::downloadProgress(qint64 bytesIn, qint64 bytesTotal) +{ + if (bytesIn > bytesTotal) return; + // calculate current speed + double speed = bytesIn * 1000 / dltime.elapsed(); + QString unit; + if (speed < 1024) { + unit = "bytes/sec"; + } + else if (speed < 1024*1024) { + speed /= 1024; + unit = "KB/s"; + } + else { + speed /= 1024*1024; + unit = "MB/s"; + } + // update progress only if difference higher than the updateInterval setting + currentProgress = ((bytesIn * 100) / bytesTotal); + if (currentProgress - lastProgress >= updateInterval){ + lastProgress = currentProgress; + emit updateProgress(currentProgress, speed, unit); + qxtLog->debug() << "Download progress of " << currentDownload->url().toString() + << ": " << bytesIn << "/" << bytesTotal << "(" << currentProgress << "\%)"; + } + return; +} +// ---------------------------------------------------------------------------------------- +void DownloadManager::downloadFinished() +{ + // check for errors + if (currentDownload->error()){ + currentDownload->deleteLater(); + outfile.remove(); + int statusCode = currentDownload->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt(); + qxtLog->debug() << "Download of " << currentDownload->url().toString() + << " failed with HTTP error code: " << statusCode; + emit notify(QString("Download failed! HTTP Status Code: %1").arg(statusCode)); + } + else{ + // end download + currentDownload->deleteLater(); + outfile.close(); + downloaded++; + qxtLog->debug() << "Download of " << currentDownload->url().toString() + << " finished. (downloaded = "<< downloaded << ")"; + emit notify(QString("Successfully downloaded %1").arg(currentDownload->url().toString())); + } + dip = false; + // process next in queue + if (dlQ.isEmpty()){ + emit downloadQueueEmpty(); + qxtLog->debug() << "Download manager ready. (2)"; + return; + } + startNextDownload(); +} +/******************************************************************************************************** +* + ** dead code: Header filename fetching & renaming ** + +const QByteArray cd = "Content-Disposition"; +QByteArray cdc = currentDownload->rawHeader(cd); +int x = cdc.indexOf("filename=\"") + 10; +cdc.remove(0, x).chop(1); +if (!cdc.isEmpty()) + currentTargetFilename = cdc; +else + currentTargetFilename = QString("download.\%1").arg(downloaded); + +QString tmp = outfile.fileName(); +tmp.remove(0, tmp.lastIndexOf(QChar('/')) + 1); +qDebug() << "Trying to rename " << tmp << " to --> " << currentTargetFilename; + +if (outfile.rename(downloadPath + "/" + currentTargetFilename)) { + qxtLog->debug() << "Renamed file!"; +} +else { + qxtLog->debug() << "Failure to rename file!"; +} +*/ diff --git a/src/downloadManager.h b/src/downloadmanager.h index 2e26b70..0cc1a35 100644 --- a/src/downloadManager.h +++ b/src/downloadmanager.h @@ -19,11 +19,6 @@ #define DOWNLOADMANAGER_H #include "fbgui.h" -#include <QObject> -#include <QDir> -#include <QMap> -#include <QtNetwork> -#include <QTime> extern bool debug; extern QUrl baseURL; @@ -32,42 +27,53 @@ extern QString downloadPath; extern int updateInterval; -class downloadManager : public QObject +class DownloadManager : public QObject { Q_OBJECT public: - downloadManager(); + DownloadManager(); private: - void processDownloadRequest(QUrl& url); + // checks for valid download directory, ran once in constructor + void checkDownloadDirectory(); + // private control function for queueing mechanism. + void processDownloadRequest(const QUrl& url); + + // base objects for downloading QNetworkAccessManager* qnam; QQueue<QUrl> dlQ; - QNetworkRequest request; QNetworkReply* currentDownload; QFile outfile; QDir downloadDir; + // download progress variables QTime dltime; - bool dip; int currentProgress, lastProgress; - + // download in progress flag + bool dip; + // static counter static int downloaded; - QString currentTargetFilename; signals: - void finished(); - void downloadInfo(QString filename, double filesize); - void updateProgress(int percent, double speed, QString unit); + // notify sends a message to the javascript interface. + void notify(const QString& msg); + // downloadInfo sends static information (name, size) to the interface. + void downloadInfo(const QString& filename, const double& filesize); + // updateProgress sends download progress information to the interface. + void updateProgress(const int& percent, const double& speed, const QString& unit); + // signal emitted when download queue is empty. void downloadQueueEmpty(); public slots: - void downloadFile(QUrl& fileUrl); - void downloadFile(QString& fileUrl); + // public slots to receive download requests. + void downloadFile(const QUrl& fileUrl); + void downloadFile(const QString& fileUrl); private slots: + // private slots to manage the downloading process void startNextDownload(); - void downloadReady(); void processMetaInfo(); + void downloadReady(); void downloadProgress(qint64 bytesIn, qint64 bytesTotal); void downloadFinished(); }; diff --git a/src/fbgui.cpp b/src/fbgui.cpp index 3408b1e..e21bdc6 100644 --- a/src/fbgui.cpp +++ b/src/fbgui.cpp @@ -1,22 +1,19 @@ #include "fbgui.h" #include "downloadManager.h" #include "javascriptInterface.h" -//#include "ipWatcher.h" +#include "loggerengine.h" +#include "downloadmanager.h" +#include "javascriptinterface.h" #include <iostream> -#include <QUrl> -#include <QDir> -#include <QHostInfo> #include <QtWebKit> -#include <QPlainTextEdit> +#include <QxtCore> -// Note: Absolute paths. binPath empty init, set in main() after QApplication instanciated. -QString binPath(""); -QString downloadPath(binPath + "/downloads"); QUrl baseURL(DEFAULT_URL); -bool debug = false; +QString binPath(""); +QString downloadPath("/tmp/fbgui/downloads"); int updateInterval = DEFAULT_UPDATE_INTERVAL; -logViewer *logView; +int debugMode = -1; //------------------------------------------------------------------------------------------- fbgui::fbgui() @@ -31,58 +28,102 @@ fbgui::fbgui() checkHost(); webView = new QWebView(this); + webView->load(baseURL); - /*show info page until the client has received an IP address*/ - /* - ipWatcher* ipw = new ipWatcher(QApplication::applicationDirPath()); - while(!ipw->ipReceived()){ - webView->load(QUrl("prc://html/loadAbout.html")); + // setup basic debug + qxtLog->disableLoggerEngine("DEFAULT"); + qxtLog->enableLogLevels(QxtLogger::DebugLevel); + if (debugMode == 0){ + qxtLog->addLoggerEngine("std_logger", new LoggerEngine_std); + qxtLog->initLoggerEngine("std_logger"); + qxtLog->setMinimumLevel("std_logger", QxtLogger::DebugLevel); + qxtLog->debug() << "Initializing fbgui..."; } - */ - webView->load(baseURL); - /* initialize javascript interface */ - javascriptInterface* jsi = new javascriptInterface(webView->page()->mainFrame()); - QObject::connect(jsi, SIGNAL(quitFbgui()), this, SLOT(close())); + // base of the gui + createActions(); + checkHost(); + _webView = new QWebView(this); + _webView->load(baseURL); + + // debug console split or normal browser + if (debugMode == 1) + setupDebugSplit(); + else + setCentralWidget(_webView); - QObject::connect(webView->page()->mainFrame(), SIGNAL(javaScriptWindowObjectCleared()), + // initialize javascript interface + JavascriptInterface* jsi = new JavascriptInterface(_webView->page()->mainFrame()); + QObject::connect(jsi, SIGNAL(quitFbgui()), this, SLOT(close())); + QObject::connect(_webView->page()->mainFrame(), SIGNAL(javaScriptWindowObjectCleared()), jsi, SLOT(attachToDOM())); - /* initialize download manager */ - downloadManager* dm = new downloadManager(); - QObject::connect(dm, SIGNAL(downloadInfo(QString, double)), jsi, SLOT(downloadInfo(QString, double))); - QObject::connect(jsi, SIGNAL(requestFile(QString&)), dm, SLOT(downloadFile(QString&))); - QObject::connect(dm, SIGNAL(updateProgress(int, double, QString)), jsi, SLOT(updateProgressBar(int, double, QString))); + + // initialize download manager + DownloadManager* dm = new DownloadManager(); + QObject::connect(dm, SIGNAL(downloadInfo(const QString&, const double&)), + jsi, SLOT(downloadInfo(const QString&, const double&))); + QObject::connect(dm, SIGNAL(notify(const QString&)), + jsi, SLOT(notify(const QString&))); + QObject::connect(jsi, SIGNAL(requestFile(const QString&)), dm, SLOT(downloadFile(const QString&))); + QObject::connect(dm, SIGNAL(updateProgress(const int&, const double&, const QString&)), + jsi, SLOT(updateProgressBar(const int&, const double&, const QString&))); QObject::connect(dm, SIGNAL(downloadQueueEmpty()), jsi, SLOT(callbackOnDlQueueFinished())); + // set properties setWindowTitle("fbgui"); setAttribute(Qt::WA_QuitOnClose, true); setWindowFlags(Qt::FramelessWindowHint); - resize(QSize(800, 600)); - setCentralWidget(webView); showFullScreen(); - show(); } //------------------------------------------------------------------------------------------- -void fbgui::keyPressEvent(QKeyEvent *event){ - /* F4 toggles debug console */ - if (debug && event->key() == Qt::Key_F4){ - if (!logView->isVisible()){ - logView->append(QString("check passed.")); - logView->raise(); - logView->setVisible(true); - } - else { - logView->lower(); - logView->setVisible(false); - } - } +void fbgui::createActions() +{ + // CTRL + X to kill the gui + _quit = new QAction(tr("&quit"), this); + _quit->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_X)); + this->addAction(_quit); + connect(_quit, SIGNAL(triggered()), this, SLOT(close())); +} +//------------------------------------------------------------------------------------------- +void fbgui::setupDebugSplit() +{ + _debugConsole = new QTextEdit(this); + _debugConsole->setWindowFlags(Qt::FramelessWindowHint); + QPalette pal; + pal.setColor(QPalette::Base, Qt::black); + _debugConsole->setPalette(pal); + _debugConsole->setTextColor(Qt::cyan); + _debugConsole->insertPlainText("Debug console initialized.\n"); + // enable custom logger engine + qxtLog->addLoggerEngine("fb_logger", new LoggerEngine_fb(_debugConsole)); + qxtLog->initLoggerEngine("fb_logger"); + qxtLog->setMinimumLevel("fb_logger", QxtLogger::DebugLevel); + // display browser and debug in a splitter + _splitter = new QSplitter(Qt::Vertical, this); + _splitter->addWidget(_webView); + _splitter->addWidget(_debugConsole); + // CTRL + D toggles debug window + _toggleDebug = new QAction(tr("&toggleDebug"), this); + _toggleDebug->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_D)); + addAction(_toggleDebug); + connect(_toggleDebug, SIGNAL(triggered()), this, SLOT(toggleDebug())); + setCentralWidget(_splitter); +} +//------------------------------------------------------------------------------------------- +void fbgui::toggleDebug() +{ + if (_debugConsole->isVisible()) + _debugConsole->hide(); + else + _debugConsole->show(); } //------------------------------------------------------------------------------------------- void fbgui::checkHost() const { + // TODO instead of closing app, show error page from qrc QHostInfo hostInfo = QHostInfo::fromName(baseURL.host()); if (hostInfo.error() != QHostInfo::NoError){ - qDebug() << "Lookup of " << baseURL.host() << "failed. Exiting..."; + qxtLog->debug() << "Lookup of " << baseURL.host() << "failed. Exiting..."; exit(EXIT_FAILURE); } } diff --git a/src/fbgui.h b/src/fbgui.h index c0ef95e..2d06afe 100644 --- a/src/fbgui.h +++ b/src/fbgui.h @@ -19,21 +19,23 @@ #define FBGUI_H #include <QtGui> -#include <QPlainTextEdit> #include <QtWebKit> +#include <QxtCore> -#include "logViewer.h" +// Internal default settings #define DEFAULT_URL "http://www.google.com" #define DEFAULT_DOWNLOAD_DIR "/tmp/fbgui/downloads" +#define DEFAULT_CONFIG_PATH "/etc/fbgui.conf" #define DEFAULT_UPDATE_INTERVAL 1; + +// Global settings extern QString binPath; extern QString downloadPath; extern QUrl baseURL; -extern bool debug; +extern int debugMode; extern int updateInterval; -extern logViewer *logView; class fbgui : public QMainWindow { @@ -41,16 +43,26 @@ class fbgui : public QMainWindow public: fbgui(); - /* public log access */ - //void log(QString text); private: + // setup procedures + void setupDebugSplit(); + void createActions(); void checkHost() const; - QWebView *webView; + // widgets constituing the gui + QWebView* _webView; + QSplitter* _splitter; + QTextEdit* _debugConsole; + + // action list + QAction* _quit; + QAction* _toggleDebug; + +private slots: + // slots for processing actions + void toggleDebug(); -protected: - void keyPressEvent(QKeyEvent *event); }; #endif // FBGUI_H diff --git a/src/fbgui.pro b/src/fbgui.pro index 1b8d1f8..353518b 100644 --- a/src/fbgui.pro +++ b/src/fbgui.pro @@ -2,23 +2,27 @@ TEMPLATE = app TARGET = fbgui CONFIG += qt \ debug -LIBS += -L/usr/local/qjson/lib \ - -lqjson -INCLUDEPATH += -I/usr/local/qjson/include QT += core \ gui \ - webkit \ - network -HEADERS += logViewer.h \ - downloadManager.h \ - fbgui.h \ - javascriptInterface.h \ - sysInfo.h -SOURCES += logViewer.cpp \ - downloadManager.cpp \ - main.cpp \ + network \ + webkit +LIBS += -L/usr/local/qjson/lib \ + -lqjson \ + -L/usr/local/Qxt/lib \ + -lQxtCore +INCLUDEPATH += /usr/local/qjson/include \ + /usr/local/Qxt/include \ + /usr/local/Qxt/include/QxtCore +HEADERS += sysinfo.h \ + loggerengine.h \ + javascriptinterface.h \ + downloadmanager.h \ + fbgui.h +SOURCES += sysinfo.cpp \ + loggerengine.cpp \ + javascriptinterface.cpp \ + downloadmanager.cpp \ fbgui.cpp \ - javascriptInterface.cpp \ - sysInfo.cpp + main.cpp FORMS += RESOURCES += fbgui.qrc diff --git a/src/javascriptInterface.cpp b/src/javascriptinterface.cpp index c4dd61b..7f1b949 100644 --- a/src/javascriptInterface.cpp +++ b/src/javascriptinterface.cpp @@ -1,31 +1,27 @@ #include "fbgui.h" -#include "javascriptInterface.h" -#include "sysInfo.h" +#include "javascriptinterface.h" +#include "sysinfo.h" + //------------------------------------------------------------------------------------------------------- -javascriptInterface::javascriptInterface(QWebFrame *parent) -{ - //TODO: check for better way to use evaluateJavaScript() +JavascriptInterface::JavascriptInterface(QWebFrame *parent){ + qxtLog->debug() << "Initializing javascript interface..."; _parent = parent; } //------------------------------------------------------------------------------------------------------- -javascriptInterface::~javascriptInterface() {} +JavascriptInterface::~JavascriptInterface() {} //------------------------------------------------------------------------------------------------------- -QString javascriptInterface::getSysInfo(QString info) -{ - sysInfo si; - if (debug) qDebug() << "Requested info: " << info << endl; +const QString JavascriptInterface::getSysInfo(const QString& info){ + SysInfo si; return si.getInfo(info); } //------------------------------------------------------------------------------------------------------- -void javascriptInterface::attachToDOM() -{ +void JavascriptInterface::attachToDOM(){ _parent->addToJavaScriptWindowObject(QString("fbgui"), this); } //------------------------------------------------------------------------------------------------------- -void javascriptInterface::startDownload(QString filename) -{ - /* ignore if empty filename */ +void JavascriptInterface::startDownload(const QString& filename){ + // ignore if empty filename if (filename.isEmpty()){ _parent->evaluateJavaScript("alert(\"No filename!\")"); return; @@ -33,33 +29,32 @@ void javascriptInterface::startDownload(QString filename) emit requestFile(filename); } //------------------------------------------------------------------------------------------------------- -void javascriptInterface::downloadInfo(QString filename, double filesize) -{ +void JavascriptInterface::downloadInfo(const QString& filename, const double& filesize){ QString code = QString("downloadInfo('\%1', \%2)").arg(filename).arg(filesize); _parent->evaluateJavaScript(code); } //------------------------------------------------------------------------------------------------------- -void javascriptInterface::updateProgressBar(int percent, double speed, QString unit) -{ +void JavascriptInterface::notify(const QString& msg){ + + QString code = QString("notify('\%1')").arg(msg); + _parent->evaluateJavaScript(code); +} +//------------------------------------------------------------------------------------------------------- +void JavascriptInterface::updateProgressBar(const int& percent, const double& speed, const QString& unit){ if (percent == 0) return; QString code = QString("updateProgress(\%1, \%2, '\%3')").arg(percent).arg(speed).arg(unit); - if (debug) qDebug() << "To JS: " << code; _parent->evaluateJavaScript(code); } //------------------------------------------------------------------------------------------------------- -void javascriptInterface::setCallbackOnDlQueueFinished(QString jsFunction) -{ - callBackOnDownloadsFinished = jsFunction; +void JavascriptInterface::setCallbackOnDlQueueFinished(QString& jsFunction){ + _callBackOnDownloadsFinished = jsFunction; } //------------------------------------------------------------------------------------------------------- -void javascriptInterface::callbackOnDlQueueFinished() -{ - QString code = QString("\%1").arg(callBackOnDownloadsFinished); +void JavascriptInterface::callbackOnDlQueueFinished(){ + QString code = QString("\%1").arg(_callBackOnDownloadsFinished); _parent->evaluateJavaScript(code); } //------------------------------------------------------------------------------------------------------- -void javascriptInterface::quit() -{ - if (debug) qDebug() << "Quit signal."; +void JavascriptInterface::quit(){ emit quitFbgui(); } diff --git a/src/javascriptInterface.h b/src/javascriptinterface.h index 457254b..9b4303c 100644 --- a/src/javascriptInterface.h +++ b/src/javascriptinterface.h @@ -20,29 +20,31 @@ #include "fbgui.h" -class javascriptInterface : public QObject{ +class JavascriptInterface : public QObject +{ Q_OBJECT private: QWebFrame* _parent; - QString callBackOnDownloadsFinished; + QString _callBackOnDownloadsFinished; public: - javascriptInterface(QWebFrame* parent); - virtual ~javascriptInterface(); + JavascriptInterface(QWebFrame* parent); + ~JavascriptInterface(); signals: - void requestFile(QString& filename); + void requestFile(const QString& filename); void quitFbgui(); public slots: void attachToDOM(); - void startDownload(QString filename); - void setCallbackOnDlQueueFinished(QString fctOnDownloadsFinished); + void startDownload(const QString& filename); + void setCallbackOnDlQueueFinished(QString& fctOnDownloadsFinished); void callbackOnDlQueueFinished(); - void updateProgressBar(int percent, double speed, QString unit); - void downloadInfo(QString filename, double filesize); - QString getSysInfo(QString info); + void updateProgressBar(const int& percent, const double& speed, const QString& unit); + void downloadInfo(const QString& filename, const double& filesize); + void notify(const QString& msg); + const QString getSysInfo(const QString& info); void quit(); }; -#endif /* JAVASCRIPTINTERFACE_H_ */ +#endif // JAVASCRIPTINTERFACE_H_ diff --git a/src/logViewer.cpp b/src/logViewer.cpp deleted file mode 100644 index 2c302f8..0000000 --- a/src/logViewer.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include <logViewer.h> -#include <fbgui.h> - -logViewer::logViewer(QWidget *parent) : QTextEdit(parent) { - QPalette qp; - qp.setColor(QPalette::Base, Qt::black); - setPalette(qp); - setTextColor(Qt::green); - setPlainText("Debug console loaded."); - resize(QSize(640, 480)); - setVisible(false); -} - -void logViewer::write(QString text){ - if (debug) this->append(text); -} diff --git a/src/logViewer.h b/src/logViewer.h deleted file mode 100644 index 7c61baf..0000000 --- a/src/logViewer.h +++ /dev/null @@ -1,29 +0,0 @@ -/* -# Copyright (c) 2010,2011 - RZ Uni Freiburg -# Copyright (c) 2010,2011 - OpenSLX Project -# -# This program/file is free software distributed under the GPL version 2. -# See http://openslx.org/COPYING -# -# If you have any feedback please consult http://openslx.org/feedback and -# send your feedback to feedback@openslx.org -# -# General information about OpenSLX can be found under http://openslx.org -# -# -# Simple logfile viewer / debug console. -# -*/ -#ifndef LOGVIEWER_H -#define LOGVIEWER_H - -#include <QTextEdit> - -class logViewer : public QTextEdit { - - public: - logViewer(QWidget *parent); - void write(QString text); -}; - -#endif // LOGVIEWER_H diff --git a/src/loggerengine.cpp b/src/loggerengine.cpp new file mode 100644 index 0000000..5638908 --- /dev/null +++ b/src/loggerengine.cpp @@ -0,0 +1,67 @@ +#include "loggerengine.h" + +// -------------------------------------------------------------------------------------------------- +// Custom Logger Engine for debugging on framebuffer +//--------------------------------------------------------------------------------------------------- +LoggerEngine_fb::LoggerEngine_fb(QTextEdit *parent) : QxtLoggerEngine(){ + // TODO: silly parent storing ... to change! + _debugConsole = parent; + _initialized = false; + setLogLevelsEnabled(QxtLogger::DebugLevel); + enableLogging(); +} +LoggerEngine_fb::~LoggerEngine_fb(){} + +void LoggerEngine_fb::initLoggerEngine(){ + _initialized = true; + return; +} + +void LoggerEngine_fb::killLoggerEngine(){return;} + +void LoggerEngine_fb::setLogLevelEnabled(QxtLogger::LogLevels level, bool enable){ + QxtLoggerEngine::setLogLevelsEnabled(level, enable); + if (!enable) QxtLoggerEngine::setLogLevelsEnabled(QxtLogger::DebugLevel); +} +bool LoggerEngine_fb::isInitialized() const{ + return _initialized; +} + +void LoggerEngine_fb::writeFormatted(QxtLogger::LogLevel level, const QList<QVariant> & msgs){ + // TODO: handle different log levels + if (msgs.isEmpty()) return; + Q_FOREACH(const QVariant& out, msgs) + { + if (!out.isNull()) + _debugConsole->insertPlainText(out.toString()); + } + _debugConsole->insertPlainText(QString("\n")); + // autoscroll + QTextCursor c = _debugConsole->textCursor(); + c.movePosition(QTextCursor::End); + _debugConsole->setTextCursor(c); +} +//--------------------------------------------------------------------------------------------------- +// Modified QxtBasicSTDLoggerEngine +//--------------------------------------------------------------------------------------------------- +LoggerEngine_std::LoggerEngine_std() : QxtBasicSTDLoggerEngine(){} + +LoggerEngine_std::~LoggerEngine_std(){} + +void LoggerEngine_std::writeToStdErr(const QString& str_level, const QList<QVariant> &msgs){ + if (msgs.isEmpty()) return; + QString header = '[' + QTime::currentTime().toString("hh:mm:ss.zzz") + "] "; + QTextStream* errstream = stdErrStream(); + Q_ASSERT(errstream); + *errstream << header; + Q_FOREACH(const QVariant& out, msgs) + { + if (!out.isNull()) + *errstream << out.toString(); + } + *errstream << endl; +} +void LoggerEngine_std::writeToStdOut(const QString& level, const QList<QVariant> & msgs){ + // reimplementing this is needed for compiling, + // we only need write to std::err, so this function is not needed +} diff --git a/src/loggerengine.h b/src/loggerengine.h new file mode 100644 index 0000000..5d93644 --- /dev/null +++ b/src/loggerengine.h @@ -0,0 +1,53 @@ +/* +# Copyright (c) 2010,2011 - RZ Uni Freiburg +# Copyright (c) 2010,2011 - OpenSLX Project +# +# This program/file is free software distributed under the GPL version 2. +# See http://openslx.org/COPYING +# +# If you have any feedback please consult http://openslx.org/feedback and +# send your feedback to feedback@openslx.org +# +# General information about OpenSLX can be found under http://openslx.org +# +# +# Custom logger engines based on Qxt library. +# +*/ +#ifndef LOGGERENGINE_H_ +#define LOGGERENGINE_H_ + +#include <QxtCore> +#include <QTime> +#include <QTextEdit> +//--------------------------------------------------------------------------------------------------- +// custom engine feeding the debug console widget +//--------------------------------------------------------------------------------------------------- +class LoggerEngine_fb : public QxtLoggerEngine { +public: + LoggerEngine_fb(QTextEdit* parent); + ~LoggerEngine_fb(); + QTextEdit *_debugConsole; + bool _initialized; + + // reimplemented virtual functions of QxtLoggerEngine + void initLoggerEngine(); + void killLoggerEngine(); + void writeFormatted(QxtLogger::LogLevel level, const QList<QVariant> & messages); + void setLogLevelEnabled(QxtLogger::LogLevels level, bool enable = true); + bool isInitialized() const; + +}; +//--------------------------------------------------------------------------------------------------- +// minor changes to QxtBasicSTDLoggerEngine +//--------------------------------------------------------------------------------------------------- +class LoggerEngine_std : public QxtBasicSTDLoggerEngine { +public: + LoggerEngine_std(); + ~LoggerEngine_std(); + // reimplemented virtual functions of QxtBasicSTDLoggerEngineqqq + void writeToStdOut(const QString& level, const QList<QVariant> &msgs); + void writeToStdErr(const QString& str_level, const QList<QVariant> &msgs); +}; + +#endif // LOGGERENGINE_H_ diff --git a/src/main.cpp b/src/main.cpp index 689b3e4..c5269a7 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -25,23 +25,22 @@ int main(int argc, char *argv[]) QApplication app(argc, argv, QApplication::GuiServer); app.setOrganizationName("team_projekt_2011"); app.setApplicationName("prebootGUI"); - app.setObjectName("test"); binPath = QApplication::applicationDirPath(); QTranslator translator; translator.load(":" + QLocale::system().name()); app.installTranslator(&translator); - /* parse command line arguments */ + // parse command line arguments QMap<QString, QString> clOpts; int longIndex = 0; - static const char *optString = "u:d:c:Dh"; + static const char *optString = "u:d:c:D:h"; static const struct option longOpts[] = { {"url", required_argument, NULL, 'u'}, {"download", required_argument, NULL, 'd'}, {"config", required_argument, NULL, 'c'}, - {"debug", no_argument, NULL, 'D'}, + {"debug", required_argument, NULL, 'D'}, {"help", no_argument, NULL, 'h'} }; int opt = getopt_long(argc, argv, optString, longOpts, &longIndex); @@ -58,7 +57,7 @@ int main(int argc, char *argv[]) case 'c': clOpts.insert("configFile", optarg); case 'D': - clOpts.insert("debug", "debug"); + clOpts.insert("debug", optarg); break; case 'h': clOpts.insert("help", "help"); @@ -70,11 +69,12 @@ int main(int argc, char *argv[]) if (clOpts.contains("help")) printHelp(); - if (clOpts.contains("debug")){ - debug = true; - qDebug() << "Debug mode activated."; - } - /* "search" config file */ + if (clOpts.contains("debug")) + debugMode = clOpts.value("debug").toInt(); + else + debugMode = -1; + + // look for config file QString configFilePath; QFileInfo confInfo; if (clOpts.contains("configFile")) @@ -88,52 +88,41 @@ int main(int argc, char *argv[]) if (confInfo.exists()) configFilePath = QString("/etc/fbgui.conf"); else - /* temporary */ - configFilePath = QApplication::applicationDirPath() + "/fbgui.conf"; + configFilePath = DEFAULT_CONFIG_PATH; } } - if (debug) qDebug() << "Config file is: " << configFilePath; - /* read the config file */ + // read the config file QSettings confFileSettings(configFilePath, QSettings::IniFormat); confFileSettings.setIniCodec("UTF-8"); if (clOpts.contains("url")) { baseURL = QUrl(clOpts.value("url")); - if (debug) qDebug() << "URL loaded from cmdline."; } else if (confFileSettings.contains("default/url")) { baseURL = confFileSettings.value("default/url").toUrl(); - if (debug) qDebug() << "URL loaded from config file."; } else { baseURL = DEFAULT_URL; - if (debug) qDebug() << "URL set by default."; } - if (debug) qDebug() << "Base URL: " << baseURL.toString(); - /* setting directory for downloads*/ + // setting directory for downloads if (clOpts.contains("downloadDir")){ downloadPath = clOpts.value("downloadDir"); - if (debug) qDebug() << "Download directory loaded from cmdline."; } else if (confFileSettings.contains("default/downloadDirectory")){ downloadPath = confFileSettings.value("default/downloadDirectory").toString(); - if (debug) qDebug() << "Download directory loaded from config file."; } - else - { + else { downloadPath = DEFAULT_DOWNLOAD_DIR; - if (debug) qDebug() << "Download directory set by default."; } - if (debug) qDebug() << "Download directory: " << downloadPath; if (confFileSettings.contains("default/updateInterval")){ updateInterval = confFileSettings.value("default/updateInterval").toInt(); - if (debug) qDebug() << "Read updateInterval from confFile: " << updateInterval; } else updateInterval = DEFAULT_UPDATE_INTERVAL; fbgui gui; + gui.show(); return app.exec(); } diff --git a/src/sysInfo.cpp b/src/sysinfo.cpp index ca20b95..1c8bc8d 100644 --- a/src/sysInfo.cpp +++ b/src/sysinfo.cpp @@ -1,21 +1,13 @@ -#include "sysInfo.h" -#include <QString> -#include <QTime> -#include <QNetworkInterface> -#include <QVariantMap> -#include <QVariantList> -#include <QByteArray> +#include "sysinfo.h" + // ------------------------------------------------------------------------------------------------ -sysInfo::sysInfo(){ - if (debug) qDebug() << "sysInfo created."; - // Maybe search for eth0, etc -} +SysInfo::SysInfo(){} // ------------------------------------------------------------------------------------------------ -sysInfo::~sysInfo(){} +SysInfo::~SysInfo(){} // ------------------------------------------------------------------------------------------------ -QString sysInfo::getInfo(QString& infoName){ - if (debug) qDebug() << "sysInfo : getInfo(" << infoName << ")"; +const QString SysInfo::getInfo(const QString& infoName){ + qxtLog->debug() << "[sysInfo] requested " << infoName; if (infoName == QString("mac")) return getMACAddress(); else if (infoName == QString("ip")) @@ -28,18 +20,18 @@ QString sysInfo::getInfo(QString& infoName){ return "info_error"; } // ------------------------------------------------------------------------------------------------ -QString sysInfo::getMACAddress(){ - /* Returns MAC address of eth0 for now. */ +const QString SysInfo::getMACAddress(){ + // Returns MAC address of eth0 for now QNetworkInterface qni = QNetworkInterface::interfaceFromName(QString("eth0")); if (!qni.isValid()){ - if (debug) qDebug() << "No interface matching \"eth0\" found."; + qxtLog->debug() << "No interface matching \"eth0\" found."; return "no_eth0"; } //eth0_index = qni.index(); return qni.hardwareAddress(); } // ------------------------------------------------------------------------------------------------ -QString sysInfo::getIPAddress(){ +const QString SysInfo::getIPAddress(){ // Again for eth0 only at the moment. // TODO: this doesn't quite work yet... QNetworkInterface qni = QNetworkInterface::interfaceFromName(QString("eth0")); @@ -47,16 +39,15 @@ QString sysInfo::getIPAddress(){ // This is does not return the right IP atm... foreach(QHostAddress addr, addrlist){ if (addr.protocol() == QAbstractSocket::IPv4Protocol && addr != QHostAddress::LocalHost){ - if (debug) qDebug() << "eth0: IPv4 Address: " << addr.toString(); return addr.toString(); } } // still here? - if (debug) qDebug() << "ip_error"; + qxtLog->debug() << "ip_error"; return "ip_error"; } // ------------------------------------------------------------------------------------------------ -QByteArray sysInfo::getNames(){ +const QByteArray SysInfo::getNames(){ QVariantMap foo; foo.insert("name", "foo"); @@ -72,12 +63,12 @@ QByteArray sysInfo::getNames(){ QJson::Serializer serializer; QByteArray json = serializer.serialize(jsonV); - if (debug) qDebug() << json; + qxtLog->debug() << json; return json; } // ------------------------------------------------------------------------------------------------ -QString sysInfo::getAllInfos(){ +QString SysInfo::getAllInfos(){ QVariantMap infos; infos.insert("mac", getMACAddress()); infos.insert("ip", getIPAddress()); @@ -87,11 +78,11 @@ QString sysInfo::getAllInfos(){ //QJson::Serializer serializer; QByteArray json = serializer.serialize(infos); - if (debug) qDebug() << json; + qxtLog->debug() << json; return json; } // ------------------------------------------------------------------------------------------------ -QString sysInfo::getScriptOutput(QString cmd) +QString SysInfo::getScriptOutput(QString cmd) { QProcess *process = new QProcess(); qDebug()<<"try to open: "<<cmd; diff --git a/src/sysInfo.h b/src/sysinfo.h index 3a6c217..cbb002e 100644 --- a/src/sysInfo.h +++ b/src/sysinfo.h @@ -20,24 +20,24 @@ #include "fbgui.h" #include <qjson/serializer.h> -#include <QVariantMap> -#include <QString> -class sysInfo { - public: - sysInfo(); - ~sysInfo(); - QString getInfo(QString& infoName); +class SysInfo { +public: + SysInfo(); + ~SysInfo(); + // public access, valid infoName: "mac", "ip", ... + const QString getInfo(const QString& infoName); - private: - QJson::Serializer serializer; - - - QByteArray getNames(); - QString getMACAddress(); - QString getIPAddress(); +private: + // private system information readers + const QString getMACAddress(); + const QString getIPAddress(); QString getAllInfos(); QString getScriptOutput(QString cmd); + + // JSon testing + QJson::Serializer serializer; + const QByteArray getNames(); }; #endif // SYSTINFO_H diff --git a/src/testApp.sh b/src/testApp.sh index 444636b..61f7c2d 100755 --- a/src/testApp.sh +++ b/src/testApp.sh @@ -11,7 +11,7 @@ script_path="$(cd "${0%/*}" 2>/dev/null; echo "$PWD"/"${0##*/}")" working_path=`dirname "$script_path"` display_id=$(grep -n $(whoami) /etc/passwd| head -n 1|awk -F : '{print $1}') # Start QT's virtual framebuffer with proper displayID -/usr/local/Trolltech/Qt-4.7.1/bin/qvfb -width 800 -height 600 -qwsdisplay :$display_id & +/usr/local/Trolltech/Qt-4.7.1/bin/qvfb -width 1024 -height 768 -qwsdisplay :$display_id & sleep 0.1 # Start fbgui. $working_path/fbgui -display QVFb:$display_id $@ |
