MultiplotConfigWidget.cpp
Go to the documentation of this file.
00001 /******************************************************************************
00002  * Copyright (C) 2015 by Ralf Kaestner                                        *
00003  * ralf.kaestner@gmail.com                                                    *
00004  *                                                                            *
00005  * This program is free software; you can redistribute it and/or modify       *
00006  * it under the terms of the Lesser GNU General Public License as published by*
00007  * the Free Software Foundation; either version 3 of the License, or          *
00008  * (at your option) any later version.                                        *
00009  *                                                                            *
00010  * This program is distributed in the hope that it will be useful,            *
00011  * but WITHOUT ANY WARRANTY; without even the implied warranty of             *
00012  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the               *
00013  * Lesser GNU General Public License for more details.                        *
00014  *                                                                            *
00015  * You should have received a copy of the Lesser GNU General Public License   *
00016  * along with this program. If not, see <http://www.gnu.org/licenses/>.       *
00017  ******************************************************************************/
00018 
00019 #include <QFileDialog>
00020 #include <QFileInfo>
00021 #include <QMessageBox>
00022 #include <QSettings>
00023 
00024 #include <ros/console.h>
00025 #include <ros/package.h>
00026 
00027 #include <rqt_multiplot/XmlSettings.h>
00028 
00029 #include <ui_MultiplotConfigWidget.h>
00030 
00031 #include "rqt_multiplot/MultiplotConfigWidget.h"
00032 
00033 namespace rqt_multiplot {
00034 
00035 /*****************************************************************************/
00036 /* Constructors and Destructor                                               */
00037 /*****************************************************************************/
00038 
00039 MultiplotConfigWidget::MultiplotConfigWidget(QWidget* parent, size_t
00040     maxHistoryLength) :
00041   QWidget(parent),
00042   ui_(new Ui::MultiplotConfigWidget()),
00043   config_(0),
00044   currentConfigModified_(false),
00045   maxHistoryLength_(maxHistoryLength) {
00046   ui_->setupUi(this);
00047   
00048   ui_->pushButtonClearHistory->setIcon(
00049     QIcon(QString::fromStdString(ros::package::getPath("rqt_multiplot").
00050     append("/resource/16x16/clear_history.png"))));
00051   ui_->pushButtonNew->setIcon(
00052     QIcon(QString::fromStdString(ros::package::getPath("rqt_multiplot").
00053     append("/resource/16x16/add.png"))));
00054   ui_->pushButtonOpen->setIcon(
00055     QIcon(QString::fromStdString(ros::package::getPath("rqt_multiplot").
00056     append("/resource/16x16/open.png"))));
00057   ui_->pushButtonSave->setIcon(
00058     QIcon(QString::fromStdString(ros::package::getPath("rqt_multiplot").
00059     append("/resource/16x16/save.png"))));
00060   ui_->pushButtonSaveAs->setIcon(
00061     QIcon(QString::fromStdString(ros::package::getPath("rqt_multiplot").
00062     append("/resource/16x16/save_as.png"))));
00063   
00064   ui_->pushButtonClearHistory->setEnabled(false);
00065   ui_->pushButtonSave->setEnabled(false);
00066   
00067   connect(ui_->configComboBox, SIGNAL(editTextChanged(const QString&)),
00068     this, SLOT(configComboBoxEditTextChanged(const QString&)));
00069   connect(ui_->configComboBox, SIGNAL(currentUrlChanged(const QString&)),
00070     this, SLOT(configComboBoxCurrentUrlChanged(const QString&)));
00071   
00072   connect(ui_->pushButtonClearHistory, SIGNAL(clicked()), this,
00073     SLOT(pushButtonClearHistoryClicked()));
00074   connect(ui_->pushButtonNew, SIGNAL(clicked()), this,
00075     SLOT(pushButtonNewClicked()));
00076   connect(ui_->pushButtonOpen, SIGNAL(clicked()), this,
00077     SLOT(pushButtonOpenClicked()));
00078   connect(ui_->pushButtonSave, SIGNAL(clicked()), this,
00079     SLOT(pushButtonSaveClicked()));
00080   connect(ui_->pushButtonSaveAs, SIGNAL(clicked()), this,
00081     SLOT(pushButtonSaveAsClicked()));
00082 }
00083 
00084 MultiplotConfigWidget::~MultiplotConfigWidget() {
00085   delete ui_;
00086 }
00087 
00088 /*****************************************************************************/
00089 /* Accessors                                                                 */
00090 /*****************************************************************************/
00091 
00092 void MultiplotConfigWidget::setConfig(MultiplotConfig* config) {
00093   if (config != config_) {
00094     if (config_)
00095       disconnect(config_, SIGNAL(changed()), this, SLOT(configChanged()));
00096     
00097     config_ = config;
00098     
00099     if (config)
00100       connect(config, SIGNAL(changed()), this, SLOT(configChanged()));
00101   }
00102 }
00103 
00104 MultiplotConfig* MultiplotConfigWidget::getConfig() const {
00105   return config_;
00106 }
00107 
00108 void MultiplotConfigWidget::setCurrentConfigUrl(const QString& url, bool
00109     updateHistory) {
00110   if (url != currentConfigUrl_) {
00111     currentConfigUrl_ = url;
00112     
00113     if (updateHistory)
00114       addConfigUrlToHistory(url);
00115     
00116     ui_->configComboBox->setCurrentUrl(url);
00117     
00118     emit currentConfigUrlChanged(url);
00119   }  
00120 }
00121 
00122 QString MultiplotConfigWidget::getCurrentConfigUrl() const {
00123   return ui_->configComboBox->getCurrentUrl();
00124 }
00125 
00126 bool MultiplotConfigWidget::setCurrentConfigModified(bool modified) {
00127   if (modified != currentConfigModified_) {
00128     currentConfigModified_ = modified;
00129     
00130     ui_->pushButtonSave->setEnabled(!currentConfigUrl_.isEmpty() &&
00131       (ui_->configComboBox->getCurrentUrl() == currentConfigUrl_) &&
00132       modified);
00133     
00134     emit currentConfigModifiedChanged(modified);
00135   }
00136 }
00137 
00138 bool MultiplotConfigWidget::isCurrentConfigModified() const {
00139   return currentConfigModified_;
00140 }
00141 
00142 void MultiplotConfigWidget::setMaxConfigUrlHistoryLength(size_t length) {
00143   if (length != maxHistoryLength_) {
00144     maxHistoryLength_ = length;
00145     
00146     while (ui_->configComboBox->count() > length)
00147       ui_->configComboBox->removeItem(ui_->configComboBox->count()-1);
00148   }
00149 }
00150 
00151 size_t MultiplotConfigWidget::getMaxConfigUrlHistoryLength() const {
00152   return maxHistoryLength_;
00153 }
00154 
00155 void MultiplotConfigWidget::setConfigUrlHistory(const QStringList& history) {
00156   ui_->configComboBox->clear();
00157   
00158   for (size_t i = 0; (i < history.count()) && (i < maxHistoryLength_); ++i)
00159     ui_->configComboBox->addItem(history[i]);
00160 }
00161 
00162 QStringList MultiplotConfigWidget::getConfigUrlHistory() const {
00163   QStringList history;
00164   
00165   for (size_t i = 0; i < ui_->configComboBox->count(); ++i)
00166     history.append(ui_->configComboBox->itemText(i));
00167   
00168   return history;
00169 }
00170 
00171 bool MultiplotConfigWidget::isFile(const QString& url) const {
00172   if (!url.isEmpty()) {
00173     UrlItemModel* model = ui_->configComboBox->getCompleter()->getModel();
00174     QString filePath = model->getFilePath(url);
00175     
00176     if (!filePath.isEmpty()) {
00177       QFileInfo fileInfo(filePath);
00178       
00179       return fileInfo.isFile();
00180     }
00181   }
00182   
00183   return false;
00184 }
00185 
00186 /*****************************************************************************/
00187 /* Methods                                                                   */
00188 /*****************************************************************************/
00189 
00190 bool MultiplotConfigWidget::loadConfig(const QString& url) {
00191   if (config_) {
00192     UrlItemModel* model = ui_->configComboBox->getCompleter()->getModel();
00193     QString filePath = model->getFilePath(url);
00194     
00195     if (!filePath.isEmpty()) {
00196       QFileInfo fileInfo(filePath);
00197       
00198       if (fileInfo.isReadable()) {
00199         QSettings settings(filePath, XmlSettings::format);
00200         
00201         if (settings.status() == QSettings::NoError) {
00202           settings.beginGroup("rqt_multiplot");
00203           config_->load(settings);
00204           settings.endGroup();
00205           
00206           setCurrentConfigUrl(url);
00207           setCurrentConfigModified(false);
00208           
00209           ROS_INFO_STREAM("Loaded configuration from [" <<
00210             url.toStdString() << "]");
00211           
00212           return true;
00213         }
00214       }
00215     }
00216   }
00217 
00218   ROS_ERROR_STREAM("Failed to load configuration from [" <<
00219     url.toStdString() << "]");
00220   
00221   return false;
00222 }
00223 
00224 bool MultiplotConfigWidget::saveCurrentConfig() {
00225   if (!currentConfigUrl_.isEmpty())
00226     return saveConfig(currentConfigUrl_);
00227     
00228   return false;
00229 }
00230 
00231 bool MultiplotConfigWidget::saveConfig(const QString& url) {
00232   if (config_) {
00233     UrlItemModel* model = ui_->configComboBox->getCompleter()->getModel();
00234     QString filePath = model->getFilePath(url);
00235     
00236     if (!filePath.isEmpty()) {
00237       QSettings settings(filePath, XmlSettings::format);
00238 
00239       if (settings.isWritable()) {
00240         settings.clear();
00241         
00242         settings.beginGroup("rqt_multiplot");
00243         config_->save(settings);
00244         settings.endGroup();
00245         
00246         settings.sync();
00247         
00248         if (settings.status() == QSettings::NoError) {
00249           setCurrentConfigUrl(url);
00250           setCurrentConfigModified(false);
00251           
00252           ROS_INFO_STREAM("Saved configuration to [" <<
00253             url.toStdString() << "]");
00254           
00255           return true;
00256         }
00257       }
00258     }
00259   }
00260   
00261   ROS_ERROR_STREAM("Failed to save configuration to [" <<
00262     url.toStdString() << "]");
00263   
00264   return false;
00265 }
00266 
00267 void MultiplotConfigWidget::resetConfig() {
00268   if (config_) {
00269     config_->reset();
00270     
00271     setCurrentConfigUrl(QString(), false);
00272     setCurrentConfigModified(false);
00273   }
00274 }
00275 
00276 bool MultiplotConfigWidget::confirmSave(bool canCancel) {
00277   if (currentConfigModified_) {
00278     QMessageBox messageBox;
00279     QMessageBox::StandardButtons buttons = QMessageBox::Save |
00280       QMessageBox::Discard;
00281       
00282     if (canCancel)
00283       buttons |= QMessageBox::Cancel;
00284     
00285     messageBox.setText("The configuration has been modified.");
00286     messageBox.setInformativeText("Do you want to save your changes?");
00287     messageBox.setStandardButtons(buttons);
00288     messageBox.setDefaultButton(QMessageBox::Save);
00289     
00290     switch (messageBox.exec()) {
00291       case QMessageBox::Save:
00292         if (currentConfigUrl_.isEmpty()) {
00293           QFileDialog dialog(this, "Save Configuration", QDir::homePath(),
00294             "Multiplot configurations (*.xml)");
00295           
00296           dialog.setAcceptMode(QFileDialog::AcceptSave);
00297           dialog.setFileMode(QFileDialog::AnyFile);
00298           dialog.selectFile("rqt_multiplot.xml");
00299           
00300           if (dialog.exec() == QDialog::Accepted)
00301             return saveConfig("file://"+dialog.selectedFiles().first());
00302           else
00303             return false;
00304         }
00305         else
00306           return saveCurrentConfig();
00307       case QMessageBox::Discard:
00308         return true;
00309       case QMessageBox::Cancel:
00310         return false;
00311       default:
00312         return false;
00313     }
00314   }
00315   
00316   return true;
00317 }
00318 
00319 void MultiplotConfigWidget::addConfigUrlToHistory(const QString& url) {
00320   if (!url.isEmpty()) {
00321     int index = ui_->configComboBox->findText(url);
00322     
00323     ui_->configComboBox->blockSignals(true);
00324     
00325     if (index < 0) {
00326       while (ui_->configComboBox->count()+1 > maxHistoryLength_)
00327         ui_->configComboBox->removeItem(ui_->configComboBox->count()-1);      
00328     }
00329     else
00330       ui_->configComboBox->removeItem(index);
00331     
00332     ui_->configComboBox->insertItem(0, url);
00333     
00334     ui_->configComboBox->blockSignals(false);
00335     
00336     ui_->pushButtonClearHistory->setEnabled(true);
00337   }
00338 }
00339 
00340 void MultiplotConfigWidget::clearConfigUrlHistory() {
00341   ui_->configComboBox->blockSignals(true);
00342 
00343   QString url = ui_->configComboBox->currentText();
00344   
00345   while (ui_->configComboBox->count())
00346     ui_->configComboBox->removeItem(ui_->configComboBox->count()-1);      
00347   
00348   if (!url.isEmpty())
00349     ui_->configComboBox->insertItem(0, url);
00350   
00351   ui_->configComboBox->blockSignals(false);
00352   
00353   ui_->pushButtonClearHistory->setEnabled(false);
00354 }
00355 
00356 /*****************************************************************************/
00357 /* Slots                                                                     */
00358 /*****************************************************************************/
00359 
00360 void MultiplotConfigWidget::configChanged() {
00361   setCurrentConfigModified(true);
00362 }
00363 
00364 void MultiplotConfigWidget::configComboBoxEditTextChanged(const
00365     QString& text) {
00366   if (!currentConfigUrl_.isEmpty()) {
00367     if (text != currentConfigUrl_)
00368       ui_->pushButtonSave->setEnabled(!isFile(text));
00369     else
00370       ui_->pushButtonSave->setEnabled(currentConfigModified_);
00371   }
00372   else
00373     ui_->pushButtonSave->setEnabled(false);
00374 }
00375 
00376 void MultiplotConfigWidget::configComboBoxCurrentUrlChanged(const
00377     QString& url) {
00378   if (url != currentConfigUrl_) {
00379     if (!isFile(url)) {
00380       if (!currentConfigUrl_.isEmpty()) {
00381         setCurrentConfigUrl(url, false);
00382         setCurrentConfigModified(true);
00383         
00384         ui_->pushButtonSave->setEnabled(true);
00385       }
00386       else
00387         ui_->pushButtonSave->setEnabled(false);
00388     }
00389     else {
00390       loadConfig(url);
00391       ui_->pushButtonSave->setEnabled(false);
00392     }
00393   }  
00394 }
00395 
00396 void MultiplotConfigWidget::pushButtonClearHistoryClicked() {
00397   QMessageBox messageBox;
00398   
00399   messageBox.setText("The configuration file history will be cleared.");
00400   messageBox.setInformativeText("Do you want to proceed?");
00401   messageBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No);
00402   messageBox.setDefaultButton(QMessageBox::No);
00403   
00404   if (messageBox.exec() == QMessageBox::Yes)
00405     clearConfigUrlHistory();
00406 }
00407 
00408 void MultiplotConfigWidget::pushButtonNewClicked() {
00409   if (confirmSave())
00410     resetConfig();
00411 }
00412 
00413 void MultiplotConfigWidget::pushButtonOpenClicked() {
00414   if (confirmSave()) {
00415     QFileDialog dialog(this, "Open Configuration", QDir::homePath(),
00416       "Multiplot configurations (*.xml)");
00417     
00418     dialog.setAcceptMode(QFileDialog::AcceptOpen);
00419     dialog.setFileMode(QFileDialog::ExistingFile);
00420     
00421     if (dialog.exec() == QDialog::Accepted)
00422       loadConfig("file://"+dialog.selectedFiles().first());
00423   }
00424 }
00425 
00426 void MultiplotConfigWidget::pushButtonSaveClicked() {
00427   if (currentConfigUrl_ == ui_->configComboBox->getCurrentUrl())
00428     saveCurrentConfig();
00429   else
00430     saveConfig(ui_->configComboBox->getCurrentUrl());
00431 }
00432 
00433 void MultiplotConfigWidget::pushButtonSaveAsClicked() {
00434   QFileDialog dialog(this, "Save Configuration", QDir::homePath(),
00435     "Multiplot configurations (*.xml)");
00436   
00437   dialog.setAcceptMode(QFileDialog::AcceptSave);
00438   dialog.setFileMode(QFileDialog::AnyFile);
00439   dialog.selectFile("rqt_multiplot.xml");
00440   
00441   if (dialog.exec() == QDialog::Accepted)
00442     saveConfig("file://"+dialog.selectedFiles().first());
00443 }
00444 
00445 }


rqt_multiplot
Author(s): Ralf Kaestner
autogenerated on Thu Jun 6 2019 21:49:11