console_window.cpp
Go to the documentation of this file.
00001 // *****************************************************************************
00002 //
00003 // Copyright (c) 2015, Southwest Research Institute® (SwRI®)
00004 // All rights reserved.
00005 //
00006 // Redistribution and use in source and binary forms, with or without
00007 // modification, are permitted provided that the following conditions are met:
00008 //     * Redistributions of source code must retain the above copyright
00009 //       notice, this list of conditions and the following disclaimer.
00010 //     * Redistributions in binary form must reproduce the above copyright
00011 //       notice, this list of conditions and the following disclaimer in the
00012 //       documentation and/or other materials provided with the distribution.
00013 //     * Neither the name of Southwest Research Institute® (SwRI®) nor the
00014 //       names of its contributors may be used to endorse or promote products
00015 //       derived from this software without specific prior written permission.
00016 //
00017 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
00018 // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00019 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00020 // ARE DISCLAIMED. IN NO EVENT SHALL Southwest Research Institute® BE LIABLE 
00021 // FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
00022 // DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 
00023 // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 
00024 // CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
00025 // LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
00026 // OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
00027 // DAMAGE.
00028 //
00029 // *****************************************************************************
00030 
00031 #include <stdint.h>
00032 #include <stdio.h>
00033 #include <set>
00034 
00035 #include <rosgraph_msgs/Log.h>
00036 #include <ros/master.h>  // required for getURI, VCM 12 April 2017
00037 
00038 
00039 #include <swri_console/console_window.h>
00040 #include <swri_console/log_database.h>
00041 #include <swri_console/log_database_proxy_model.h>
00042 #include <swri_console/node_list_model.h>
00043 #include <swri_console/settings_keys.h>
00044 
00045 #include <QColorDialog>
00046 #include <QRegExp>
00047 #include <QApplication>
00048 #include <QClipboard>
00049 #include <QDateTime>
00050 #include <QFileDialog>
00051 #include <QDir>
00052 #include <QScrollBar>
00053 #include <QMenu>
00054 #include <QSettings>
00055 
00056 using namespace Qt;
00057 
00058 namespace swri_console {
00059 
00060 ConsoleWindow::ConsoleWindow(LogDatabase *db)
00061   :
00062   QMainWindow(),
00063   db_(db),
00064   db_proxy_(new LogDatabaseProxyModel(db)),
00065   node_list_model_(new NodeListModel(db)),
00066   node_click_handler_(new NodeClickHandler())
00067 {
00068   ui.setupUi(this); 
00069 
00070   QObject::connect(ui.action_NewWindow, SIGNAL(triggered(bool)),
00071                    this, SIGNAL(createNewWindow()));
00072 
00073   QObject::connect(ui.action_Copy, SIGNAL(triggered()),
00074                    this, SLOT(copyLogs()));
00075 
00076   QObject::connect(ui.action_CopyExtended, SIGNAL(triggered()),
00077                    this, SLOT(copyExtendedLogs()));
00078   
00079   QObject::connect(ui.action_SelectAll, SIGNAL(triggered()),
00080                    this, SLOT(selectAllLogs()));
00081 
00082   QObject::connect(ui.action_ReadBagFile, SIGNAL(triggered(bool)),
00083                    this, SIGNAL(readBagFile()));
00084 
00085   QObject::connect(ui.action_ReadLogFile, SIGNAL(triggered(bool)),
00086                    this, SIGNAL(readLogFile()));
00087 
00088   QObject::connect(ui.action_ReadLogDirectory, SIGNAL(triggered(bool)),
00089                    this, SIGNAL(readLogDirectory()));
00090 
00091   QObject::connect(ui.action_SaveLogs, SIGNAL(triggered(bool)),
00092                    this, SLOT(saveLogs()));
00093 
00094   QObject::connect(ui.action_AbsoluteTimestamps, SIGNAL(toggled(bool)),
00095                    db_proxy_, SLOT(setAbsoluteTime(bool)));
00096 
00097   QObject::connect(ui.action_ShowTimestamps, SIGNAL(toggled(bool)),
00098                    db_proxy_, SLOT(setDisplayTime(bool)));
00099 
00100   QObject::connect(ui.action_RegularExpressions, SIGNAL(toggled(bool)),
00101                    db_proxy_, SLOT(setUseRegularExpressions(bool)));
00102 
00103   QObject::connect(ui.action_RegularExpressions, SIGNAL(toggled(bool)),
00104                    this, SLOT(updateIncludeLabel()));
00105 
00106   QObject::connect(ui.action_RegularExpressions, SIGNAL(toggled(bool)),
00107                    this, SLOT(updateExcludeLabel()));
00108 
00109   QObject::connect(ui.action_SelectFont, SIGNAL(triggered(bool)),
00110                    this, SIGNAL(selectFont()));
00111 
00112   QObject::connect(ui.action_ColorizeLogs, SIGNAL(toggled(bool)),
00113                    db_proxy_, SLOT(setColorizeLogs(bool)));
00114 
00115   QObject::connect(ui.debugColorWidget, SIGNAL(clicked(bool)),
00116                    this, SLOT(setDebugColor()));
00117   QObject::connect(ui.infoColorWidget, SIGNAL(clicked(bool)),
00118                    this, SLOT(setInfoColor()));
00119   QObject::connect(ui.warnColorWidget, SIGNAL(clicked(bool)),
00120                    this, SLOT(setWarnColor()));
00121   QObject::connect(ui.errorColorWidget, SIGNAL(clicked(bool)),
00122                    this, SLOT(setErrorColor()));
00123   QObject::connect(ui.fatalColorWidget, SIGNAL(clicked(bool)),
00124                    this, SLOT(setFatalColor()));
00125 
00126   ui.nodeList->setModel(node_list_model_);  
00127   ui.messageList->setModel(db_proxy_);
00128   ui.messageList->setUniformItemSizes(true);
00129 
00130   QObject::connect(
00131     ui.nodeList->selectionModel(),
00132     SIGNAL(selectionChanged(const QItemSelection &,
00133                                 const QItemSelection &)),
00134     this,
00135     SLOT(nodeSelectionChanged()));
00136 
00137   ui.nodeList->installEventFilter(node_click_handler_);
00138 
00139   QObject::connect(
00140     ui.checkDebug, SIGNAL(toggled(bool)),
00141     this, SLOT(setSeverityFilter()));
00142   QObject::connect(
00143     ui.checkInfo, SIGNAL(toggled(bool)),
00144     this, SLOT(setSeverityFilter()));
00145   QObject::connect(
00146     ui.checkWarn, SIGNAL(toggled(bool)),
00147     this, SLOT(setSeverityFilter()));
00148   QObject::connect(
00149     ui.checkError, SIGNAL(toggled(bool)),
00150     this, SLOT(setSeverityFilter()));
00151   QObject::connect(
00152     ui.checkFatal, SIGNAL(toggled(bool)),
00153     this, SLOT(setSeverityFilter()));
00154   QObject::connect(
00155     db_proxy_, SIGNAL(messagesAdded()),
00156     this, SLOT(messagesAdded()));
00157   QObject::connect(ui.checkFollowNewest, SIGNAL(toggled(bool)),
00158                    this, SLOT(setFollowNewest(bool)));
00159 
00160   // Right-click menu for the message list
00161   QObject::connect(ui.messageList, SIGNAL(customContextMenuRequested(const QPoint&)),
00162                     this, SLOT(showLogContextMenu(const QPoint&)));
00163 
00164   QObject::connect(ui.clearAllButton, SIGNAL(clicked()),
00165                     this, SLOT(clearAll()));
00166   QObject::connect(ui.clearMessagesButton, SIGNAL(clicked()),
00167                     this, SLOT(clearMessages()));
00168 
00169   QObject::connect(
00170     ui.messageList->verticalScrollBar(), SIGNAL(valueChanged(int)),
00171     this, SLOT(userScrolled(int)));
00172 
00173   QObject::connect(
00174     ui.includeText, SIGNAL(textChanged(const QString &)),
00175     this, SLOT(includeFilterUpdated(const QString &)));
00176 
00177   QObject::connect(
00178     ui.excludeText, SIGNAL(textChanged(const QString &)),
00179     this, SLOT(excludeFilterUpdated(const QString &)));
00180 
00181   // Connect 'Search' text modification to searchIndex, VCM 13 April 2017
00182   QObject::connect(
00183     ui.searchText, SIGNAL(textChanged(const QString &)),
00184     this, SLOT(searchIndex()));
00185   // Connect pushPrev to prevIndex()
00186   QObject::connect(ui.pushPrev, SIGNAL(clicked()),
00187     this, SLOT(prevIndex()));
00188   // Connect pushNext to nextIndex()
00189   QObject::connect(ui.pushNext, SIGNAL(clicked()),
00190     this, SLOT(nextIndex()));
00191 
00192 
00193   QList<int> sizes;
00194   sizes.append(100);
00195   sizes.append(1000);
00196   ui.splitter->setSizes(sizes);
00197 
00198   loadSettings();
00199 }
00200 
00201 ConsoleWindow::~ConsoleWindow()
00202 {
00203   delete db_proxy_;
00204 }
00205 
00206 void ConsoleWindow::clearAll()
00207 {
00208   db_->clear();
00209   node_list_model_->clear();
00210   db_proxy_->clearSearchFailure();  // resets failed search variables, VCM 27 April 2017
00211 }
00212 
00213 void ConsoleWindow::clearMessages()
00214 {
00215   db_->clear();
00216   db_proxy_->clearSearchFailure();  // resets failed search variables, VCM 27 April 2017
00217 }
00218 
00219 void ConsoleWindow::saveLogs()
00220 {
00221   QString defaultname = QDateTime::currentDateTime().toString(Qt::ISODate) + ".bag";
00222   QString filename = QFileDialog::getSaveFileName(this,
00223                                                   "Save Logs",
00224                                                   QDir::homePath() + QDir::separator() + defaultname,
00225                                                   tr("Bag Files (*.bag);;Text Files (*.txt)"));
00226   if (filename != NULL && !filename.isEmpty()) {
00227     db_proxy_->saveToFile(filename);
00228   }
00229 }
00230 
00231 void ConsoleWindow::connected(bool connected)
00232 {
00233   if (connected) {
00234     // When connected, display current URL along with status in the status bar, VCM 4/12/2017
00235     QString currentUrl = QString::fromStdString(ros::master::getURI());
00236     statusBar()->showMessage("Connected to ROS Master.  URL: "+currentUrl);
00237   } else {
00238     statusBar()->showMessage("Disconnected from ROS Master.");
00239   }
00240 }
00241 
00242 void ConsoleWindow::closeEvent(QCloseEvent *event)
00243 {
00244   QMainWindow::closeEvent(event);
00245 }
00246 
00247 void ConsoleWindow::nodeSelectionChanged()
00248 {
00249   db_proxy_->clearSearchFailure();  // clear search failure criteria, VCM 26 April 2017
00250   QModelIndexList selection = ui.nodeList->selectionModel()->selectedIndexes();
00251   std::set<std::string> nodes;
00252   QStringList node_names;
00253 
00254   for (int i = 0; i < selection.size(); i++) {
00255     std::string name = node_list_model_->nodeName(selection[i]);
00256     nodes.insert(name);
00257     node_names.append(name.c_str());
00258   }
00259 
00260   db_proxy_->setNodeFilter(nodes);
00261 
00262   for (int i = 0; i < node_names.size(); i++) {
00263     node_names[i] = node_names[i].split("/", QString::SkipEmptyParts).last();
00264   }
00265     
00266   setWindowTitle(QString("SWRI Console (") + node_names.join(", ") + ")");
00267 }
00268 
00269 void ConsoleWindow::setSeverityFilter()
00270 {
00271   uint8_t mask = 0;
00272 
00273   if (ui.checkDebug->isChecked()) {
00274     mask |= rosgraph_msgs::Log::DEBUG;
00275   }
00276   if (ui.checkInfo->isChecked()) {
00277     mask |= rosgraph_msgs::Log::INFO;
00278   }
00279   if (ui.checkWarn->isChecked()) {
00280     mask |= rosgraph_msgs::Log::WARN;
00281   }
00282   if (ui.checkError->isChecked()) {
00283     mask |= rosgraph_msgs::Log::ERROR;
00284   }
00285   if (ui.checkFatal->isChecked()) {
00286     mask |= rosgraph_msgs::Log::FATAL;
00287   }
00288 
00289   QSettings settings;
00290   settings.setValue(SettingsKeys::SHOW_DEBUG, ui.checkDebug->isChecked());
00291   settings.setValue(SettingsKeys::SHOW_INFO, ui.checkInfo->isChecked());
00292   settings.setValue(SettingsKeys::SHOW_WARN, ui.checkWarn->isChecked());
00293   settings.setValue(SettingsKeys::SHOW_ERROR, ui.checkError->isChecked());
00294   settings.setValue(SettingsKeys::SHOW_FATAL, ui.checkFatal->isChecked());
00295 
00296   db_proxy_->setSeverityFilter(mask);
00297   db_proxy_->clearSearchFailure();  // resets search failure variables, VCM 27 April 2017
00298 }
00299 
00300 void ConsoleWindow::messagesAdded()
00301 {
00302   if (ui.checkFollowNewest->isChecked()) {
00303     ui.messageList->scrollToBottom();
00304   }
00305 }
00306 
00307 
00308 void ConsoleWindow::showLogContextMenu(const QPoint& point)
00309 {
00310   QMenu contextMenu(tr("Context menu"), ui.messageList);
00311 
00312   QAction select_all(tr("Select All"), ui.messageList);
00313   connect(&select_all, SIGNAL(triggered()), this, SLOT(selectAllLogs()));
00314 
00315   QAction copy(tr("Copy"), ui.messageList);
00316   connect(&copy, SIGNAL(triggered()), this, SLOT(copyLogs()));
00317 
00318   QAction copy_extended(tr("Copy Extended"), ui.messageList);
00319   connect(&copy_extended, SIGNAL(triggered()), this, SLOT(copyExtendedLogs()));
00320 
00321   QAction alternate_row_colors(tr("Alternate Row Colors"), ui.messageList);
00322   alternate_row_colors.setCheckable(true);
00323   alternate_row_colors.setChecked(ui.messageList->alternatingRowColors());
00324   connect(&alternate_row_colors, SIGNAL(toggled(bool)),
00325           this, SLOT(toggleAlternateRowColors(bool)));
00326             
00327   contextMenu.addAction(&select_all);
00328   contextMenu.addAction(&copy);
00329   contextMenu.addAction(&copy_extended);
00330   contextMenu.addAction(&alternate_row_colors);
00331 
00332   contextMenu.exec(ui.messageList->mapToGlobal(point));
00333 }
00334 
00335 void ConsoleWindow::userScrolled(int value)
00336 {
00337   if (value != ui.messageList->verticalScrollBar()->maximum()) {
00338     ui.checkFollowNewest->setChecked(false);
00339   } else {
00340     ui.checkFollowNewest->setChecked(true);
00341   }
00342 }
00343 
00344 
00345 void ConsoleWindow::selectAllLogs()
00346 {
00347   if (ui.nodeList->hasFocus()) {
00348     ui.nodeList->selectAll();
00349   } else {
00350     ui.messageList->selectAll();
00351   }
00352 }
00353 
00354 void ConsoleWindow::copyLogs()
00355 {
00356   QStringList buffer;
00357   foreach(const QModelIndex &index, ui.messageList->selectionModel()->selectedIndexes())
00358   {
00359     buffer << db_proxy_->data(index, Qt::DisplayRole).toString();
00360   }
00361   QApplication::clipboard()->setText(buffer.join(tr("\n")));
00362 }
00363 
00364 void ConsoleWindow::copyExtendedLogs()
00365 {
00366   QStringList buffer;
00367   foreach(const QModelIndex &index, ui.messageList->selectionModel()->selectedIndexes())
00368   {
00369     buffer << db_proxy_->data(index, LogDatabaseProxyModel::ExtendedLogRole).toString();
00370   }
00371   QApplication::clipboard()->setText(buffer.join(tr("\n\n")));
00372 }
00373 
00374 void ConsoleWindow::setFollowNewest(bool follow)
00375 {
00376   QSettings settings;
00377   settings.setValue(SettingsKeys::FOLLOW_NEWEST, follow);
00378 }
00379 
00380 void ConsoleWindow::includeFilterUpdated(const QString &text)
00381 {
00382   QStringList items = text.split(";", QString::SkipEmptyParts);
00383   QStringList filtered;
00384   
00385   for (int i = 0; i < items.size(); i++) {
00386     QString x = items[i].trimmed();
00387     if (!x.isEmpty()) {
00388       filtered.append(x);
00389     }
00390   }
00391 
00392   db_proxy_->setIncludeFilters(filtered);
00393   db_proxy_->setIncludeRegexpPattern(text);
00394   db_proxy_->clearSearchFailure();  // resets failed search variables, VCM 27 April 2017
00395   updateIncludeLabel();
00396 }
00397 
00398 void ConsoleWindow::excludeFilterUpdated(const QString &text)
00399 {
00400   QStringList items = text.split(";", QString::SkipEmptyParts);
00401   QStringList filtered;
00402   
00403   for (int i = 0; i < items.size(); i++) {
00404     QString x = items[i].trimmed();
00405     if (!x.isEmpty()) {
00406       filtered.append(x);
00407     }
00408   }
00409 
00410   db_proxy_->setExcludeFilters(filtered);
00411   db_proxy_->setExcludeRegexpPattern(text);
00412   db_proxy_->clearSearchFailure();  // resets failed search variables, VCM 27 April 2017
00413   updateExcludeLabel();
00414 }
00415 
00416 // Slot called when 'Search' text modified, 13 April 2017 VCM
00417 void ConsoleWindow::searchIndex()
00418 {
00419   updateCurrentIndex(SEARCH);
00420 }
00421 // Slot called when 'Previous' button pushed, 13 April 2017 VCM
00422 void ConsoleWindow::prevIndex()
00423 {
00424   updateCurrentIndex(PREV);
00425 }
00426 // Slot called when 'Next' button pushed,  13 April 2017 VCM
00427 void ConsoleWindow::nextIndex()
00428 {
00429   updateCurrentIndex(NEXT);
00430 }
00431 
00432 // Search Function sF Definitions:
00433 //   1)search - user modified 'Search' text
00434 //   2)next   - user pressed 'Next' button
00435 //   3)prev   - user pressed 'Previous' button
00436 // Locates and selects the next item based on search criteria, VCM 26 April 2017
00437 void ConsoleWindow::updateCurrentIndex(function sF)
00438 {
00439   int rowSearchStart = ui.messageList->currentIndex().row();  // retrieve current index
00440   int increment = 1;  // used for search/next/prev; prev(ious) increment will change to -1
00441   QString searchText = ui.searchText->text();  // actual text to search for
00442   searchText = searchText.toUpper().trimmed();  // remove lowercase and lead/trailing spaces.
00443   // next button pushed
00444   if(sF == NEXT){
00445     rowSearchStart++;  // start search row after current.
00446   }
00447   // Previous button pushed
00448   else if(sF== PREV){
00449     rowSearchStart--;  // start search row before current
00450     increment=-1;  // -1 to move search up instead of down
00451   }
00452   // search text modified
00453   else if(sF==SEARCH )
00454   {
00455     if (rowSearchStart==-1){
00456       rowSearchStart =0;  // for search, no selection (-1) index change to 0
00457     }
00458   }
00459   else
00460   {
00461     // should not end up here
00462     printf("Invalid string passed to ConsoleWindow::nextIndex");
00463     return;
00464   }
00465   // calls getItemIndex in log_database_proxy_m, returns new index
00466   int newRowIndex = db_proxy_->getItemIndex(searchText,rowSearchStart, increment);
00467   ui.messageList->clearSelection();  // clear current selection
00468   if(newRowIndex == -1)  // indicates no match.
00469   {
00470     return;
00471   }
00472 
00473   QModelIndex index = ui.messageList->model()->index(newRowIndex,0);  // defines desired index
00474   ui.messageList->setCurrentIndex(index);  // sets desired index, re-centers screen on new index
00475   ui.checkFollowNewest->setChecked(false);  // stops scrolling if search found
00476 
00477 
00478 }
00479 
00480 
00481 void ConsoleWindow::updateIncludeLabel()
00482 {
00483   if (db_proxy_->isIncludeValid()) {
00484     ui.includeLabel->setText("Include");
00485   } else {
00486     ui.includeLabel->setText("<font color='red'>Include</font>");
00487   }
00488 }
00489 
00490 void ConsoleWindow::updateExcludeLabel()
00491 {
00492   if (db_proxy_->isExcludeValid()) {
00493     ui.excludeLabel->setText("Exclude");
00494   } else {
00495     ui.excludeLabel->setText("<font color='red'>Exclude</font>");
00496   }
00497 }
00498 
00499 void ConsoleWindow::setFont(const QFont &font)
00500 {
00501   ui.messageList->setFont(font);
00502   ui.nodeList->setFont(font);
00503 }
00504 
00505 void ConsoleWindow::setDebugColor()
00506 {
00507   chooseButtonColor(ui.debugColorWidget);
00508 }
00509 
00510 void ConsoleWindow::setInfoColor()
00511 {
00512   chooseButtonColor(ui.infoColorWidget);
00513 }
00514 
00515 void ConsoleWindow::setWarnColor()
00516 {
00517   chooseButtonColor(ui.warnColorWidget);
00518 }
00519 
00520 void ConsoleWindow::setErrorColor()
00521 {
00522   chooseButtonColor(ui.errorColorWidget);
00523 }
00524 
00525 void ConsoleWindow::setFatalColor()
00526 {
00527   chooseButtonColor(ui.fatalColorWidget);
00528 }
00529 
00530 void ConsoleWindow::chooseButtonColor(QPushButton* widget)
00531 {
00532   QColor old_color = getButtonColor(widget);
00533   QColor color = QColorDialog::getColor(old_color, this);
00534   if (color.isValid()) {
00535     updateButtonColor(widget, color);
00536   }
00537 }
00538 
00539 QColor ConsoleWindow::getButtonColor(const QPushButton* button) const
00540 {
00541   QString ss = button->styleSheet();
00542   QRegExp re("background: (#\\w*);");
00543   QColor old_color;
00544   if (re.indexIn(ss) >= 0) {
00545     old_color = QColor(re.cap(1));
00546   }
00547   return old_color;
00548 }
00549 
00550 void ConsoleWindow::updateButtonColor(QPushButton* widget, const QColor& color)
00551 {
00552   QString s("background: #"
00553             + QString(color.red() < 16? "0" : "") + QString::number(color.red(),16)
00554             + QString(color.green() < 16? "0" : "") + QString::number(color.green(),16)
00555             + QString(color.blue() < 16? "0" : "") + QString::number(color.blue(),16) + ";");
00556   widget->setStyleSheet(s);
00557   widget->update();
00558 
00559   if (widget == ui.debugColorWidget) {
00560     db_proxy_->setDebugColor(color);
00561   }
00562   else if (widget == ui.infoColorWidget) {
00563     db_proxy_->setInfoColor(color);
00564   }
00565   else if (widget == ui.warnColorWidget) {
00566     db_proxy_->setWarnColor(color);
00567   }
00568   else if (widget == ui.errorColorWidget) {
00569     db_proxy_->setErrorColor(color);
00570   }
00571   else if (widget == ui.fatalColorWidget) {
00572     db_proxy_->setFatalColor(color);
00573   }
00574   else {
00575     qWarning("Unexpected widget passed to ConsoleWindow::updateButtonColor.");
00576   }
00577 }
00578 
00579 void ConsoleWindow::loadColorButtonSetting(const QString& key, QPushButton* button)
00580 {
00581   QSettings settings;
00582   QColor defaultColor;
00583   // The color buttons don't have a default value set in the .ui file, so we need to
00584   // supply defaults for them here in case the appropriate setting isn't found.
00585   if (button == ui.debugColorWidget) {
00586     defaultColor = Qt::gray;
00587   }
00588   else if (button == ui.infoColorWidget) {
00589     defaultColor = Qt::black;
00590   }
00591   else if (button == ui.warnColorWidget) {
00592     defaultColor = QColor(255, 127, 0);
00593   }
00594   else if (button == ui.errorColorWidget) {
00595     defaultColor = Qt::red;
00596   }
00597   else if (button == ui.fatalColorWidget) {
00598     defaultColor = Qt::magenta;
00599   }
00600   QColor color = settings.value(key, defaultColor).value<QColor>();
00601   updateButtonColor(button, color);
00602 }
00603 
00604 void ConsoleWindow::toggleAlternateRowColors(bool checked)
00605 {
00606   ui.messageList->setAlternatingRowColors(checked);
00607 
00608   QSettings settings;
00609   settings.setValue(SettingsKeys::ALTERNATE_LOG_ROW_COLORS, checked);
00610 }
00611 
00612 void ConsoleWindow::loadSettings()
00613 {
00614   // First, load all the boolean settings...
00615   loadBooleanSetting(SettingsKeys::DISPLAY_TIMESTAMPS, ui.action_ShowTimestamps);
00616   loadBooleanSetting(SettingsKeys::ABSOLUTE_TIMESTAMPS, ui.action_AbsoluteTimestamps);
00617   loadBooleanSetting(SettingsKeys::USE_REGEXPS, ui.action_RegularExpressions);
00618   loadBooleanSetting(SettingsKeys::COLORIZE_LOGS, ui.action_ColorizeLogs);
00619   loadBooleanSetting(SettingsKeys::FOLLOW_NEWEST, ui.checkFollowNewest);
00620 
00621   // The severity level has to be handled a little differently, since they're all combined
00622   // into a single integer mask under the hood.  First they have to be loaded from the settings,
00623   // then set in the UI, then the mask has to actually be applied.
00624   QSettings settings;
00625   bool showDebug = settings.value(SettingsKeys::SHOW_DEBUG, true).toBool();
00626   bool showInfo = settings.value(SettingsKeys::SHOW_INFO, true).toBool();
00627   bool showWarn = settings.value(SettingsKeys::SHOW_WARN, true).toBool();
00628   bool showError = settings.value(SettingsKeys::SHOW_ERROR, true).toBool();
00629   bool showFatal = settings.value(SettingsKeys::SHOW_FATAL, true).toBool();
00630   ui.checkDebug->setChecked(showDebug);
00631   ui.checkInfo->setChecked(showInfo);
00632   ui.checkWarn->setChecked(showWarn);
00633   ui.checkError->setChecked(showError);
00634   ui.checkFatal->setChecked(showFatal);
00635   setSeverityFilter();
00636 
00637   // Load button colors.
00638   loadColorButtonSetting(SettingsKeys::DEBUG_COLOR, ui.debugColorWidget);
00639   loadColorButtonSetting(SettingsKeys::INFO_COLOR, ui.infoColorWidget);
00640   loadColorButtonSetting(SettingsKeys::WARN_COLOR, ui.warnColorWidget);
00641   loadColorButtonSetting(SettingsKeys::ERROR_COLOR, ui.errorColorWidget);
00642   loadColorButtonSetting(SettingsKeys::FATAL_COLOR, ui.fatalColorWidget);
00643 
00644   // Finally, load the filter contents.
00645   QString includeFilter = settings.value(SettingsKeys::INCLUDE_FILTER, "").toString();
00646   ui.includeText->setText(includeFilter);
00647   QString excludeFilter = settings.value(SettingsKeys::EXCLUDE_FILTER, "").toString();
00648   ui.excludeText->setText(excludeFilter);
00649 
00650   bool alternate_row_colors = settings.value(SettingsKeys::ALTERNATE_LOG_ROW_COLORS, true).toBool();
00651   ui.messageList->setAlternatingRowColors(alternate_row_colors);
00652 }
00653 }  // namespace swri_console
00654 


swri_console
Author(s):
autogenerated on Sat Jun 8 2019 18:46:13