File indexing completed on 2025-07-13 04:09:36
0001 /*************************************************************************** 0002 * * 0003 * copyright : (C) 2007 The University of Toronto * 0004 * netterfield@astro.utoronto.ca * 0005 * * 0006 * This program is free software; you can redistribute it and/or modify * 0007 * it under the terms of the GNU General Public License as published by * 0008 * the Free Software Foundation; either version 2 of the License, or * 0009 * (at your option) any later version. * 0010 * * 0011 ***************************************************************************/ 0012 0013 #include "mainwindow.h" 0014 #include "boxitem.h" 0015 #include "datamanager.h" 0016 #include "debugdialog.h" 0017 #include "debugnotifier.h" 0018 #include "document.h" 0019 #include "ellipseitem.h" 0020 #include "exportgraphicsdialog.h" 0021 #include "exportvectorsdialog.h" 0022 #include "logdialog.h" 0023 #include "application.h" 0024 #include "debug.h" 0025 #include "labelitem.h" 0026 #include "lineitem.h" 0027 #include "circleitem.h" 0028 #include "arrowitem.h" 0029 #include "memorywidget.h" 0030 #include "objectstore.h" 0031 #include "pictureitem.h" 0032 #include "plotitem.h" 0033 #include "plotitemmanager.h" 0034 #include "svgitem.h" 0035 #include "tabwidget.h" 0036 #include "sharedaxisboxitem.h" 0037 #include "ui_aboutdialog.h" 0038 #include "viewvectordialog.h" 0039 #include "viewmatrixdialog.h" 0040 #include "viewprimitivedialog.h" 0041 #include "view.h" 0042 #include "applicationsettings.h" 0043 #include "updatemanager.h" 0044 #include "datasourcepluginmanager.h" 0045 #include "pluginmenuitemaction.h" 0046 0047 #include "applicationsettingsdialog.h" 0048 #include "themedialog.h" 0049 #include "differentiatecurvesdialog.h" 0050 #include "filtermultipledialog.h" 0051 #include "choosecolordialog.h" 0052 #include "changedatasampledialog.h" 0053 #include "changefiledialog.h" 0054 #include "bugreportwizard.h" 0055 #include "datawizard.h" 0056 #include "aboutdialog.h" 0057 #include "shortcutdialog.h" 0058 #include "datavector.h" 0059 #include "commandlineparser.h" 0060 #include "dialogdefaults.h" 0061 #include "colorsequence.h" 0062 #include "settings.h" 0063 0064 #include "dialoglauncher.h" 0065 #include "scriptserver.h" 0066 0067 #include "geticon.h" 0068 0069 #ifndef KST_NO_SVG 0070 #include <QSvgGenerator> 0071 #endif 0072 0073 #include <QUndoGroup> 0074 #ifndef KST_NO_PRINTER 0075 #include <QPrintDialog> 0076 #endif 0077 #include <QMenuBar> 0078 #include <QStatusBar> 0079 #include <QProgressBar> 0080 #include <QMessageBox> 0081 #include <QImageWriter> 0082 #include <QToolBar> 0083 #include <QDebug> 0084 #include <QDesktopServices> 0085 #include <QSignalMapper> 0086 #include <QClipboard> 0087 0088 namespace Kst { 0089 0090 MainWindow::MainWindow() : 0091 _settings(createSettings("application")), 0092 _dataManager(0), 0093 _exportGraphics(0), 0094 _exportVectors(0), 0095 _logDialog(0), 0096 _differentiateCurvesDialog(0), 0097 _filterMultipleDialog(0), 0098 _chooseColorDialog(0), 0099 _changeDataSampleDialog(0), 0100 _changeFileDialog(0), 0101 _bugReportWizard(0), 0102 _applicationSettingsDialog(0), 0103 _themeDialog(0), 0104 _aboutDialog(0), 0105 _shortcutDialog(0), 0106 _viewVectorDialog(0), 0107 _highlightPoint(false), 0108 _statusBarTimeout(0), 0109 #if defined(__QNX__) 0110 qnxToolbarsVisible(true), 0111 #endif 0112 _ae_width(1280), 0113 _ae_height(1024), 0114 _ae_display(2), 0115 _ae_export_all(false), 0116 _ae_autosave_period(0), 0117 _ae_Timer(0), 0118 _sessionFileName(QString()) 0119 { 0120 _doc = new Document(this); 0121 _scriptServer = new ScriptServer(_doc->objectStore()); 0122 _videoMapper = new QSignalMapper(this); 0123 0124 _tabWidget = new TabWidget(this); 0125 _undoGroup = new QUndoGroup(this); 0126 _debugDialog = new DebugDialog(this); 0127 0128 Debug::self()->setHandler(_debugDialog); 0129 0130 setKstWindowTitle(); 0131 0132 createActions(); 0133 createMenus(); 0134 createToolBars(); 0135 createStatusBar(); 0136 0137 _tabWidget->createView(); 0138 0139 setCentralWidget(_tabWidget); 0140 _tabWidget->setAcceptDrops(false); // Force drops to be passed to parent 0141 connect(_tabWidget, SIGNAL(currentChanged(int)), this, SLOT(currentViewChanged())); 0142 connect(_tabWidget, SIGNAL(currentViewModeChanged()), this, SLOT(currentViewModeChanged())); 0143 connect(PlotItemManager::self(), SIGNAL(tiedZoomRemoved()), this, SLOT(tiedZoomRemoved())); 0144 connect(PlotItemManager::self(), SIGNAL(allPlotsTiedZoom()), this, SLOT(allPlotsTiedZoom())); 0145 0146 readSettings(); 0147 connect(UpdateManager::self(), SIGNAL(objectsUpdated(qint64)), this, SLOT(updateViewItems(qint64))); 0148 0149 QTimer::singleShot(0, this, SLOT(performHeavyStartupActions())); 0150 0151 updateRecentKstFiles(); 0152 setAcceptDrops(true); 0153 0154 #if defined(__QNX__) 0155 // We want to be able to intercept bezel gestures, which show up in Qt as menu button keyPressEvents. 0156 qApp->installEventFilter(this); 0157 qnxToggleToolbarVisibility(); 0158 #endif 0159 0160 } 0161 0162 0163 MainWindow::~MainWindow() { 0164 delete _dataManager; 0165 _dataManager = 0; 0166 delete _doc; 0167 _doc = 0; 0168 delete _viewVectorDialog; 0169 _viewVectorDialog = 0; 0170 delete _scriptServer; 0171 _scriptServer = 0; 0172 } 0173 0174 0175 void MainWindow::performHeavyStartupActions() { 0176 // Set the timer for the UpdateManager. 0177 UpdateManager::self()->setMinimumUpdatePeriod(ApplicationSettings::self()->minimumUpdatePeriod()); 0178 DataObject::init(); 0179 DataSourcePluginManager::init(); 0180 } 0181 0182 void MainWindow::cleanup() { 0183 if (document() && document()->objectStore()) { 0184 document()->objectStore()->clear(); 0185 } 0186 } 0187 0188 0189 void MainWindow::setLayoutMode(bool layoutMode) { 0190 foreach (View *v, tabWidget()->views() ) { 0191 0192 Q_ASSERT(v); 0193 0194 if (layoutMode) { 0195 v->setViewMode(View::Layout); 0196 _highlightPointAct->setEnabled(false); 0197 _tiedZoomAct->setEnabled(false); 0198 } else { 0199 v->setViewMode(View::Data); 0200 _highlightPointAct->setEnabled(true); 0201 _tiedZoomAct->setEnabled(true); 0202 } 0203 } 0204 } 0205 0206 void MainWindow::setHighlightPoint(bool highlight) { 0207 _highlightPoint = highlight; 0208 } 0209 0210 void MainWindow::changeZoomOnlyMode(QAction* act) { 0211 if (act == _layoutModeAct && act->isChecked()) { 0212 setLayoutMode(true); 0213 } else { 0214 setLayoutMode(false); 0215 } 0216 foreach (View *view, tabWidget()->views() ) { 0217 view->setZoomOnly((View::ZoomOnlyMode)act->data().toInt()); 0218 } 0219 0220 } 0221 0222 void MainWindow::toggleTiedZoom() { 0223 if (isTiedTabs()) { 0224 PlotItemManager::self()->toggleAllTiedZoom(0); 0225 /* 0226 QList<View*> views = tabWidget()->views(); 0227 foreach (View* view, views) { 0228 PlotItemManager::self()->toggleAllTiedZoom(view); 0229 } 0230 */ 0231 } else { 0232 PlotItemManager::self()->toggleAllTiedZoom(tabWidget()->currentView()); 0233 } 0234 } 0235 0236 void MainWindow::tiedZoomRemoved() { 0237 _tiedZoomAct->setChecked(false); 0238 } 0239 0240 0241 void MainWindow::allPlotsTiedZoom() { 0242 _tiedZoomAct->setChecked(true); 0243 } 0244 0245 0246 bool MainWindow::promptSaveDone() { 0247 if (! _doc->isChanged()) { 0248 return true; // No need to ask if there is no unsaved change -> we're done 0249 } 0250 else { // Changes registered: ask the user 0251 int rc = QMessageBox::warning(this, tr("Kst: Save Prompt"), tr("Your document has been modified.\nSave changes?"), QMessageBox::Save | QMessageBox::Discard | QMessageBox::Cancel, QMessageBox::Save); 0252 if (rc == QMessageBox::Save) { 0253 save(); 0254 } else if (rc == QMessageBox::Cancel) { 0255 return false; 0256 } 0257 return true; 0258 } 0259 } 0260 0261 0262 void MainWindow::closeEvent(QCloseEvent *e) { 0263 if (!promptSaveDone()) { 0264 e->ignore(); 0265 return; 0266 } 0267 //cleanup(); 0268 QMainWindow::closeEvent(e); 0269 kstApp->closeAllWindows(); 0270 } 0271 0272 0273 Document *MainWindow::document() const { 0274 return _doc; 0275 } 0276 0277 0278 QUndoGroup *MainWindow::undoGroup() const { 0279 return _undoGroup; 0280 } 0281 0282 0283 TabWidget *MainWindow::tabWidget() const { 0284 return _tabWidget; 0285 } 0286 0287 0288 void MainWindow::save() { 0289 if (_doc->isOpen()) { 0290 _doc->save(); 0291 } else { 0292 saveAs(); 0293 } 0294 } 0295 0296 0297 void MainWindow::saveAs() { 0298 QString fn = QFileDialog::getSaveFileName(this, tr("Kst: Save File"), _doc->fileName(), tr("Kst Sessions (*.kst)")); 0299 if (fn.isEmpty()) { 0300 return; 0301 } 0302 QString restorePath = QDir::currentPath(); 0303 QString kstfiledir = fn.left(fn.lastIndexOf('/')) + '/'; 0304 QDir::setCurrent(kstfiledir); 0305 //QString currentP = QDir::currentPath(); 0306 _doc->save(fn); 0307 QDir::setCurrent(restorePath); 0308 _sessionFileName = fn; 0309 setKstWindowTitle(); 0310 updateRecentKstFiles(fn); 0311 } 0312 0313 void MainWindow::newDoc(bool force) { 0314 bool clearApproved = false; 0315 if (force) { 0316 clearApproved = true; 0317 } else { 0318 clearApproved = promptSaveDone(); 0319 } 0320 0321 if (clearApproved) { 0322 cleanup(); 0323 delete _dataManager; 0324 _dataManager = 0; 0325 delete _doc; 0326 resetNameIndexes(); 0327 _doc = new Document(this); 0328 _scriptServer->setStore(_doc->objectStore()); 0329 tabWidget()->clear(); 0330 tabWidget()->createView(); 0331 return; 0332 } else { 0333 return; 0334 } 0335 0336 } 0337 0338 void MainWindow::open() { 0339 if (!promptSaveDone()) { 0340 return; 0341 } 0342 const QString key = "lastOpenedKstFile"; 0343 QString fn = _settings.value(key).toString(); 0344 if (fn.isEmpty()) { 0345 fn = _doc->fileName(); 0346 } 0347 fn = QFileDialog::getOpenFileName(this, tr("Kst: Open File"), fn, tr("Kst Sessions (*.kst)")); 0348 if (fn.isEmpty()) { 0349 return; 0350 } 0351 _settings.setValue(key, fn); 0352 openFile(fn); 0353 } 0354 0355 0356 0357 QAction* MainWindow::createRecentFileAction(const QString& filename, int idx, const QString& name, const char* openslot) 0358 { 0359 QAction* action = new QAction(this); 0360 QString text = tr("&%1 %2", "Part of a list. %1 is an index. %2 is a file name").arg(idx).arg(name); 0361 action->setText(text); 0362 action->setData(filename); 0363 action->setStatusTip(filename); 0364 action->setVisible(true); 0365 connect(action, SIGNAL(triggered()), this, openslot); 0366 return action; 0367 } 0368 0369 0370 void MainWindow::updateRecentKstFiles(const QString& filename) 0371 { 0372 updateRecentFiles("recentKstFileList", _fileMenu, _bottomRecentKstActions, _recentKstFilesMenu, filename, SLOT(openRecentKstFile())); 0373 } 0374 0375 void MainWindow::setKstWindowTitle() 0376 { 0377 QString title = "Kst"; 0378 QString server_name = _scriptServer->serverName; 0379 QString user_name = "--"+kstApp->userName(); 0380 0381 if (server_name.endsWith(user_name)) { 0382 server_name.remove(server_name.lastIndexOf(user_name),10000); 0383 } 0384 0385 if (!_sessionFileName.isEmpty()) { 0386 title += " - " + _sessionFileName; 0387 } 0388 if (scriptServerNameSet()) { 0389 title += " -- " + server_name; 0390 } 0391 setWindowTitle(title); 0392 } 0393 0394 QString MainWindow::scriptServerName() 0395 { 0396 return _scriptServer->serverName; 0397 } 0398 0399 bool MainWindow::scriptServerNameSet() 0400 { 0401 return _scriptServer->serverNameSet; 0402 } 0403 0404 void MainWindow::setScriptServerName(QString server_name) 0405 { 0406 _scriptServer->setScriptServerName(server_name); 0407 setKstWindowTitle(); 0408 } 0409 0410 void MainWindow::copyTab() 0411 { 0412 View *view = _tabWidget->currentView(); 0413 QClipboard *clipboard = QApplication::clipboard(); 0414 QMimeData *mimedata = new QMimeData(); 0415 0416 QPainter painter; 0417 QPixmap pixmap(view->size()); 0418 0419 painter.begin(&pixmap); 0420 0421 view->setPrinting(true); 0422 view->render(&painter); 0423 view->setPrinting(false); 0424 0425 painter.end(); 0426 0427 //mimedata->setText("Some text from kst, just for you!"); 0428 mimedata->setImageData(pixmap.toImage()); 0429 0430 clipboard->setMimeData(mimedata); 0431 } 0432 0433 0434 void MainWindow::updateRecentDataFiles(const QString& filename) 0435 { 0436 updateRecentFiles("recentDataFileList", _toolsMenu, _bottomRecentDataActions, _recentDataFilesMenu, filename, SLOT(openRecentDataFile())); 0437 if (!filename.isEmpty()) { 0438 dialogDefaults().setValue("vector/datasource", filename); 0439 } 0440 } 0441 0442 0443 QStringList MainWindow::recentDataFiles() { 0444 QStringList recentFiles = _settings.value("recentDataFileList").toStringList(); 0445 if (recentFiles.removeDuplicates() > 0) { 0446 _settings.setValue("recentDataFileList", recentFiles); 0447 } 0448 return recentFiles; 0449 } 0450 0451 void MainWindow::cleanupRecentDataFilesList() { 0452 QStringList recentFiles = _settings.value("recentDataFileList").toStringList(); 0453 recentFiles.removeDuplicates(); 0454 foreach(const QString& it, recentFiles) { 0455 if (!QFileInfo(it).exists()) { 0456 recentFiles.removeOne(it); 0457 } 0458 } 0459 _settings.setValue("recentDataFileList", recentFiles); 0460 updateRecentKstFiles(); 0461 updateRecentDataFiles(); 0462 } 0463 0464 0465 void MainWindow::updateRecentFiles(const QString& key ,QMenu* menu, QList<QAction*>& actions, QMenu* submenu, const QString& newfilename, const char* openslot) 0466 { 0467 // Always add absolute paths to the recent file lists, otherwise they are not very reusable 0468 QString absoluteFilePath = DataSource::cleanPath(newfilename); 0469 if (!newfilename.isEmpty() && !QDir::isAbsolutePath(newfilename)) { // If it's not empty and not absolute either, add the dir 0470 absoluteFilePath = DataSource::cleanPath(QDir::currentPath() + '/' + newfilename); 0471 } 0472 foreach(QAction* it, actions) { 0473 menu->removeAction(it); 0474 delete it; 0475 } 0476 actions.clear(); 0477 QStringList recentFiles = _settings.value(key).toStringList(); 0478 if (recentFiles.removeDuplicates() > 0) { 0479 _settings.setValue(key, recentFiles); 0480 } 0481 if (!absoluteFilePath.isEmpty()) { 0482 recentFiles.removeOne(absoluteFilePath); 0483 recentFiles.push_front(absoluteFilePath); 0484 recentFiles = recentFiles.mid(0, 30); 0485 _settings.setValue(key, recentFiles); 0486 } 0487 0488 submenu->clear(); 0489 QAction* check = new QAction(this); 0490 check->setText(tr("&Cleanup Non-Existent Files")); 0491 check->setData(key); 0492 check->setVisible(true); 0493 connect(check, SIGNAL(triggered()), this, SLOT(checkRecentFilesOnExistence())); 0494 submenu->addAction(check); 0495 submenu->addSeparator(); 0496 int i = 0; 0497 foreach(const QString& it, recentFiles) { 0498 i++; 0499 if (i <= 5) { 0500 // don't make file menu too wide, show complete path in statusbar 0501 QAction* action = createRecentFileAction(it, i, QFileInfo(it).fileName(), openslot); 0502 actions << action; 0503 menu->addAction(action); 0504 } 0505 submenu->addAction(createRecentFileAction(it, i, it, openslot)); 0506 } 0507 } 0508 0509 0510 void MainWindow::openRecentKstFile() 0511 { 0512 QAction *action = qobject_cast<QAction *>(sender()); 0513 if (action) { 0514 openFile(action->data().toString()); 0515 } 0516 } 0517 0518 0519 void MainWindow::checkRecentFilesOnExistence() 0520 { 0521 QAction *action = qobject_cast<QAction *>(sender()); 0522 if (action) { 0523 QStringList recentFiles = _settings.value(action->data().toString()).toStringList(); 0524 recentFiles.removeDuplicates(); 0525 foreach(const QString& it, recentFiles) { 0526 if (!QFileInfo(it).exists()) { 0527 recentFiles.removeOne(it); 0528 } 0529 } 0530 _settings.setValue(action->data().toString(), recentFiles); 0531 updateRecentKstFiles(); 0532 updateRecentDataFiles(); 0533 } 0534 } 0535 0536 void MainWindow::autoExportImage() { 0537 exportGraphicsFile(_ae_filename, _ae_format, _ae_width, _ae_height, _ae_display, _ae_export_all, _ae_autosave_period); 0538 } 0539 0540 0541 0542 bool MainWindow::initFromCommandLine() { 0543 delete _doc; 0544 _doc = new Document(this); 0545 _scriptServer->setStore(_doc->objectStore()); 0546 0547 CommandLineParser P(_doc, this); 0548 0549 bool ok = _doc->initFromCommandLine(&P); 0550 if (!P.pngFile().isEmpty()) { 0551 int w = 1280; 0552 int h = 1024; 0553 0554 if (P.pngWidth()>1) { 0555 w = P.pngWidth(); 0556 } 0557 if (P.pngHeight()>1) { 0558 h = P.pngHeight(); 0559 } 0560 exportGraphicsFile(P.pngFile(), "png", w, h, 2, true, 0); 0561 ok = false; 0562 } 0563 if (!P.printFile().isEmpty()) { 0564 #ifndef KST_NO_PRINTER 0565 printFromCommandLine(P.printFile()); 0566 #endif 0567 ok = false; 0568 } 0569 if (!P.kstFileName().isEmpty()) { 0570 _sessionFileName = P.kstFileName(); 0571 setKstWindowTitle(); 0572 } 0573 _doc->setChanged(false); 0574 return ok; 0575 } 0576 0577 void MainWindow::openFile(const QString &file) { 0578 QApplication::setOverrideCursor(QCursor(Qt::WaitCursor)); 0579 cleanup(); 0580 newDoc(true); // Does all the init stuff, but does not ask for override as it's supposed to be done elsewhere 0581 bool ok = _doc->open(file); 0582 updateProgress(100, ""); 0583 QApplication::restoreOverrideCursor(); 0584 0585 if (!ok) { 0586 QString lastError = _doc->lastError(); 0587 if (lastError.isEmpty()) 0588 lastError = tr("For details see Help->Debug Dialog->Log."); 0589 QMessageBox::critical(this, tr("Kst"),tr("Error opening document:\n '%1'\n%2\n").arg(file, lastError)); 0590 } 0591 0592 _sessionFileName = file; 0593 setKstWindowTitle(); 0594 updateRecentKstFiles(file); 0595 } 0596 0597 0598 void MainWindow::exportGraphicsFile(const QString &filename, const QString &format, int width, int height, int display, bool export_all, int autosave_period) { 0599 int viewCount = 0; 0600 int n_views = _tabWidget->views().size(); 0601 int i_startview, i_endview; 0602 0603 _ae_filename = filename; 0604 _ae_format = format; 0605 _ae_width = width; 0606 _ae_height = height; 0607 _ae_display = display; 0608 _ae_export_all = export_all; 0609 _ae_autosave_period = autosave_period; 0610 0611 dialogDefaults().setValue("export/filename", filename); 0612 dialogDefaults().setValue("export/format", format); 0613 dialogDefaults().setValue("export/xsize", width); 0614 dialogDefaults().setValue("export/ysize", height); 0615 dialogDefaults().setValue("export/sizeOption", display); 0616 0617 if (export_all) { 0618 i_startview = 0; 0619 i_endview = n_views-1; 0620 } else { 0621 i_startview = i_endview = _tabWidget->currentIndex(); 0622 } 0623 0624 for (int i_view = i_startview; i_view<=i_endview; i_view++) { 0625 View *view = _tabWidget->views().at(i_view); 0626 QSize size; 0627 if (display == 0) { // Width set by user, maintain aspect ratio 0628 QSize sizeWindow(view->geometry().size()); 0629 size.setWidth(width); 0630 size.setHeight((int)((qreal)width * (qreal)sizeWindow.height() / (qreal)sizeWindow.width())); 0631 } else if (display == 1) { // Height set by user, maintain aspect ratio 0632 QSize sizeWindow(view->geometry().size()); 0633 size.setHeight(height); 0634 size.setWidth((int)((qreal)height * (qreal)sizeWindow.width() / (qreal)sizeWindow.height())); 0635 } else if (display == 2) { // Width and height set by user 0636 size.setWidth(width); 0637 size.setHeight(height); 0638 } else { //if (display == 3) { // Square (width x width) 0639 size.setWidth(width); 0640 size.setHeight(width); 0641 } 0642 0643 QString file = filename; 0644 if (i_startview - i_endview != 0) { 0645 QFileInfo QFI(filename); 0646 file = QFI.dir().path() + '/' + QFI.completeBaseName() + 0647 '_' + 0648 _tabWidget->tabBar()->tabText(viewCount).replace(QString("&"),QString()) + '.' + 0649 QFI.suffix(); 0650 } 0651 if (format == QString("svg")) { 0652 #ifndef KST_NO_SVG 0653 QPainter painter; 0654 QSvgGenerator generator; 0655 0656 QSize currentSize(view->size()); 0657 view->resize(size); 0658 view->processResize(size); 0659 view->setPrinting(true); 0660 0661 generator.setFileName(file); 0662 generator.setResolution(300); 0663 generator.setSize(view->size()); 0664 generator.setViewBox(view->rect()); 0665 0666 painter.begin(&generator); 0667 view->render(&painter); 0668 painter.end(); 0669 0670 view->setPrinting(false); 0671 view->resize(currentSize); 0672 view->processResize(currentSize); 0673 #endif 0674 } else if (format == QString("eps")) { 0675 #ifndef KST_NO_PRINTER 0676 QPrinter printer(QPrinter::ScreenResolution); 0677 #ifdef QT5 0678 printer.setOutputFormat(QPrinter::PdfFormat); 0679 #else 0680 printer.setOutputFormat(QPrinter::PostScriptFormat); 0681 #endif 0682 printer.setOutputFileName(file); 0683 printer.setOrientation(QPrinter::Portrait); 0684 0685 printer.setPrintRange(QPrinter::PageRange); 0686 printer.setFromTo(i_view+1, i_view+1); 0687 0688 printer.setPaperSize(size, QPrinter::DevicePixel); 0689 printToPrinter(&printer); 0690 0691 } else if (format == QString("pdf")) { 0692 QPrinter printer(QPrinter::ScreenResolution); 0693 printer.setOutputFormat(QPrinter::PdfFormat); 0694 printer.setOutputFileName(file); 0695 //setPrinterDefaults(&printer); 0696 printer.setOrientation(QPrinter::Portrait); 0697 0698 printer.setPrintRange(QPrinter::PageRange); 0699 printer.setFromTo(i_view+1, i_view+1); 0700 0701 printer.setPaperSize(size, QPrinter::DevicePixel); 0702 printToPrinter(&printer); 0703 #endif 0704 } else { 0705 QPainter painter; 0706 QImage image(size, QImage::Format_ARGB32); 0707 0708 painter.begin(&image); 0709 0710 QSize currentSize(view->size()); 0711 view->resize(size); 0712 view->processResize(size); 0713 view->setPrinting(true); 0714 view->render(&painter); 0715 view->setPrinting(false); 0716 view->resize(currentSize); 0717 view->processResize(currentSize); 0718 0719 painter.end(); 0720 0721 QImageWriter imageWriter(file, format.toLatin1()); 0722 imageWriter.write(image); 0723 } 0724 viewCount++; 0725 } 0726 0727 if (_ae_autosave_period > 0) { 0728 if (_ae_Timer == 0) { // create timer (only once) 0729 _ae_Timer = new QTimer(this); 0730 _ae_Timer->setSingleShot(true); 0731 connect(_ae_Timer, SIGNAL(timeout()), this, SLOT(autoExportImage())); 0732 } 0733 _ae_Timer->start(_ae_autosave_period); // one shot timer... 0734 } 0735 } 0736 0737 void MainWindow::exportLog(const QString &imagename, QString &msgfilename, const QString &format, int x_size, int y_size, 0738 int size_option_index, const QString &message) { 0739 View *view = _tabWidget->currentView(); 0740 0741 QSize size; 0742 if (size_option_index == 0) { 0743 size.setWidth(x_size); 0744 size.setHeight(y_size); 0745 } else if (size_option_index == 1) { 0746 size.setWidth(x_size); 0747 size.setHeight(y_size); 0748 } else if (size_option_index == 2) { 0749 QSize sizeWindow(view->geometry().size()); 0750 0751 size.setWidth(x_size); 0752 size.setHeight((int)((qreal)x_size * (qreal)sizeWindow.height() / (qreal)sizeWindow.width())); 0753 } else { 0754 QSize sizeWindow(view->geometry().size()); 0755 0756 size.setHeight(y_size); 0757 size.setWidth((int)((qreal)y_size * (qreal)sizeWindow.width() / (qreal)sizeWindow.height())); 0758 } 0759 0760 QImage image(size, QImage::Format_ARGB32); 0761 0762 QPainter painter(&image); 0763 QSize currentSize(view->size()); 0764 view->resize(size); 0765 view->processResize(size); 0766 view->setPrinting(true); 0767 view->render(&painter); 0768 view->setPrinting(false); 0769 view->resize(currentSize); 0770 view->processResize(currentSize); 0771 0772 QImageWriter imageWriter(imagename, format.toLatin1()); 0773 imageWriter.write(image); 0774 0775 QFile file(msgfilename); 0776 0777 if (file.open(QIODevice::WriteOnly | QIODevice::Text)) { 0778 QTextStream out(&file); 0779 out << message; 0780 file.close(); 0781 } 0782 0783 } 0784 0785 #ifndef KST_NO_PRINTER 0786 void MainWindow::printToPrinter(QPrinter *printer) { 0787 QPainter painter(printer); 0788 QList<View*> pages; 0789 0790 switch (printer->printRange()) { 0791 case QPrinter::PageRange: 0792 if (printer->fromPage()>0) { 0793 for (int i_page = printer->fromPage(); i_page<=printer->toPage(); i_page++) { 0794 pages.append(_tabWidget->views().at(i_page-1)); 0795 } 0796 } 0797 break; 0798 case QPrinter::AllPages: 0799 foreach (View *view, _tabWidget->views()) { 0800 pages.append(view); 0801 } 0802 break; 0803 case QPrinter::Selection: 0804 default: 0805 pages.append(_tabWidget->currentView()); 0806 break; 0807 } 0808 0809 QSize printerPageSize = printer->pageRect().size(); 0810 for (int i = 0; i < printer->numCopies(); ++i) { 0811 for (int i_page = 0; i_page<pages.count(); i_page++) { 0812 View *view = pages.at(i_page); 0813 QSize currentSize(view->size()); 0814 view->resize(printerPageSize); 0815 view->processResize(printerPageSize); 0816 view->setPrinting(true); 0817 view->render(&painter); 0818 view->setPrinting(false); 0819 view->resize(currentSize); 0820 view->processResize(currentSize); 0821 if (i_page<pages.count()-1) 0822 printer->newPage(); 0823 0824 } 0825 } 0826 } 0827 0828 void MainWindow::printFromCommandLine(const QString &printFileName) { 0829 QPrinter printer(QPrinter::ScreenResolution); 0830 printer.setResolution(300); 0831 printer.setOutputFileName(printFileName); 0832 setPrinterDefaults(&printer); 0833 0834 printer.setPrintRange(QPrinter::AllPages); 0835 printToPrinter(&printer); 0836 } 0837 0838 void MainWindow::setPrinterDefaults(QPrinter *printer) { 0839 if (dialogDefaults().value("print/landscape",true).toBool()) { 0840 printer->setOrientation(QPrinter::Landscape); 0841 } else { 0842 printer->setOrientation(QPrinter::Portrait); 0843 } 0844 0845 printer->setPaperSize(QPrinter::PaperSize(dialogDefaults().value("print/paperSize", QPrinter::Letter).toInt())); 0846 0847 QPointF topLeft =dialogDefaults().value("print/topLeftMargin", QPointF(15.0,15.0)).toPointF(); 0848 QPointF bottomRight =dialogDefaults().value("print/bottomRightMargin", QPointF(15.0,15.0)).toPointF(); 0849 0850 printer->setPageMargins(topLeft.x(), topLeft.y(), bottomRight.x(), bottomRight.y(), QPrinter::Millimeter); 0851 // Apparent Qt bug: setting the page margins here doesn't set the correspoding values in the print 0852 // dialog->printer-options sub-dialog under linux. If you don't open the printer-options sub-dialog, 0853 // the values here are honored. 0854 } 0855 0856 void MainWindow::savePrinterDefaults(QPrinter *printer) { 0857 dialogDefaults().setValue("print/landscape", printer->orientation() == QPrinter::Landscape); 0858 dialogDefaults().setValue("print/paperSize", int(printer->paperSize())); 0859 0860 qreal left, top, right, bottom; 0861 printer->getPageMargins(&left, &top, &right, &bottom, QPrinter::Millimeter); 0862 dialogDefaults().setValue("print/topLeftMargin", QPointF(left, top)); 0863 dialogDefaults().setValue("print/bottomRightMargin", QPointF(right, bottom)); 0864 0865 } 0866 0867 void MainWindow::print() { 0868 QPrinter printer(QPrinter::ScreenResolution); 0869 printer.setResolution(300); 0870 0871 setPrinterDefaults(&printer); 0872 0873 #ifndef Q_OS_WIN 0874 // QPrintDialog: Cannot be used on non-native printers 0875 printer.setOutputFileName(dialogDefaults().value("print/path", "./print.pdf").toString()); 0876 #endif 0877 QPointer<QPrintDialog> pd = new QPrintDialog(&printer, this); 0878 #if QT_VERSION >= 0x040500 0879 pd->setOption(QPrintDialog::PrintToFile); 0880 pd->setOption(QPrintDialog::PrintPageRange, true); 0881 pd->setOption(QAbstractPrintDialog::PrintShowPageSize,true); 0882 #endif 0883 0884 if (pd->exec() == QDialog::Accepted) { 0885 QApplication::setOverrideCursor(QCursor(Qt::WaitCursor)); 0886 printToPrinter(&printer); 0887 QApplication::restoreOverrideCursor(); 0888 savePrinterDefaults(&printer); 0889 } 0890 dialogDefaults().setValue("print/path", printer.outputFileName()); 0891 delete pd; 0892 } 0893 #endif 0894 0895 void MainWindow::currentViewChanged() { 0896 if(!_tabWidget->currentView()) 0897 return; 0898 _undoGroup->setActiveStack(_tabWidget->currentView()->undoStack()); 0899 currentViewModeChanged(); 0900 } 0901 0902 0903 void MainWindow::currentViewModeChanged() { 0904 if(!_tabWidget->currentView()) 0905 return; 0906 _layoutModeAct->setChecked(_tabWidget->currentView()->viewMode() == View::Layout); 0907 } 0908 0909 void MainWindow::aboutToQuit() { 0910 writeSettings(); 0911 } 0912 0913 0914 void MainWindow::about() { 0915 if (!_aboutDialog) { 0916 _aboutDialog = new AboutDialog(this); 0917 } 0918 if (_aboutDialog->isVisible()) { 0919 _aboutDialog->raise(); 0920 _aboutDialog->activateWindow(); 0921 } 0922 _aboutDialog->show(); 0923 } 0924 0925 0926 void MainWindow::showShortcutDialog() { 0927 if (!_shortcutDialog) { 0928 _shortcutDialog = new ShortcutDialog(this); 0929 } else if (_shortcutDialog->isVisible()) { 0930 _shortcutDialog->raise(); 0931 _shortcutDialog->activateWindow(); 0932 } 0933 _shortcutDialog->show(); 0934 0935 _shortcutDialog->resetWidth(); 0936 0937 } 0938 0939 0940 void MainWindow::clearDrawingMarker() { 0941 _createBoxAct->setChecked(false); 0942 _createSharedAxisBoxAct->setChecked(false); 0943 _createCircleAct->setChecked(false); 0944 _createEllipseAct->setChecked(false); 0945 _createLabelAct->setChecked(false); 0946 _createLineAct->setChecked(false); 0947 _createArrowAct->setChecked(false); 0948 _createPictureAct->setChecked(false); 0949 _createPlotAct->setChecked(false); 0950 #ifndef KST_NO_SVG 0951 _createSvgAct->setChecked(false); 0952 #endif 0953 _tabWidget->currentView()->setMouseMode(View::Default); 0954 } 0955 0956 0957 void MainWindow::createBox() { 0958 if (_createBoxAct->isChecked()) { 0959 clearDrawingMarker(); 0960 _createBoxAct->setChecked(true); 0961 CreateBoxCommand *cmd = new CreateBoxCommand; 0962 cmd->createItem(); 0963 } else { 0964 _tabWidget->currentView()->setMouseMode(View::Default); 0965 } 0966 } 0967 0968 0969 0970 void MainWindow::createSharedAxisBox() { 0971 if (_createSharedAxisBoxAct->isChecked()) { 0972 clearDrawingMarker(); 0973 _createSharedAxisBoxAct->setChecked(true); 0974 CreateSharedAxisBoxCommand *cmd = new CreateSharedAxisBoxCommand; 0975 cmd->createItem(); 0976 } else { 0977 _tabWidget->currentView()->setMouseMode(View::Default); 0978 } 0979 } 0980 0981 void MainWindow::createVector() { 0982 QString tmp; 0983 DialogLauncher::self()->showVectorDialog(tmp); 0984 } 0985 0986 0987 void MainWindow::createMatrix() { 0988 QString tmp; 0989 DialogLauncher::self()->showMatrixDialog(tmp); 0990 } 0991 0992 0993 void MainWindow::createScalar() { 0994 QString scalarName; 0995 DialogLauncher::self()->showScalarDialog(scalarName); 0996 } 0997 0998 0999 void MainWindow::createString() { 1000 QString stringName; 1001 DialogLauncher::self()->showStringDialog(stringName); 1002 } 1003 1004 1005 void MainWindow::createCircle() { 1006 if (_createCircleAct->isChecked()) { 1007 clearDrawingMarker(); 1008 _createCircleAct->setChecked(true); 1009 CreateCircleCommand *cmd = new CreateCircleCommand; 1010 cmd->createItem(); 1011 } else { 1012 _tabWidget->currentView()->setMouseMode(View::Default); 1013 } 1014 } 1015 1016 1017 void MainWindow::createEllipse() { 1018 if (_createEllipseAct->isChecked()) { 1019 clearDrawingMarker(); 1020 _createEllipseAct->setChecked(true); 1021 CreateEllipseCommand *cmd = new CreateEllipseCommand; 1022 cmd->createItem(); 1023 } else { 1024 _tabWidget->currentView()->setMouseMode(View::Default); 1025 } 1026 } 1027 1028 1029 void MainWindow::createLabel() { 1030 if (_createLabelAct->isChecked()) { 1031 clearDrawingMarker(); 1032 _createLabelAct->setChecked(true); 1033 CreateLabelCommand *cmd = new CreateLabelCommand; 1034 cmd->createItem(); 1035 } else { 1036 _tabWidget->currentView()->setMouseMode(View::Default); 1037 } 1038 } 1039 1040 1041 void MainWindow::createLine() { 1042 if (_createLineAct->isChecked()) { 1043 clearDrawingMarker(); 1044 _createLineAct->setChecked(true); 1045 CreateLineCommand *cmd = new CreateLineCommand; 1046 cmd->createItem(); 1047 } else { 1048 _tabWidget->currentView()->setMouseMode(View::Default); 1049 } 1050 } 1051 1052 1053 void MainWindow::createArrow() { 1054 if (_createArrowAct->isChecked()) { 1055 clearDrawingMarker(); 1056 _createArrowAct->setChecked(true); 1057 CreateArrowCommand *cmd = new CreateArrowCommand; 1058 cmd->createItem(); 1059 } else { 1060 _tabWidget->currentView()->setMouseMode(View::Default); 1061 } 1062 } 1063 1064 1065 void MainWindow::createPicture() { 1066 if (_createPictureAct->isChecked()) { 1067 clearDrawingMarker(); 1068 _createPictureAct->setChecked(true); 1069 CreatePictureCommand *cmd = new CreatePictureCommand; 1070 cmd->createItem(); 1071 } else { 1072 _tabWidget->currentView()->setMouseMode(View::Default); 1073 } 1074 } 1075 1076 1077 void MainWindow::createPlot() { 1078 if (_createPlotAct->isChecked()) { 1079 clearDrawingMarker(); 1080 _createPlotAct->setChecked(true); 1081 CreatePlotCommand *cmd = new CreatePlotCommand; 1082 cmd->createItem(); 1083 } else { 1084 _tabWidget->currentView()->setMouseMode(View::Default); 1085 } 1086 } 1087 1088 void MainWindow::insertPlot() { 1089 CreatePlotForCurve *cmd = new CreatePlotForCurve(); 1090 cmd->createItem(); 1091 1092 PlotItem *plotItem = static_cast<PlotItem*>(cmd->item()); 1093 plotItem->view()->resetPlotFontSizes(plotItem); 1094 plotItem->view()->configurePlotFontDefaults(plotItem); // copy plots already in window 1095 plotItem->view()->appendToLayout(CurvePlacement::Auto, plotItem, 0); 1096 1097 } 1098 1099 #ifndef KST_NO_SVG 1100 void MainWindow::createSvg() { 1101 if (_createSvgAct->isChecked()) { 1102 clearDrawingMarker(); 1103 _createSvgAct->setChecked(true); 1104 CreateSvgCommand *cmd = new CreateSvgCommand; 1105 cmd->createItem(); 1106 } else { 1107 _tabWidget->currentView()->setMouseMode(View::Default); 1108 } 1109 } 1110 #endif 1111 1112 void MainWindow::createCurve() { 1113 DialogLauncher::self()->showCurveDialog(); 1114 } 1115 1116 void MainWindow::createPSD() { 1117 DialogLauncher::self()->showPowerSpectrumDialog(); 1118 } 1119 1120 void MainWindow::createEquation() { 1121 DialogLauncher::self()->showEquationDialog(); 1122 } 1123 1124 void MainWindow::createHistogram() { 1125 DialogLauncher::self()->showHistogramDialog(); 1126 } 1127 1128 void MainWindow::createImage() { 1129 DialogLauncher::self()->showImageDialog(); 1130 } 1131 1132 void MainWindow::createSpectogram() { 1133 DialogLauncher::self()->showCSDDialog(); 1134 } 1135 1136 void MainWindow::createEventMonitor() { 1137 DialogLauncher::self()->showEventMonitorDialog(); 1138 } 1139 1140 void MainWindow::createActions() { 1141 // ***************************** File actions ******************************** // 1142 _openAct = new QAction(tr("&Open..."), this); 1143 _openAct->setStatusTip(tr("Open a new session")); 1144 _openAct->setShortcuts(QKeySequence::Open); 1145 _openAct->setIcon(KstGetIcon("document-open")); 1146 connect(_openAct, SIGNAL(triggered()), this, SLOT(open())); 1147 1148 _saveAct = new QAction(tr("&Save"), this); 1149 _saveAct->setStatusTip(tr("Save the current session")); 1150 _saveAct->setShortcuts(QKeySequence::Save); 1151 _saveAct->setIcon(KstGetIcon("document-save")); 1152 connect(_saveAct, SIGNAL(triggered()), this, SLOT(save())); 1153 1154 _saveAsAct = new QAction(tr("Save &as..."), this); 1155 _saveAsAct->setStatusTip(tr("Save the current session")); 1156 _saveAsAct->setIcon(KstGetIcon("document-save-as")); 1157 _saveAsAct->setShortcuts(QKeySequence::SaveAs); 1158 connect(_saveAsAct, SIGNAL(triggered()), this, SLOT(saveAs())); 1159 1160 _closeAct = new QAction(tr("Ne&w Session"), this); 1161 _closeAct->setStatusTip(tr("Close current session and start a new, empty one")); 1162 _closeAct->setIcon(KstGetIcon("document-close")); 1163 _closeAct->setShortcuts(QKeySequence::Close); 1164 connect(_closeAct, SIGNAL(triggered()), this, SLOT(newDoc())); 1165 1166 _reloadAct = new QAction(tr("Reload All &Data Sources"), this); 1167 _reloadAct->setStatusTip(tr("Reload all data sources")); 1168 _reloadAct->setIcon(KstGetIcon("kst_reload")); 1169 connect(_reloadAct, SIGNAL(triggered()), this, SLOT(reload())); 1170 1171 _printAct = new QAction(tr("&Print..."), this); 1172 _printAct->setStatusTip(tr("Print the current view")); 1173 _printAct->setIcon(KstGetIcon("document-print")); 1174 _printAct->setShortcuts(QKeySequence::Print); 1175 connect(_printAct, SIGNAL(triggered()), this, SLOT(print())); 1176 #ifdef KST_NO_PRINTER 1177 _printAct->setEnabled(false); 1178 #endif 1179 1180 _exportGraphicsAct = new QAction(tr("&Export as Image(s)..."), this); 1181 _exportGraphicsAct->setStatusTip(tr("Export graphics to disk")); 1182 _exportGraphicsAct->setIcon(KstGetIcon("insert-image")); 1183 connect(_exportGraphicsAct, SIGNAL(triggered()), this, SLOT(showExportGraphicsDialog())); 1184 1185 _exportVectorsAct = new QAction(tr("Save &Vectors to Disk..."), this); 1186 _exportVectorsAct->setStatusTip(tr("Export vectors to ascii file")); 1187 _exportVectorsAct->setIcon(KstGetIcon("save-vectors")); 1188 connect(_exportVectorsAct, SIGNAL(triggered()), this, SLOT(showExportVectorsDialog())); 1189 1190 _logAct = new QAction(tr("&Log Entry..."), this); 1191 _logAct->setStatusTip(tr("Commit a log entry")); 1192 _logAct->setIcon(KstGetIcon("new-log-event")); 1193 connect(_logAct, SIGNAL(triggered()), this, SLOT(showLogDialog())); 1194 1195 _newTabAct = new QAction(tr("&New Tab"), this); 1196 _newTabAct->setStatusTip(tr("Create a new tab")); 1197 _newTabAct->setIcon(KstGetIcon("tab-new")); 1198 1199 connect(_newTabAct, SIGNAL(triggered()), tabWidget(), SLOT(createView())); 1200 1201 _closeTabAct = new QAction(tr("&Close Tab"), this); 1202 _closeTabAct->setStatusTip(tr("Close the current tab")); 1203 _closeTabAct->setIcon(KstGetIcon("tab-close")); 1204 connect(_closeTabAct, SIGNAL(triggered()), tabWidget(), SLOT(closeCurrentView())); 1205 1206 _exitAct = new QAction(tr("E&xit"), this); 1207 _exitAct->setShortcuts(QKeySequence::Quit); 1208 _exitAct->setStatusTip(tr("Exit the application")); 1209 _exitAct->setIcon(KstGetIcon("application-exit")); 1210 connect(_exitAct, SIGNAL(triggered()), this, SLOT(close())); 1211 1212 // ************************** Edit Actions ******************************* // 1213 _undoAct = _undoGroup->createUndoAction(this); 1214 _undoAct->setShortcuts(QKeySequence::Undo); 1215 _undoAct->setIcon(KstGetIcon("edit-undo")); 1216 1217 _redoAct = _undoGroup->createRedoAction(this); 1218 _redoAct->setShortcuts(QKeySequence::Redo); 1219 _redoAct->setIcon(KstGetIcon("edit-redo")); 1220 1221 _copyTabAct = new QAction(tr("Copy Tab Image"), this); 1222 _copyTabAct->setStatusTip("Copy image of the current tab to the desktop clipboard"); 1223 _copyTabAct->setIcon(KstGetIcon("edit-copy")); 1224 connect(_copyTabAct, SIGNAL(triggered()), this, SLOT(copyTab())); 1225 1226 // ********************* View Actions ********************************** // 1227 _vectorEditorAct = new QAction(tr("&Vectors"), this); 1228 _vectorEditorAct->setStatusTip(tr("Show all vectors in a spreadsheet")); 1229 connect(_vectorEditorAct, SIGNAL(triggered()), this, SLOT(showVectorEditor())); 1230 1231 _scalarEditorAct = new QAction(tr("&Scalars"), this); 1232 _scalarEditorAct->setStatusTip(tr("Show all scalars in a spreadsheet")); 1233 connect(_scalarEditorAct, SIGNAL(triggered()), this, SLOT(showScalarEditor())); 1234 1235 _matrixEditorAct = new QAction(tr("&Matrices"), this); 1236 _matrixEditorAct->setStatusTip(tr("Show all matrices in a spreadsheet")); 1237 connect(_matrixEditorAct, SIGNAL(triggered()), this, SLOT(showMatrixEditor())); 1238 1239 _stringEditorAct = new QAction(tr("S&trings"), this); 1240 _stringEditorAct->setStatusTip(tr("Show all strings in a spreadsheet")); 1241 connect(_stringEditorAct, SIGNAL(triggered()), this, SLOT(showStringEditor())); 1242 1243 // ************************ Data Range 1 click Actions ************************** // 1244 _backAct = new QAction(tr("&Back One Screen"), this); 1245 _backAct->setStatusTip(tr("Back one screen (Page Up)")); 1246 _backAct->setToolTip(tr("Back one screen (Page Up)")); 1247 _backAct->setIcon(KstGetIcon("page-previous")); 1248 _backAct->setShortcut(Qt::Key_PageUp); 1249 connect(_backAct, SIGNAL(triggered()), this, SLOT(back())); 1250 1251 _forwardAct = new QAction(tr("&Forward One Screen"), this); 1252 _forwardAct->setStatusTip(tr("Forward one screen (Page Down)")); 1253 _forwardAct->setToolTip(tr("Forward one screen (Page Down)")); 1254 _forwardAct->setIcon(KstGetIcon("page-next")); 1255 _forwardAct->setShortcut(Qt::Key_PageDown); 1256 connect(_forwardAct, SIGNAL(triggered()), this, SLOT(forward())); 1257 1258 _backSmallAct = new QAction(tr("&Back 1/5th Screen"), this); 1259 _backSmallAct->setStatusTip(tr("Back 1/5th screen (Shift + Page Up)")); 1260 _backSmallAct->setToolTip(tr("Back 1/5th screen (Shift + Page Up)")); 1261 _backSmallAct->setIcon(KstGetIcon("page-previous")); 1262 _backSmallAct->setShortcut(Qt::SHIFT + Qt::Key_PageDown); 1263 connect(_backSmallAct, SIGNAL(triggered()), this, SLOT(backSmall())); 1264 1265 _forwardSmallAct = new QAction(tr("&Forward 1/5th Screen"), this); 1266 _forwardSmallAct->setStatusTip(tr("Forward 1/5th screen (Page Down)")); 1267 _forwardSmallAct->setToolTip(tr("Forward 1/5th screen (Page Down)")); 1268 _forwardSmallAct->setIcon(KstGetIcon("page-next")); 1269 _forwardSmallAct->setShortcut(Qt::SHIFT + Qt::Key_PageUp); 1270 connect(_forwardSmallAct, SIGNAL(triggered()), this, SLOT(forwardSmall())); 1271 1272 _readFromEndAct = new QAction(tr("&Count from End"), this); 1273 _readFromEndAct->setStatusTip(tr("Count from end mode (End)")); 1274 _readFromEndAct->setToolTip(tr("Count from end mode (End)")); 1275 _readFromEndAct->setIcon(KstGetIcon("count-from-end")); 1276 _readFromEndAct->setShortcut(Qt::Key_End); 1277 connect(_readFromEndAct, SIGNAL(triggered()), this, SLOT(readFromEnd())); 1278 1279 _readToEndAct = new QAction(tr("&Read to End"), this); 1280 _readToEndAct->setStatusTip(tr("Read to end mode")); 1281 _readToEndAct->setToolTip(tr("Read to end mode (shift+end)")); 1282 _readToEndAct->setIcon(KstGetIcon("read-to-end")); 1283 _readToEndAct->setShortcut(Qt::ShiftModifier+Qt::Key_End); 1284 connect(_readToEndAct, SIGNAL(triggered()), this, SLOT(readToEnd())); 1285 1286 _pauseAct = new QAction(tr("&Pause"), this); 1287 _pauseAct->setIcon(KstGetIcon("pause")); 1288 _pauseAct->setCheckable(true); 1289 _pauseAct->setShortcut(tr("p", "shortcut for pause")); 1290 _pauseAct->setStatusTip(tr("Toggle pause updates of data sources (%1)").arg(_pauseAct->shortcut().toString())); 1291 _pauseAct->setToolTip(tr("Toggle \"Pause Data Sources\" (%1)").arg(_pauseAct->shortcut().toString())); 1292 connect(_pauseAct, SIGNAL(toggled(bool)), this, SLOT(pause(bool))); 1293 1294 _changeDataSampleDialogAct = new QAction(tr("Change Data &Sample Range..."), this); 1295 _changeDataSampleDialogAct->setShortcut(tr("J", "shortcut change data sample dialog")); 1296 _changeDataSampleDialogAct->setStatusTip(tr("Show Kst's Change Data Sample Range Dialog (%1)").arg(_changeDataSampleDialogAct->shortcut().toString())); 1297 _changeDataSampleDialogAct->setToolTip(tr("Change Data Sample Range (%1)").arg(_changeDataSampleDialogAct->shortcut().toString())); 1298 _changeDataSampleDialogAct->setIcon(KstGetIcon("kst_changenpts")); 1299 connect(_changeDataSampleDialogAct, SIGNAL(triggered()), this, SLOT(showChangeDataSampleDialog())); 1300 1301 // ************************ Create Actions ************************** // 1302 _insertPlotAct = new QAction(tr("&Plot"), this); 1303 _insertPlotAct->setIcon(KstGetIcon("kst_newplot")); 1304 _insertPlotAct->setShortcut(QString("F11")); 1305 _insertPlotAct->setStatusTip(tr("Insert a plot in the current view (%1)").arg(_insertPlotAct->shortcut().toString())); 1306 _insertPlotAct->setToolTip(tr("New plot (%1)").arg(_insertPlotAct->shortcut().toString())); 1307 _insertPlotAct->setCheckable(false); 1308 connect(_insertPlotAct, SIGNAL(triggered()), this, SLOT(insertPlot())); 1309 1310 _createPlotAct = new QAction(tr("&Plot"), this); 1311 _createPlotAct->setIcon(KstGetIcon("kst_newplot")); 1312 //_createPlotAct->setShortcut(QString("F11")); 1313 _createPlotAct->setStatusTip(tr("Create a plot for the current view")); 1314 _createPlotAct->setCheckable(true); 1315 connect(_createPlotAct, SIGNAL(triggered()), this, SLOT(createPlot())); 1316 1317 _newScalarAct = new QAction(tr("&Scalar"), this); 1318 connect(_newScalarAct, SIGNAL(triggered()), this, SLOT(createScalar())); 1319 1320 _newVectorAct = new QAction(tr("&Vector"), this); 1321 connect(_newVectorAct, SIGNAL(triggered()), this, SLOT(createVector())); 1322 1323 _newMatrixAct = new QAction(tr("&Matrix"), this); 1324 connect(_newMatrixAct, SIGNAL(triggered()), this, SLOT(createMatrix())); 1325 1326 _newStringAct = new QAction(tr("Strin&g"), this); 1327 connect(_newStringAct, SIGNAL(triggered()), this, SLOT(createString())); 1328 1329 _newCurveAct = new QAction(tr("&Curve"), this); 1330 connect(_newCurveAct, SIGNAL(triggered()), this, SLOT(createCurve())); 1331 1332 _newEquationAct = new QAction(tr("&Equation"), this); 1333 connect(_newEquationAct, SIGNAL(triggered()), this, SLOT(createEquation())); 1334 1335 _newPSDAct = new QAction(tr("Po&wer Spectrum"), this); 1336 connect(_newPSDAct, SIGNAL(triggered()), this, SLOT(createPSD())); 1337 1338 _newHistogramAct = new QAction(tr("&Histogram"), this); 1339 connect(_newHistogramAct, SIGNAL(triggered()), this, SLOT(createHistogram())); 1340 1341 _newImageAct = new QAction(tr("&Image"), this); 1342 connect(_newImageAct, SIGNAL(triggered()), this, SLOT(createImage())); 1343 1344 _newSpectrogramAct = new QAction(tr("Spectr&ogram"), this); 1345 connect(_newSpectrogramAct, SIGNAL(triggered()), this, SLOT(createSpectogram())); 1346 1347 _newEventMonitorAct = new QAction(tr("Eve&nt Monitor"), this); 1348 connect(_newEventMonitorAct, SIGNAL(triggered()), this, SLOT(createEventMonitor())); 1349 1350 // Advanced layout 1351 _createLabelAct = new QAction(tr("&Label"), this); 1352 _createLabelAct->setIcon(KstGetIcon("kst_gfx_label")); 1353 _createLabelAct->setShortcut(QString("F3")); 1354 _createLabelAct->setStatusTip(tr("Create a label for the current view (%1)").arg(_createLabelAct->shortcut().toString())); 1355 _createLabelAct->setToolTip(tr("Create label (%1)").arg(_createLabelAct->shortcut().toString())); 1356 _createLabelAct->setCheckable(true); 1357 connect(_createLabelAct, SIGNAL(triggered()), this, SLOT(createLabel())); 1358 1359 _createBoxAct = new QAction(tr("&Box"), this); 1360 _createBoxAct->setIcon(KstGetIcon("kst_gfx_rectangle")); 1361 _createBoxAct->setShortcut(QString("F4")); 1362 _createBoxAct->setStatusTip(tr("Create a box for the current view (%1)").arg(_createBoxAct->shortcut().toString())); 1363 _createBoxAct->setToolTip(tr("Create box (%1)").arg(_createBoxAct->shortcut().toString())); 1364 _createBoxAct->setCheckable(true); 1365 connect(_createBoxAct, SIGNAL(triggered()), this, SLOT(createBox())); 1366 1367 _createCircleAct = new QAction(tr("&Circle"), this); 1368 _createCircleAct->setIcon(KstGetIcon("kst_gfx_circle")); 1369 _createCircleAct->setShortcut(QString("F5")); 1370 _createCircleAct->setStatusTip(tr("Create a circle for the current view (%1)").arg(_createCircleAct->shortcut().toString())); 1371 _createCircleAct->setToolTip(tr("Create circle (%1)").arg(_createCircleAct->shortcut().toString())); 1372 _createCircleAct->setCheckable(true); 1373 connect(_createCircleAct, SIGNAL(triggered()), this, SLOT(createCircle())); 1374 1375 _createEllipseAct = new QAction(tr("&Ellipse"), this); 1376 _createEllipseAct->setIcon(KstGetIcon("kst_gfx_ellipse")); 1377 _createEllipseAct->setShortcut(QString("F6")); 1378 _createEllipseAct->setStatusTip(tr("Create an ellipse for the current view (%1)").arg(_createEllipseAct->shortcut().toString())); 1379 _createEllipseAct->setToolTip(tr("Create ellipse (%1)").arg(_createEllipseAct->shortcut().toString())); 1380 _createEllipseAct->setCheckable(true); 1381 connect(_createEllipseAct, SIGNAL(triggered()), this, SLOT(createEllipse())); 1382 1383 _createLineAct = new QAction(tr("&Line"), this); 1384 _createLineAct->setIcon(KstGetIcon("kst_gfx_line")); 1385 _createLineAct->setShortcut(QString("F7")); 1386 _createLineAct->setStatusTip(tr("Create a line for the current view (%1)").arg(_createLineAct->shortcut().toString())); 1387 _createLineAct->setToolTip(tr("Create line (%1)").arg(_createLineAct->shortcut().toString())); 1388 _createLineAct->setCheckable(true); 1389 connect(_createLineAct, SIGNAL(triggered()), this, SLOT(createLine())); 1390 1391 _createArrowAct = new QAction(tr("&Arrow"), this); 1392 _createArrowAct->setIcon(KstGetIcon("kst_gfx_arrow")); 1393 _createArrowAct->setShortcut(QString("F8")); 1394 _createArrowAct->setStatusTip(tr("Create a arrow for the current view (%1)").arg(_createArrowAct->shortcut().toString())); 1395 _createArrowAct->setToolTip(tr("Create arrow (%1)").arg(_createArrowAct->shortcut().toString())); 1396 _createArrowAct->setCheckable(true); 1397 connect(_createArrowAct, SIGNAL(triggered()), this, SLOT(createArrow())); 1398 1399 _createPictureAct = new QAction(tr("&Picture"), this); 1400 _createPictureAct->setIcon(KstGetIcon("insert-image")); 1401 _createPictureAct->setShortcut(QString("F9")); 1402 _createPictureAct->setStatusTip(tr("Create a picture for the current view (%1)").arg(_createPictureAct->shortcut().toString())); 1403 _createPictureAct->setToolTip(tr("Create picture (%1)").arg(_createPictureAct->shortcut().toString())); 1404 _createPictureAct->setCheckable(true); 1405 connect(_createPictureAct, SIGNAL(triggered()), this, SLOT(createPicture())); 1406 1407 #ifndef KST_NO_SVG 1408 _createSvgAct = new QAction(tr("&Svg"), this); 1409 _createSvgAct->setIcon(KstGetIcon("draw-bezier-curves")); 1410 _createSvgAct->setShortcut(QString("F10")); 1411 _createSvgAct->setStatusTip(tr("Create a svg for the current view (%1)").arg(_createSvgAct->shortcut().toString())); 1412 _createSvgAct->setToolTip(tr("Create embedded svg image (%1)").arg(_createSvgAct->shortcut().toString())); 1413 _createSvgAct->setCheckable(true); 1414 connect(_createSvgAct, SIGNAL(triggered()), this, SLOT(createSvg())); 1415 #endif 1416 1417 _createSharedAxisBoxAct = new QAction(tr("Shared Axis &Box"), this); 1418 _createSharedAxisBoxAct->setStatusTip(tr("Create a shared axis box for the current item")); 1419 _createSharedAxisBoxAct->setIcon(KstGetIcon("kst_gfx_sharedaxisbox")); 1420 _createSharedAxisBoxAct->setCheckable(true); 1421 connect(_createSharedAxisBoxAct, SIGNAL(triggered()), this, SLOT(createSharedAxisBox())); 1422 1423 // ************************** Mode Actions ******************************* // 1424 // First, general options 1425 _tiedZoomAct = new QAction(tr("&Toggle Tied Zoom"), this); 1426 _tiedZoomAct->setIcon(KstGetIcon("tied-zoom")); 1427 _tiedZoomAct->setCheckable(false); 1428 _tiedZoomAct->setShortcut(Qt::Key_O); 1429 _tiedZoomAct->setStatusTip(tr("Toggle the current view's tied zoom (%1)").arg(_tiedZoomAct->shortcut().toString())); 1430 _tiedZoomAct->setToolTip(tr("Toggle tied zoom (%1)").arg(_tiedZoomAct->shortcut().toString())); 1431 connect(_tiedZoomAct, SIGNAL(triggered()), this, SLOT(toggleTiedZoom())); 1432 1433 _tabTiedAct = new QAction(tr("Tie &Across All Tabs"), this); 1434 _tabTiedAct->setStatusTip(tr("Tied zoom applies between tabs")); 1435 //_tiedZoomAct->setIcon(KstGetIcon("tied-zoom")); 1436 _tabTiedAct->setCheckable(true); 1437 //connect(_tiedZoomAct, SIGNAL(triggered()), this, SLOT(toggleTiedZoom())); 1438 1439 1440 _highlightPointAct = new QAction(tr("&Highlight Data Points"), this); 1441 _highlightPointAct->setShortcut(QString("h")); 1442 _highlightPointAct->setStatusTip(tr("Highlight closest data point (%1)").arg(_highlightPointAct->shortcut().toString())); 1443 _highlightPointAct->setToolTip(tr("Highlight closest data point (%1)").arg(_highlightPointAct->shortcut().toString())); 1444 _highlightPointAct->setIcon(KstGetIcon("kst_datamode")); 1445 _highlightPointAct->setCheckable(true); 1446 connect(_highlightPointAct, SIGNAL(toggled(bool)), this, SLOT(setHighlightPoint(bool))); 1447 1448 1449 // Then, exclusive interaction modes 1450 QActionGroup* _interactionModeGroup = new QActionGroup(this); 1451 1452 _standardZoomAct = _interactionModeGroup->addAction(tr("X-Y Zoom/Scroll")); 1453 _standardZoomAct->setStatusTip(tr("Zoom arbitrarily in X- or Y-direction")); 1454 _standardZoomAct->setShortcut(Qt::Key_K); 1455 _standardZoomAct->setToolTip(tr("X-Y Zoom mode (%1)").arg(_standardZoomAct->shortcut().toString())); 1456 _standardZoomAct->setCheckable(true); 1457 _standardZoomAct->setData(View::ZoomOnlyDisabled); 1458 _standardZoomAct->setIcon(KstGetIcon("xy-zoom")); 1459 1460 _xOnlyZoomAct = _interactionModeGroup->addAction(tr("&X-only Zoom")); 1461 _xOnlyZoomAct->setStatusTip(tr("Zoom only in X direction")); 1462 _xOnlyZoomAct->setShortcut(Qt::CTRL + Qt::Key_K); 1463 _xOnlyZoomAct->setToolTip(tr("X Zoom mode (%1)").arg(_xOnlyZoomAct->shortcut().toString())); 1464 _xOnlyZoomAct->setCheckable(true); 1465 _xOnlyZoomAct->setData(View::ZoomOnlyX); 1466 _xOnlyZoomAct->setIcon(KstGetIcon("x-zoom")); 1467 1468 _yOnlyZoomAct = _interactionModeGroup->addAction(tr("&Y-only Zoom")); 1469 _yOnlyZoomAct->setStatusTip(tr("Zoom only in Y direction")); 1470 _yOnlyZoomAct->setShortcut(Qt::SHIFT + Qt::Key_K); 1471 _yOnlyZoomAct->setToolTip(tr("Y Zoom mode (%1)").arg(_yOnlyZoomAct->shortcut().toString())); 1472 _yOnlyZoomAct->setData(View::ZoomOnlyY); 1473 _yOnlyZoomAct->setCheckable(true); 1474 _yOnlyZoomAct->setIcon(KstGetIcon("y-zoom")); 1475 1476 _layoutModeAct = _interactionModeGroup->addAction(tr("&Layout Mode")); 1477 _layoutModeAct->setIcon(KstGetIcon("transform-move")); 1478 _layoutModeAct->setCheckable(true); 1479 _layoutModeAct->setShortcut(QString("F2")); 1480 _layoutModeAct->setStatusTip(tr("Toggle the current view's layout mode (%1)").arg(_layoutModeAct->shortcut().toString())); 1481 _layoutModeAct->setToolTip(tr("Layout mode (%1)").arg(_layoutModeAct->shortcut().toString())); 1482 connect(_layoutModeAct, SIGNAL(toggled(bool)), this, SLOT(setLayoutMode(bool))); 1483 1484 _interactionModeGroup->setExclusive(true); 1485 connect(_interactionModeGroup, SIGNAL(triggered(QAction*)), this, SLOT(changeZoomOnlyMode(QAction*))); 1486 1487 // *********************** Tools actions ************************************** // 1488 _dataManagerAct = new QAction(tr("Data Manager"), this); 1489 _dataManagerAct->setIcon(KstGetIcon("data-manager")); 1490 _dataManagerAct->setShortcut(QString("d")); 1491 _dataManagerAct->setStatusTip(tr("Show Kst's data manager window (%1)").arg(_dataManagerAct->shortcut().toString())); 1492 _dataManagerAct->setToolTip(tr("Show Data Manager (%1)").arg(_dataManagerAct->shortcut().toString())); 1493 connect(_dataManagerAct, SIGNAL(triggered()), this, SLOT(showDataManager())); 1494 1495 _dataWizardAct = new QAction(tr("&Data Wizard"), this); 1496 _dataWizardAct->setIcon(KstGetIcon("tools-wizard")); 1497 _dataWizardAct->setShortcut(QString("w")); 1498 _dataWizardAct->setStatusTip(tr("Show Kst's Data Wizard (%1)").arg(_dataWizardAct->shortcut().toString())); 1499 _dataWizardAct->setToolTip(tr("Show Data Wizard (%1)").arg(_dataWizardAct->shortcut().toString())); 1500 connect(_dataWizardAct, SIGNAL(triggered()), this, SLOT(showDataWizard())); 1501 1502 _changeFileDialogAct = new QAction(tr("Change Data &File"), this); 1503 _changeFileDialogAct->setIcon(KstGetIcon("change-data-file")); 1504 _changeFileDialogAct->setStatusTip(tr("Show Kst's Change Data File Dialog (%1)").arg(_changeFileDialogAct->shortcut().toString())); 1505 _changeFileDialogAct->setShortcut(QString("f")); 1506 _changeFileDialogAct->setToolTip(tr("Show Change Data File Dialog (%1)").arg(_changeFileDialogAct->shortcut().toString())); 1507 connect(_changeFileDialogAct, SIGNAL(triggered()), this, SLOT(showChangeFileDialog())); 1508 1509 _chooseColorDialogAct = new QAction(tr("Assign Curve &Color per File"), this); 1510 _chooseColorDialogAct->setStatusTip(tr("Show Kst's Choose Color Dialog")); 1511 _chooseColorDialogAct->setIcon(KstGetIcon("code-class")); 1512 connect(_chooseColorDialogAct, SIGNAL(triggered()), this, SLOT(showChooseColorDialog())); 1513 1514 _differentiateCurvesDialogAct = new QAction(tr("D&ifferentiate Curves"), this); 1515 _differentiateCurvesDialogAct->setStatusTip(tr("Show Kst's Differentiate Curves Dialog")); 1516 _differentiateCurvesDialogAct->setIcon(KstGetIcon("kst_differentiatecurves")); 1517 connect(_differentiateCurvesDialogAct, SIGNAL(triggered()), this, SLOT(showDifferentiateCurvesDialog())); 1518 1519 _filterMultipleDialogAct = new QAction(tr("&Filter Vectors"), this); 1520 _filterMultipleDialogAct->setStatusTip(tr("Filter multiple vectors")); 1521 _filterMultipleDialogAct->setIcon(KstGetIcon("kst_filter_vectors")); 1522 connect(_filterMultipleDialogAct, SIGNAL(triggered()), this, SLOT(filterMultipleDialog())); 1523 1524 // *********************** Settings actions ************************************** // 1525 _settingsDialogAct = new QAction(tr("&Configure Kst"), this); 1526 _settingsDialogAct->setStatusTip(tr("Show Kst's Configuration Dialog")); 1527 _settingsDialogAct->setIcon(KstGetIcon("configure")); 1528 connect(_settingsDialogAct, SIGNAL(triggered()), this, SLOT(showSettingsDialog())); 1529 1530 _themeDialogAct = new QAction(tr("&Theme"), this); 1531 _themeDialogAct->setStatusTip(tr("Show Kst's Theme Dialog")); 1532 _themeDialogAct->setIcon(KstGetIcon("themes")); 1533 connect(_themeDialogAct, SIGNAL(triggered()), this, SLOT(showThemeDialog())); 1534 1535 _clearUISettings = new QAction(tr("Clear settings and defaults"), this); 1536 _clearUISettings->setStatusTip(tr("Clear sticky defaults and all settings in all dialogs.")); 1537 //_clearUISettings->setIcon(KstGetIcon("configure")); // FIXME: pick an icon (broom?) 1538 connect(_clearUISettings, SIGNAL(triggered()), this, SLOT(clearDefaults())); 1539 1540 _clearDataSourceSettings = new QAction(tr("Clear datasource settings"), this); 1541 _clearDataSourceSettings->setStatusTip(tr("Clear datasource settings")); 1542 //_clearDataSourceSettings->setIcon(KstGetIcon("configure")); // FIXME: pick an icon (broom?) 1543 connect(_clearDataSourceSettings, SIGNAL(triggered()), this, SLOT(clearDataSourceSettings())); 1544 1545 _toggleStatusBar = new QAction(tr("Show status bar"), this); 1546 _toggleStatusBar->setCheckable(true); 1547 _toggleStatusBar->setChecked(_settings.value("showstatusbar", true).toBool()); 1548 connect(_toggleStatusBar, SIGNAL(triggered()), this, SLOT(toggleStatusBar())); 1549 1550 // *********************** Help actions ************************************** // 1551 _debugDialogAct = new QAction(tr("&Debug Dialog"), this); 1552 _debugDialogAct->setStatusTip(tr("Show the Kst debugging dialog")); 1553 _debugDialogAct->setIcon(KstGetIcon("text-x-log")); 1554 connect(_debugDialogAct, SIGNAL(triggered()), this, SLOT(showDebugDialog())); 1555 1556 _bugReportWizardAct = new QAction(tr("&Bug Report Wizard"), this); 1557 _bugReportWizardAct->setStatusTip(tr("Show Kst's Bug Report Wizard")); 1558 _bugReportWizardAct->setIcon(KstGetIcon("kbugbuster")); 1559 connect(_bugReportWizardAct, SIGNAL(triggered()), this, SLOT(showBugReportWizard())); 1560 1561 _aboutAct = new QAction(tr("&About"), this); 1562 _aboutAct->setStatusTip(tr("Show Kst's About box")); 1563 _aboutAct->setIcon(KstGetIcon("dialog-information")); 1564 connect(_aboutAct, SIGNAL(triggered()), this, SLOT(about())); 1565 1566 _showShortcutAct = new QAction(tr("Keyboard Shortcuts"), this); 1567 _showShortcutAct->setStatusTip(tr("Show a list of keyboard shortcuts")); 1568 connect(_showShortcutAct, SIGNAL(triggered()), this, SLOT(showShortcutDialog())); 1569 1570 _video1Act = new QAction(tr("#&1: Quick Start"), this); 1571 _video1Act->setStatusTip(tr("Kst presentation #1: The shortest tutorial to the fastest plotting tool")); 1572 connect(_video1Act, SIGNAL(triggered()), _videoMapper, SLOT(map())); 1573 _videoMapper->setMapping(_video1Act, 1); 1574 _video2Act = new QAction(tr("#&2: General UI Presentation"), this); 1575 _video2Act->setStatusTip(tr("Kst presentation #2: General presentation of the user interface and most important concepts")); 1576 connect(_video2Act, SIGNAL(triggered()), _videoMapper, SLOT(map())); 1577 _videoMapper->setMapping(_video2Act, 2); 1578 _video3Act = new QAction(tr("#&3: Live Data / Range Tools"), this); 1579 _video3Act->setStatusTip(tr("Kst presentation #3: Range tools and live plots with streaming data")); 1580 connect(_video3Act, SIGNAL(triggered()), _videoMapper, SLOT(map())); 1581 _videoMapper->setMapping(_video3Act, 3); 1582 _video4Act = new QAction(tr("#&4: FFT, Equations, Fits, Filters"), this); 1583 _video4Act->setStatusTip(tr("Kst presentation #4: FFTs, equations, filters, fits, plugins")); 1584 connect(_video4Act, SIGNAL(triggered()), _videoMapper, SLOT(map())); 1585 _videoMapper->setMapping(_video4Act, 4); 1586 _video5Act = new QAction(tr("#&5: Productivity Features"), this); 1587 _video5Act->setStatusTip(tr("Kst presentation #5: Unique productivity features like edit multiple mode and change data file tool")); 1588 connect(_video5Act, SIGNAL(triggered()), _videoMapper, SLOT(map())); 1589 _videoMapper->setMapping(_video5Act, 5); 1590 _video6Act = new QAction(tr("#&6: Advanced Layout / Export"), this); 1591 _video6Act->setStatusTip(tr("Kst presentation #6: Advanced layout and export options")); 1592 connect(_video6Act, SIGNAL(triggered()), _videoMapper, SLOT(map())); 1593 _videoMapper->setMapping(_video6Act, 6); 1594 _video7Act = new QAction(tr("#&7: Matrices / Images / Metadata"), this); 1595 _video7Act->setStatusTip(tr("Kst presentation #7: Matrices, images and metadata")); 1596 connect(_video7Act, SIGNAL(triggered()), _videoMapper, SLOT(map())); 1597 _videoMapper->setMapping(_video7Act, 7); 1598 connect(_videoMapper, SIGNAL(mapped(int)), this, SLOT(videoTutorial(int))); 1599 } 1600 1601 1602 void MainWindow::createMenus() { 1603 _fileMenu = menuBar()->addMenu(tr("&File")); 1604 // Session operations 1605 _fileMenu->addAction(_openAct); 1606 _fileMenu->addAction(_saveAct); 1607 _fileMenu->addAction(_saveAsAct); 1608 _fileMenu->addAction(_closeAct); 1609 _fileMenu->addSeparator(); 1610 _recentKstFilesMenu = _fileMenu->addMenu(tr("&Recent Sessions")); 1611 _recentDataFilesMenu = _fileMenu->addMenu(tr("Recent Data &Files")); 1612 _fileMenu->addSeparator(); 1613 // Reload, isolate it a bit from the other entries to avoid inadvertent triggering 1614 _fileMenu->addAction(_reloadAct); 1615 _fileMenu->addSeparator(); 1616 // Print/export 1617 _fileMenu->addAction(_printAct); 1618 _fileMenu->addAction(_exportGraphicsAct); 1619 _fileMenu->addAction(_exportVectorsAct); 1620 _fileMenu->addAction(_logAct); 1621 _fileMenu->addSeparator(); 1622 // Tabs 1623 _fileMenu->addAction(_newTabAct); 1624 _fileMenu->addAction(_closeTabAct); 1625 _fileMenu->addSeparator(); 1626 // exit 1627 _fileMenu->addAction(_exitAct); 1628 // recent files 1629 _fileMenu->addSeparator(); 1630 updateRecentKstFiles(); 1631 1632 1633 _editMenu = menuBar()->addMenu(tr("&Edit")); 1634 _editMenu->addAction(_undoAct); 1635 _editMenu->addAction(_redoAct); 1636 _editMenu->addAction(_copyTabAct); 1637 // Cut/Copy/Paste will come here 1638 1639 _viewMenu = menuBar()->addMenu(tr("&View")); 1640 _viewMenu->addAction(_vectorEditorAct); 1641 _viewMenu->addAction(_scalarEditorAct); 1642 _viewMenu->addAction(_matrixEditorAct); 1643 _viewMenu->addAction(_stringEditorAct); 1644 1645 _rangeMenu = menuBar()->addMenu(tr("&Range")); 1646 _rangeMenu->addAction(_backAct); 1647 _rangeMenu->addAction(_backSmallAct); 1648 _rangeMenu->addAction(_forwardAct); 1649 _rangeMenu->addAction(_forwardSmallAct); 1650 _rangeMenu->addSeparator(); 1651 _rangeMenu->addAction(_readFromEndAct); 1652 _rangeMenu->addAction(_readToEndAct); 1653 _rangeMenu->addAction(_pauseAct); 1654 _rangeMenu->addSeparator(); 1655 _rangeMenu->addAction(_changeDataSampleDialogAct); 1656 1657 _createMenu = menuBar()->addMenu(tr("&Create")); 1658 // Containers 1659 _createMenu->addAction(_insertPlotAct); 1660 //_createMenu->addAction(_createPlotAct); 1661 _createMenu->addAction(_createSharedAxisBoxAct); 1662 _createMenu->addSeparator(); 1663 // Primitives 1664 _createMenu->addAction(_newScalarAct); 1665 _createMenu->addAction(_newVectorAct); 1666 _createMenu->addAction(_newMatrixAct); 1667 _createMenu->addAction(_newStringAct); 1668 _createMenu->addSeparator(); 1669 // Data objects 1670 _createMenu->addAction(_newEquationAct); 1671 _createMenu->addAction(_newHistogramAct); 1672 _createMenu->addAction(_newPSDAct); 1673 _createMenu->addAction(_newSpectrogramAct); 1674 _createMenu->addAction(_newEventMonitorAct); 1675 _createMenu->addSeparator(); 1676 1677 // Now, create the dynamic plugin menus 1678 QMenu* _pluginsMenu = _createMenu->addMenu(tr("Standard P&lugin")); 1679 QMenu* _fitPluginsMenu = _createMenu->addMenu(tr("Fit Pl&ugin")); 1680 QMenu* _filterPluginsMenu = _createMenu->addMenu(tr("Fil&ter Plugin")); 1681 PluginMenuItemAction* action; 1682 foreach (const QString &pluginName, DataObject::dataObjectPluginList()) { 1683 action = new PluginMenuItemAction(pluginName, this); 1684 connect(action, SIGNAL(triggered(QString&)), this, SLOT(showPluginDialog(QString&))); 1685 _pluginsMenu->addAction(action); 1686 } 1687 foreach (const QString &pluginName, DataObject::fitsPluginList()) { 1688 action = new PluginMenuItemAction(pluginName, this); 1689 connect(action, SIGNAL(triggered(QString&)), this, SLOT(showPluginDialog(QString&))); 1690 _fitPluginsMenu->addAction(action); 1691 } 1692 foreach (const QString &pluginName, DataObject::filterPluginList()) { 1693 action = new PluginMenuItemAction(pluginName, this); 1694 connect(action, SIGNAL(triggered(QString&)), this, SLOT(showPluginDialog(QString&))); 1695 _filterPluginsMenu->addAction(action); 1696 } 1697 _createMenu->addSeparator(); 1698 // Relations 1699 _createMenu->addAction(_newCurveAct); 1700 _createMenu->addAction(_newImageAct); 1701 _createMenu->addSeparator(); 1702 // Annotation objects 1703 QMenu* annotations = _createMenu->addMenu(tr("&Annotation")); 1704 annotations->addAction(_createLabelAct); 1705 annotations->addAction(_createBoxAct); 1706 annotations->addAction(_createCircleAct); 1707 annotations->addAction(_createEllipseAct); 1708 annotations->addAction(_createLineAct); 1709 annotations->addAction(_createArrowAct); 1710 annotations->addAction(_createPictureAct); 1711 #ifndef KST_NO_SVG 1712 annotations->addAction(_createSvgAct); 1713 #endif 1714 1715 _modeMenu = menuBar()->addMenu(tr("&Mode")); 1716 // Interaction mode 1717 _modeMenu->addSeparator()->setText(tr("Interaction mode")); 1718 _modeMenu->addAction(_standardZoomAct); 1719 _modeMenu->addAction(_xOnlyZoomAct); 1720 _modeMenu->addAction(_yOnlyZoomAct); 1721 _modeMenu->addAction(_layoutModeAct); 1722 _standardZoomAct->setChecked(true); 1723 _modeMenu->addSeparator(); 1724 // Tied zoom options 1725 _modeMenu->addAction(_tiedZoomAct); 1726 _modeMenu->addAction(_tabTiedAct); 1727 _modeMenu->addSeparator(); 1728 // Data mode 1729 _modeMenu->addAction(_highlightPointAct); 1730 1731 _toolsMenu = menuBar()->addMenu(tr("&Tools")); 1732 _toolsMenu->addAction(_dataManagerAct); 1733 _toolsMenu->addAction(_dataWizardAct); 1734 _toolsMenu->addAction(_changeFileDialogAct); 1735 _toolsMenu->addAction(_chooseColorDialogAct); 1736 _toolsMenu->addAction(_differentiateCurvesDialogAct); 1737 _toolsMenu->addAction(_filterMultipleDialogAct); 1738 _toolsMenu->addSeparator(); 1739 updateRecentDataFiles(); 1740 1741 _settingsMenu = menuBar()->addMenu(tr("&Settings")); 1742 _settingsMenu->addAction(_settingsDialogAct); 1743 _settingsMenu->addAction(_themeDialogAct); 1744 _settingsMenu->addAction(_clearUISettings); 1745 _settingsMenu->addAction(_clearDataSourceSettings); 1746 _settingsMenu->addAction(_toggleStatusBar); 1747 1748 menuBar()->addSeparator(); 1749 1750 _helpMenu = menuBar()->addMenu(tr("&Help")); 1751 QMenu* _videoTutorialsMenu = _helpMenu->addMenu(tr("&Video tutorials")); 1752 _videoTutorialsMenu->addAction(_video1Act); 1753 _videoTutorialsMenu->addAction(_video2Act); 1754 _videoTutorialsMenu->addAction(_video3Act); 1755 _videoTutorialsMenu->addAction(_video4Act); 1756 _videoTutorialsMenu->addAction(_video5Act); 1757 _videoTutorialsMenu->addAction(_video6Act); 1758 _videoTutorialsMenu->addAction(_video7Act); 1759 _helpMenu->addSeparator(); 1760 _helpMenu->addAction(_debugDialogAct); 1761 _helpMenu->addAction(_bugReportWizardAct); 1762 _helpMenu->addSeparator(); 1763 _helpMenu->addAction(_showShortcutAct); 1764 _helpMenu->addAction(_aboutAct); 1765 1766 } 1767 1768 1769 void MainWindow::createToolBars() { 1770 setToolButtonStyle(Qt::ToolButtonIconOnly); 1771 1772 _fileToolBar = addToolBar(tr("File")); 1773 _fileToolBar->setObjectName("File Toolbar"); 1774 _fileToolBar->addAction(_openAct); 1775 _fileToolBar->addAction(_saveAct); 1776 _fileToolBar->addAction(_reloadAct); 1777 _fileToolBar->addAction(_printAct); 1778 _fileToolBar->addAction(_logAct); 1779 1780 _editToolBar = addToolBar(tr("Edit")); 1781 _editToolBar->setObjectName("Edit Toolbar"); 1782 _editToolBar->addAction(_undoAct); 1783 _editToolBar->addAction(_redoAct); 1784 _editToolBar->addAction(_copyTabAct); 1785 1786 _toolsToolBar = addToolBar(tr("Tools")); 1787 _toolsToolBar->setObjectName("Tools Toolbar"); 1788 _toolsToolBar->addAction(_dataManagerAct); 1789 _toolsToolBar->addAction(_dataWizardAct); 1790 _toolsToolBar->addAction(_changeDataSampleDialogAct); 1791 _toolsToolBar->addAction(_changeFileDialogAct); 1792 1793 _rangeToolBar = addToolBar(tr("Data Range")); 1794 _rangeToolBar->setObjectName("Data Range Toolbar"); 1795 _rangeToolBar->addAction(_backAct); 1796 _rangeToolBar->addAction(_forwardAct); 1797 _rangeToolBar->addAction(_readFromEndAct); 1798 _rangeToolBar->addAction(_readToEndAct); 1799 _rangeToolBar->addAction(_pauseAct); 1800 1801 _modeToolBar = addToolBar(tr("Mode")); 1802 _modeToolBar->setObjectName("Mode Toolbar"); 1803 _modeToolBar->addAction(_tiedZoomAct); 1804 _modeToolBar->addAction(_highlightPointAct); 1805 _modeToolBar->addSeparator(); 1806 _modeToolBar->addAction(_standardZoomAct); 1807 _modeToolBar->addAction(_xOnlyZoomAct); 1808 _modeToolBar->addAction(_yOnlyZoomAct); 1809 _modeToolBar->addAction(_layoutModeAct); 1810 1811 _plotLayoutToolBar = addToolBar(tr("Plot Layout")); 1812 _plotLayoutToolBar->setObjectName("Plot Layout Toolbar"); 1813 _plotLayoutToolBar->addAction(_createSharedAxisBoxAct); 1814 _plotLayoutToolBar->addAction(_insertPlotAct); 1815 //_plotLayoutToolBar->addAction(_createPlotAct); 1816 1817 _annotationToolBar = addToolBar(tr("Advanced Layout")); 1818 _annotationToolBar->setObjectName("Advanced Layout Toolbar"); 1819 _annotationToolBar->addAction(_createLabelAct); 1820 _annotationToolBar->addAction(_createBoxAct); 1821 _annotationToolBar->addAction(_createCircleAct); 1822 _annotationToolBar->addAction(_createEllipseAct); 1823 _annotationToolBar->addAction(_createLineAct); 1824 _annotationToolBar->addAction(_createArrowAct); 1825 _annotationToolBar->addAction(_createPictureAct); 1826 #ifndef KST_NO_SVG 1827 _annotationToolBar->addAction(_createSvgAct); 1828 #endif 1829 } 1830 1831 1832 void MainWindow::createStatusBar() { 1833 _messageLabel = new QLabel(statusBar()); 1834 setStatusMessage(tr("Ready"), 3000); 1835 1836 _progressBar = new QProgressBar(statusBar()); 1837 _progressBar->setFixedWidth(200); 1838 _progressBar->hide(); 1839 statusBar()->addPermanentWidget(_progressBar); 1840 MemoryWidget *mw = new MemoryWidget(statusBar()); 1841 statusBar()->addPermanentWidget(mw); 1842 DebugNotifier *dn = new DebugNotifier(statusBar()); 1843 connect(dn, SIGNAL(showDebugLog()), this, SLOT(showDebugDialog())); 1844 connect(_debugDialog, SIGNAL(notifyOfError()), dn, SLOT(reanimate())); 1845 connect(_debugDialog, SIGNAL(notifyAllClear()), dn, SLOT(close())); 1846 statusBar()->addPermanentWidget(dn); 1847 1848 bool statusBarVisible = _settings.value("showstatusbar", true).toBool(); 1849 statusBar()->setVisible( statusBarVisible ); 1850 1851 } 1852 1853 /** set the status bar message. If you are doing this inside a view 1854 * object paint() call, then set delayed to true, and call ::updateStatusMessage() 1855 * later (after leaving paint). This is currently done for you in updateViewItems */ 1856 void MainWindow::setStatusMessage(QString message, int timeout, bool delayed) { 1857 _statusBarMessage = message; 1858 _statusBarTimeout = timeout; 1859 if (!delayed) { 1860 statusBar()->showMessage(message, timeout); 1861 } 1862 } 1863 1864 void MainWindow::videoTutorial(int i) { 1865 switch (i) { 1866 case 1: 1867 QDesktopServices::openUrl(QUrl("http://www.youtube.com/watch?v=d1uz5g_cWh4")); break; 1868 case 2: 1869 QDesktopServices::openUrl(QUrl("http://www.youtube.com/watch?v=6z2bGNrgwL0")); break; 1870 case 3: 1871 QDesktopServices::openUrl(QUrl("http://www.youtube.com/watch?v=dstOQpmfY1U")); break; 1872 case 4: 1873 QDesktopServices::openUrl(QUrl("http://www.youtube.com/watch?v=YJ54X0nKnmk")); break; 1874 case 5: 1875 QDesktopServices::openUrl(QUrl("http://www.youtube.com/watch?v=3YZVC-GiS_4")); break; 1876 case 6: 1877 QDesktopServices::openUrl(QUrl("http://www.youtube.com/watch?v=rI7nYHlz6rs")); break; 1878 case 7: 1879 QDesktopServices::openUrl(QUrl("http://www.youtube.com/watch?v=mgP24MryyKw")); break; 1880 default: 1881 break; 1882 } 1883 } 1884 1885 QString MainWindow::statusMessage() { 1886 return statusBar()->currentMessage(); 1887 } 1888 1889 void MainWindow::updateStatusMessage() { 1890 statusBar()->showMessage(_statusBarMessage, _statusBarTimeout); 1891 } 1892 1893 QProgressBar *MainWindow::progressBar() const { 1894 return _progressBar; 1895 } 1896 1897 void MainWindow::updateProgress(int percent, const QString& message) 1898 { 1899 if (percent == -1) { 1900 _progressBar->setMaximum(0); 1901 _progressBar->setMinimum(0); 1902 _progressBar->show(); 1903 return; 1904 } 1905 1906 if (percent > 0 && percent < 100) { 1907 _progressBar->setMaximum(100); 1908 _progressBar->setValue(percent); 1909 _progressBar->show(); 1910 } else { 1911 _progressBar->hide(); 1912 } 1913 setStatusMessage(message); 1914 } 1915 1916 void MainWindow::readFromEnd() { 1917 int nf = 0; 1918 int skip; 1919 bool do_skip; 1920 bool do_filter; 1921 1922 DataVectorList dataVectors = document()->objectStore()->getObjects<DataVector>(); 1923 1924 foreach (DataVectorPtr v, dataVectors) { 1925 v->readLock(); 1926 nf = v->reqNumFrames(); 1927 if (nf <=0 ) { 1928 nf = v->numFrames(); 1929 } 1930 skip = v->skip(); 1931 do_skip = v->doSkip(); 1932 do_filter = v->doAve(); 1933 v->unlock(); 1934 1935 v->writeLock(); 1936 v->changeFrames(-1, nf, skip, do_skip, do_filter); 1937 v->registerChange(); 1938 v->unlock(); 1939 } 1940 1941 VScalarList vScalars = document()->objectStore()->getObjects<VScalar>(); 1942 foreach (VScalarPtr s, vScalars) { 1943 s->readLock(); 1944 s->changeFrame(-1); 1945 s->registerChange(); 1946 s->unlock(); 1947 } 1948 1949 DataStringList dataStrings = document()->objectStore()->getObjects<DataString>(); 1950 foreach (DataStringPtr s, dataStrings) { 1951 if (s->isStream()) { 1952 s->readLock(); 1953 s->setFrame(-1); 1954 s->registerChange(); 1955 s->unlock(); 1956 } 1957 } 1958 1959 DataMatrixList dataMatrices = document()->objectStore()->getObjects<DataMatrix>(); 1960 foreach (DataMatrixPtr m, dataMatrices) { 1961 m->readLock(); 1962 m->setFrame(-1); 1963 m->registerChange(); 1964 m->unlock(); 1965 } 1966 1967 UpdateManager::self()->doUpdates(true); 1968 dialogDefaults().setValue("vector/range", nf); 1969 dialogDefaults().setValue("vector/countFromEnd", true); 1970 dialogDefaults().setValue("vector/readToEnd", false); 1971 } 1972 1973 void MainWindow::readToEnd() { 1974 int f0 = 0; 1975 int skip; 1976 bool do_skip; 1977 bool do_filter; 1978 1979 DataVectorList dataVectors = document()->objectStore()->getObjects<DataVector>(); 1980 1981 foreach (DataVectorPtr v, dataVectors) { 1982 v->readLock(); 1983 f0 = v->startFrame(); 1984 skip = v->skip(); 1985 do_skip = v->doSkip(); 1986 do_filter = v->doAve(); 1987 v->unlock(); 1988 1989 v->writeLock(); 1990 v->changeFrames(f0, -1, skip, do_skip, do_filter); 1991 v->registerChange(); 1992 v->unlock(); 1993 } 1994 1995 VScalarList vScalars = document()->objectStore()->getObjects<VScalar>(); 1996 foreach (VScalarPtr s, vScalars) { 1997 s->readLock(); 1998 s->changeFrame(-1); 1999 s->registerChange(); 2000 s->unlock(); 2001 } 2002 2003 DataStringList dataStrings = document()->objectStore()->getObjects<DataString>(); 2004 foreach (DataStringPtr s, dataStrings) { 2005 if (s->isStream()) { 2006 s->readLock(); 2007 s->setFrame(-1); 2008 s->registerChange(); 2009 s->unlock(); 2010 } 2011 } 2012 2013 DataMatrixList dataMatrices = document()->objectStore()->getObjects<DataMatrix>(); 2014 foreach (DataMatrixPtr m, dataMatrices) { 2015 m->readLock(); 2016 m->setFrame(-1); 2017 m->registerChange(); 2018 m->unlock(); 2019 } 2020 2021 dialogDefaults().setValue("vector/start", f0); 2022 dialogDefaults().setValue("vector/countFromEnd", false); 2023 dialogDefaults().setValue("vector/readToEnd", true); 2024 UpdateManager::self()->doUpdates(true); 2025 } 2026 2027 void MainWindow::pause(bool pause) { 2028 UpdateManager::self()->setPaused(pause); 2029 2030 //if (!pause) { 2031 //foreach (DataSourcePtr s, document()->objectStore()->dataSourceList()) { 2032 //s->checkUpdate(); 2033 //} 2034 //} 2035 } 2036 2037 void MainWindow::forward(double scale) { 2038 int f0 = 0; 2039 int nf = 0; 2040 int lastF = -1; 2041 int skip; 2042 int filelength; 2043 bool count_from_end; 2044 bool read_to_end; 2045 bool do_skip; 2046 bool do_filter; 2047 2048 DataVectorList dataVectors = document()->objectStore()->getObjects<DataVector>(); 2049 DataMatrixList dataMatrices = document()->objectStore()->getObjects<DataMatrix>(); 2050 VScalarList vScalars = document()->objectStore()->getObjects<VScalar>(); 2051 DataStringList dataStrings = document()->objectStore()->getObjects<DataString>(); 2052 QHash<int,int> lastframehash; 2053 2054 foreach (DataVectorPtr v, dataVectors) { 2055 v->readLock(); 2056 f0 = v->startFrame(); 2057 nf = v->numFrames(); 2058 count_from_end = v->countFromEOF(); 2059 read_to_end = v->readToEOF(); 2060 filelength = v->fileLength(); 2061 2062 skip = v->skip(); 2063 do_skip = v->doSkip(); 2064 do_filter = v->doAve(); 2065 v->unlock(); 2066 2067 if ((!count_from_end) && (!read_to_end)) { 2068 f0 += ceil(scale*nf); 2069 if (f0+nf>=filelength) { 2070 f0 = filelength - nf; 2071 } 2072 lastF = f0 + nf - 1; 2073 ++lastframehash[lastF]; 2074 2075 v->writeLock(); 2076 v->changeFrames(f0, nf, skip, do_skip, do_filter); 2077 v->registerChange(); 2078 v->unlock(); 2079 } 2080 } 2081 2082 int most_popular_lastF = -1; 2083 int n_most_popular_lastF = -1; 2084 foreach (int key, lastframehash.keys()) { 2085 int n = lastframehash[key] ; 2086 if (n > n_most_popular_lastF) { 2087 n_most_popular_lastF = n; 2088 most_popular_lastF = key; 2089 } 2090 } 2091 2092 foreach (VScalarPtr vs, vScalars) { 2093 int new_frame; 2094 int filelength = vs->fileLength(); 2095 if (most_popular_lastF>=0) { 2096 if (most_popular_lastF < filelength) { 2097 new_frame = most_popular_lastF; 2098 } else { 2099 new_frame = filelength-1; 2100 } 2101 } else { 2102 if (vs->F0() < 0) { 2103 new_frame = -1; 2104 } else if (vs->F0()+1 <= filelength) { 2105 new_frame = vs->F0()+1; 2106 } else { 2107 new_frame = filelength-1; 2108 } 2109 } 2110 vs->writeLock(); 2111 vs->changeFrame(new_frame); 2112 vs->registerChange(); 2113 vs->unlock(); 2114 } 2115 2116 foreach (DataStringPtr s, dataStrings) { 2117 if (s->isStream()) { 2118 int new_frame; 2119 int filelength = s->fileLength(); 2120 if (most_popular_lastF>=0) { 2121 if (most_popular_lastF < filelength) { 2122 new_frame = most_popular_lastF; 2123 } else { 2124 new_frame = filelength-1; 2125 } 2126 } else { 2127 if (s->frame() < 0) { 2128 new_frame = -1; 2129 } else if (s->frame()+1 < filelength) { 2130 new_frame = s->frame()+1; 2131 } else { 2132 new_frame = filelength-1; 2133 } 2134 } 2135 s->writeLock(); 2136 s->setFrame(new_frame); 2137 s->registerChange(); 2138 s->unlock(); 2139 } 2140 } 2141 2142 2143 foreach (DataMatrixPtr m, dataMatrices) { 2144 if (m->isStream()) { 2145 int new_frame; 2146 int filelength = m->fileLength(); 2147 if (most_popular_lastF>=0) { 2148 if (most_popular_lastF < filelength) { 2149 new_frame = most_popular_lastF; 2150 } else { 2151 new_frame = filelength-1; 2152 } 2153 } else { 2154 if (m->frame() < 0) { 2155 new_frame = -1; 2156 } else if (m->frame()+1 < filelength) { 2157 new_frame = m->frame()+1; 2158 } else { 2159 new_frame = filelength-1; 2160 } 2161 } 2162 m->writeLock(); 2163 m->setFrame(new_frame); 2164 m->registerChange(); 2165 m->unlock(); 2166 } 2167 } 2168 2169 dialogDefaults().setValue("vector/range", nf); 2170 dialogDefaults().setValue("vector/start", f0); 2171 dialogDefaults().setValue("vector/countFromEnd", false); 2172 dialogDefaults().setValue("vector/readToEnd", false); 2173 2174 UpdateManager::self()->doUpdates(true); 2175 } 2176 2177 void MainWindow::back(double scale) { 2178 int f0 = 0; 2179 int nf = 0; 2180 int skip; 2181 int filelength; 2182 bool count_from_end; 2183 bool read_to_end; 2184 bool do_skip; 2185 bool do_filter; 2186 int lastF = -1; 2187 2188 DataVectorList dataVectors = document()->objectStore()->getObjects<DataVector>(); 2189 DataMatrixList dataMatrices = document()->objectStore()->getObjects<DataMatrix>(); 2190 VScalarList vScalars = document()->objectStore()->getObjects<VScalar>(); 2191 DataStringList dataStrings = document()->objectStore()->getObjects<DataString>(); 2192 2193 QHash<int,int> lastframehash; 2194 2195 foreach (DataVectorPtr v, dataVectors) { 2196 v->readLock(); 2197 f0 = v->startFrame(); 2198 nf = v->numFrames(); 2199 count_from_end = v->countFromEOF(); 2200 read_to_end = v->readToEOF(); 2201 filelength = v->fileLength(); 2202 2203 skip = v->skip(); 2204 do_skip = v->doSkip(); 2205 do_filter = v->doAve(); 2206 v->unlock(); 2207 2208 if (f0 != 0) { 2209 if (count_from_end) { 2210 f0 = filelength - nf; 2211 } 2212 if (read_to_end) { 2213 nf = filelength - f0; 2214 } 2215 2216 f0 -= ceil(scale*nf); 2217 if (f0<0) { 2218 f0 = 0; 2219 } 2220 lastF = f0 + nf - 1; 2221 ++lastframehash[lastF]; 2222 2223 v->writeLock(); 2224 v->changeFrames(f0, nf, skip, do_skip, do_filter); 2225 v->registerChange(); 2226 v->unlock(); 2227 } 2228 } 2229 2230 int most_popular_lastF = -1; 2231 int n_most_popular_lastF = -1; 2232 foreach (int key, lastframehash.keys()) { 2233 int n = lastframehash[key] ; 2234 if (n > n_most_popular_lastF) { 2235 n_most_popular_lastF = n; 2236 most_popular_lastF = key; 2237 } 2238 } 2239 2240 foreach (VScalarPtr vs, vScalars) { 2241 int new_frame; 2242 int filelength = vs->fileLength(); 2243 if (most_popular_lastF>=0) { 2244 if (most_popular_lastF < filelength) { 2245 new_frame = most_popular_lastF; 2246 } else { 2247 new_frame = filelength-1; 2248 } 2249 } else { 2250 if (vs->F0() < 0) { 2251 new_frame = filelength-1; 2252 } else if (vs->F0()-1 >= 0) { 2253 new_frame = vs->F0()-1; 2254 } else { 2255 new_frame = 0; 2256 } 2257 } 2258 vs->writeLock(); 2259 vs->changeFrame(new_frame); 2260 vs->registerChange(); 2261 vs->unlock(); 2262 } 2263 2264 foreach (DataStringPtr s, dataStrings) { 2265 if (s->isStream()) { 2266 int new_frame; 2267 int filelength = s->fileLength(); 2268 if (most_popular_lastF>=0) { 2269 if (most_popular_lastF < filelength) { 2270 new_frame = most_popular_lastF; 2271 } else { 2272 new_frame = filelength-1; 2273 } 2274 } else { 2275 if (s->frame() < 0) { 2276 new_frame = filelength-1; 2277 } else if (s->frame()-1 >= 0) { 2278 new_frame = s->frame()-1; 2279 } else { 2280 new_frame = 0; 2281 } 2282 } 2283 s->writeLock(); 2284 s->setFrame(new_frame); 2285 s->registerChange(); 2286 s->unlock(); 2287 } 2288 } 2289 2290 foreach (DataMatrixPtr m, dataMatrices) { 2291 if (m->isStream()) { 2292 int new_frame; 2293 int filelength = m->fileLength(); 2294 if (most_popular_lastF>=0) { 2295 if (most_popular_lastF < filelength) { 2296 new_frame = most_popular_lastF; 2297 } else { 2298 new_frame = filelength-1; 2299 } 2300 } else { 2301 if (m->frame() < 0) { 2302 new_frame = filelength-1; 2303 } else if (m->frame()-1 >= 0) { 2304 new_frame = m->frame()-1; 2305 } else { 2306 new_frame = filelength-2; 2307 } 2308 } 2309 m->writeLock(); 2310 m->setFrame(new_frame); 2311 m->registerChange(); 2312 m->unlock(); 2313 } 2314 } 2315 2316 dialogDefaults().setValue("vector/range", nf); 2317 dialogDefaults().setValue("vector/start", f0); 2318 dialogDefaults().setValue("vector/countFromEnd", false); 2319 dialogDefaults().setValue("vector/readToEnd", false); 2320 UpdateManager::self()->doUpdates(true); 2321 } 2322 2323 void MainWindow::reload() { 2324 document()->objectStore()->rebuildDataSourceList(); 2325 UpdateManager::self()->doUpdates(true); 2326 //document()->setChanged(true); 2327 } 2328 2329 void MainWindow::showDataManager() { 2330 if (!_dataManager) { 2331 _dataManager = new DataManager(this, _doc); 2332 } 2333 if (_dataManager->isVisible()) { 2334 _dataManager->raise(); 2335 _dataManager->activateWindow(); 2336 } 2337 _dataManager->show(); 2338 } 2339 2340 2341 void Kst::MainWindow::updateViewItems(qint64 serial) 2342 { 2343 2344 QList<PlotItem *> plots = ViewItem::getItems<PlotItem>(); 2345 2346 bool changed = false; 2347 foreach (PlotItem *plot, plots) { 2348 changed |= plot->handleChangedInputs(serial); 2349 } 2350 2351 QList<LabelItem*> labels = ViewItem::getItems<LabelItem>(); 2352 foreach (LabelItem * label, labels) { 2353 if (label->_labelRc) { 2354 label->inputsChanged(serial); 2355 } 2356 } 2357 2358 2359 if (changed) { 2360 _tabWidget->currentView()->update(); 2361 if (_viewVectorDialog) { 2362 _viewVectorDialog->update(); 2363 } 2364 kstApp->mainWindow()->updateStatusMessage(); 2365 } 2366 2367 QTimer::singleShot(20, UpdateManager::self(), SLOT(viewItemUpdateFinished())); // why 20ms ??? 2368 } 2369 2370 void MainWindow::showVectorEditor() { 2371 if (!_viewVectorDialog) { 2372 _viewVectorDialog = new ViewVectorDialog(this, _doc); 2373 } 2374 if (_viewVectorDialog->isVisible()) { 2375 _viewVectorDialog->raise(); 2376 _viewVectorDialog->activateWindow(); 2377 } 2378 _viewVectorDialog->show(); 2379 } 2380 2381 2382 void MainWindow::showScalarEditor() { 2383 ViewPrimitiveDialog *viewScalarDialog = new ViewScalarDialog(this, _doc); 2384 viewScalarDialog->show(); 2385 } 2386 2387 2388 void MainWindow::showStringEditor() { 2389 ViewPrimitiveDialog *viewStringDialog = new ViewStringDialog(this, _doc); 2390 viewStringDialog->show(); 2391 } 2392 2393 void MainWindow::showMatrixEditor() { 2394 ViewMatrixDialog *viewMatrixDialog = new ViewMatrixDialog(this, _doc); 2395 viewMatrixDialog->show(); 2396 } 2397 2398 2399 void MainWindow::showDebugDialog() { 2400 if (!_debugDialog) { 2401 _debugDialog = new DebugDialog(this); 2402 } 2403 _debugDialog->setObjectStore(document()->objectStore()); 2404 if (_debugDialog->isVisible()) { 2405 _debugDialog->raise(); 2406 _debugDialog->activateWindow(); 2407 } 2408 _debugDialog->show(); 2409 } 2410 2411 2412 void MainWindow::showExportGraphicsDialog() { 2413 if (!_exportGraphics) { 2414 _exportGraphics = new ExportGraphicsDialog(this); 2415 connect(_exportGraphics, SIGNAL(exportGraphics(QString,QString,int,int,int,bool,int)), 2416 this, SLOT(exportGraphicsFile(QString,QString,int,int,int,bool,int))); 2417 } 2418 if (_exportGraphics->isVisible()) { 2419 _exportGraphics->raise(); 2420 _exportGraphics->activateWindow(); 2421 } 2422 _exportGraphics->show(); 2423 } 2424 2425 2426 void MainWindow::showExportVectorsDialog() { 2427 if (!_exportVectors) { 2428 _exportVectors = new ExportVectorsDialog(this); 2429 } 2430 if (_exportVectors->isVisible()) { 2431 _exportVectors->raise(); 2432 _exportVectors->activateWindow(); 2433 } 2434 _exportVectors->show(); 2435 } 2436 2437 2438 void MainWindow::showLogDialog() { 2439 if (!_logDialog) { 2440 _logDialog = new LogDialog(this); 2441 //connect(_logDialog, SIGNAL(exportLog(const QString &, time_t, const QString &, int, int, int, const QString &)), 2442 // this, SLOT(exportLog(const QString &, time_t, const QString &, int, int, int, const QString &))); 2443 } 2444 if (_logDialog->isVisible()) { 2445 _logDialog->raise(); 2446 _logDialog->activateWindow(); 2447 } 2448 _logDialog->show(); 2449 } 2450 2451 2452 void MainWindow::showSettingsDialog() { 2453 if (!_applicationSettingsDialog) { 2454 _applicationSettingsDialog = new ApplicationSettingsDialog(this); 2455 } 2456 if (_applicationSettingsDialog->isVisible()) { 2457 _applicationSettingsDialog->raise(); 2458 _applicationSettingsDialog->activateWindow(); 2459 } 2460 _applicationSettingsDialog->show(); 2461 } 2462 2463 2464 void MainWindow::showThemeDialog() { 2465 if (!_themeDialog) { 2466 _themeDialog = new ThemeDialog(this); 2467 } 2468 if (_themeDialog->isVisible()) { 2469 _themeDialog->raise(); 2470 _themeDialog->activateWindow(); 2471 } 2472 2473 _themeDialog->reset(); 2474 _themeDialog->show(); 2475 } 2476 2477 2478 void MainWindow::clearDefaults() { 2479 2480 QMessageBox confirmationBox; 2481 confirmationBox.setText(tr("Clear all settings and defaults?")); 2482 confirmationBox.setInformativeText(tr("You are about to clear all settings defaults in all dialogs in kst.\nThis can not be undone.")); 2483 confirmationBox.setStandardButtons(QMessageBox::Ok | QMessageBox::Cancel); 2484 confirmationBox.setDefaultButton(QMessageBox::Ok); 2485 int confirmed = confirmationBox.exec(); 2486 2487 switch (confirmed) { 2488 case QMessageBox::Ok: 2489 dialogDefaults().clear(); 2490 ApplicationSettings::self()->clear(); 2491 DataSourcePluginManager::settingsObject().clear(); 2492 break; 2493 case QMessageBox::Cancel: 2494 default: 2495 // cancel: do nothing at all. 2496 break; 2497 } 2498 } 2499 2500 void MainWindow::clearDataSourceSettings() { 2501 2502 QMessageBox confirmationBox; 2503 confirmationBox.setText(tr("Clear datasource settings?")); 2504 confirmationBox.setInformativeText(tr("You are about to clear all\nconfiguration settings for\nall datasources/file types.")); 2505 confirmationBox.setStandardButtons(QMessageBox::Ok | QMessageBox::Cancel); 2506 confirmationBox.setDefaultButton(QMessageBox::Ok); 2507 int confirmed = confirmationBox.exec(); 2508 2509 switch (confirmed) { 2510 case QMessageBox::Ok: 2511 DataSourcePluginManager::settingsObject().clear(); 2512 break; 2513 case QMessageBox::Cancel: 2514 default: 2515 // cancel: do nothing at all. 2516 break; 2517 } 2518 2519 } 2520 2521 2522 void MainWindow::showDifferentiateCurvesDialog() { 2523 if (!_differentiateCurvesDialog) { 2524 _differentiateCurvesDialog = new DifferentiateCurvesDialog(this); 2525 } 2526 if (_differentiateCurvesDialog->isVisible()) { 2527 _differentiateCurvesDialog->raise(); 2528 _differentiateCurvesDialog->activateWindow(); 2529 } 2530 _differentiateCurvesDialog->show(); 2531 } 2532 2533 2534 void MainWindow::filterMultipleDialog() { 2535 if (!_filterMultipleDialog) { 2536 _filterMultipleDialog = new FilterMultipleDialog(this); 2537 } 2538 if (_filterMultipleDialog->isVisible()) { 2539 _filterMultipleDialog->raise(); 2540 _filterMultipleDialog->activateWindow(); 2541 } 2542 _filterMultipleDialog->show(); 2543 } 2544 2545 void MainWindow::toggleStatusBar() { 2546 bool statusBarVisible = _settings.value("showstatusbar", true).toBool(); 2547 2548 statusBarVisible = !statusBarVisible; 2549 2550 statusBar()->setVisible(statusBarVisible); 2551 _toggleStatusBar->setChecked(statusBarVisible); 2552 2553 _settings.setValue("showstatusbar",statusBarVisible); 2554 } 2555 2556 2557 void MainWindow::showChooseColorDialog() { 2558 if (!_chooseColorDialog) { 2559 _chooseColorDialog = new ChooseColorDialog(this); 2560 } 2561 if (_chooseColorDialog->isVisible()) { 2562 _chooseColorDialog->raise(); 2563 _chooseColorDialog->activateWindow(); 2564 } 2565 _chooseColorDialog->show(); 2566 } 2567 2568 2569 void MainWindow::showChangeDataSampleDialog() { 2570 if (!_changeDataSampleDialog) { 2571 _changeDataSampleDialog = new ChangeDataSampleDialog(this); 2572 } 2573 if (_changeDataSampleDialog->isVisible()) { 2574 _changeDataSampleDialog->raise(); 2575 _changeDataSampleDialog->activateWindow(); 2576 } 2577 _changeDataSampleDialog->show(); 2578 } 2579 2580 2581 void MainWindow::showDataWizard() { 2582 DataWizard *dataWizard = new DataWizard(this); 2583 connect(dataWizard, SIGNAL(dataSourceLoaded(QString)), this, SLOT(updateRecentDataFiles(QString))); 2584 dataWizard->show(); 2585 } 2586 2587 void MainWindow::showDataWizard(const QString &dataFile) { 2588 DataWizard *dataWizard = new DataWizard(this, dataFile); 2589 dataWizard->show(); 2590 } 2591 2592 2593 void MainWindow::openRecentDataFile() 2594 { 2595 QAction *action = qobject_cast<QAction *>(sender()); 2596 if (action) { 2597 DataWizard *dataWizard = new DataWizard(this, action->data().toString()); 2598 connect(dataWizard, SIGNAL(dataSourceLoaded(QString)), this, SLOT(updateRecentDataFiles(QString))); 2599 dataWizard->show(); 2600 } 2601 } 2602 2603 2604 void MainWindow::showBugReportWizard() { 2605 if (!_bugReportWizard) { 2606 _bugReportWizard = new BugReportWizard(this); 2607 } 2608 if (_bugReportWizard->isVisible()) { 2609 _bugReportWizard->raise(); 2610 _bugReportWizard->activateWindow(); 2611 } 2612 _bugReportWizard->show(); 2613 } 2614 2615 void MainWindow::showChangeFileDialog() { 2616 if (!_changeFileDialog) { 2617 _changeFileDialog = new ChangeFileDialog(this); 2618 } 2619 if (_changeFileDialog->isVisible()) { 2620 _changeFileDialog->raise(); 2621 _changeFileDialog->activateWindow(); 2622 } 2623 _changeFileDialog->show(); 2624 } 2625 2626 void MainWindow::showPluginDialog(QString &pluginName) { 2627 DialogLauncher::self()->showBasicPluginDialog(pluginName); 2628 } 2629 2630 bool MainWindow::isTiedTabs() { 2631 return _tabTiedAct->isChecked(); 2632 } 2633 2634 void MainWindow::readSettings() { 2635 #if defined(__QNX__) || defined(__ANDROID__) 2636 // There is only one size we want on mobile platforms - full screen! 2637 setWindowState(Qt::WindowFullScreen); 2638 #else 2639 QByteArray geo = _settings.value("geometry").toByteArray(); 2640 if (!geo.isEmpty()) { 2641 restoreGeometry(geo); 2642 } else { 2643 setGeometry(50, 50, 800, 600); 2644 } 2645 #endif // defined(__QNX__) || defined(__ANDROID__) 2646 2647 restoreState(_settings.value("toolbarState").toByteArray()); 2648 _tabTiedAct->setChecked(_settings.value("tieTabs").toBool()); 2649 2650 // read default curve color and set the color sequence. 2651 int color_offset = dialogDefaults().value("curves/default_color", 0).toInt(); 2652 ColorSequence::self().setOffset(color_offset); 2653 } 2654 2655 2656 void MainWindow::writeSettings() { 2657 _settings.setValue("geometry", saveGeometry()); 2658 _settings.setValue("toolbarState", saveState()); 2659 _settings.setValue("tieTabs", _tabTiedAct->isChecked()); 2660 } 2661 2662 void MainWindow::setWidgetFlags(QWidget* widget) 2663 { 2664 if (widget) { 2665 // Make sure the dialog gets maximize and minimize buttons under Windows 2666 widget->QWidget::setWindowFlags((Qt::WindowFlags) Qt::Dialog | Qt::WindowMinimizeButtonHint | Qt::WindowMaximizeButtonHint 2667 #if QT_VERSION >= 0x040500 2668 | Qt::WindowCloseButtonHint 2669 #endif 2670 ); 2671 } 2672 } 2673 2674 void MainWindow::dragEnterEvent(QDragEnterEvent *event) 2675 { 2676 if (event->mimeData()->hasUrls()) { 2677 event->acceptProposedAction(); 2678 } 2679 } 2680 2681 2682 void MainWindow::dropEvent(QDropEvent *event) 2683 { 2684 QString path = event->mimeData()->urls().first().toLocalFile(); 2685 if (path.endsWith(QString(".kst"))) { 2686 if (!promptSaveDone()) { // There are things to save => cancel 2687 event->ignore(); 2688 return; 2689 } 2690 openFile(path); 2691 } 2692 else { 2693 showDataWizard(path); // This is not destructive: it only add data, no need to ask for confirmation 2694 } 2695 event->accept(); 2696 } 2697 2698 void MainWindow::cleanUpDataSourceList() { 2699 _doc->objectStore()->cleanUpDataSourceList(); 2700 } 2701 2702 #if defined(__QNX__) 2703 bool MainWindow::eventFilter(QObject *obj, QEvent *event) { 2704 if (!qApp->activeWindow()) { 2705 activateWindow(); 2706 } 2707 if (event->type() == QEvent::KeyPress) { 2708 QKeyEvent *keyEvent = static_cast<QKeyEvent *>(event); 2709 if (keyEvent->key()==Qt::Key_Menu) { // i.e., bezel swipe gesture... 2710 qnxToggleToolbarVisibility(); 2711 } 2712 return false; 2713 } else if (event->type() == QEvent::MouseButtonPress && obj != menuBar()) { 2714 if (_qnxToolbarsVisible) qnxToggleToolbarVisibility(); 2715 update(); 2716 return false; 2717 } else if (event->type() == QEvent::WindowActivate) { 2718 update(); 2719 return false; 2720 } else { 2721 return QObject::eventFilter(obj, event); 2722 } 2723 } 2724 2725 void MainWindow::keyPressEvent(QKeyEvent *event) { 2726 if ((event->type() == QEvent::KeyPress && static_cast<QKeyEvent*>(event)->key() == Qt::Key_Menu)) { 2727 qnxToggleToolbarVisibility(); 2728 } 2729 } 2730 2731 void MainWindow::qnxToggleToolbarVisibility() { 2732 if (_qnxLastToolbarEvent.msecsTo(QDateTime::currentDateTime()) < 100) { 2733 return; // HACK 2734 } 2735 _qnxLastToolbarEvent = QDateTime::currentDateTime(); 2736 menuBar()->setVisible(!_qnxToolbarsVisible); 2737 statusBar()->setVisible(!_qnxToolbarsVisible); 2738 _fileToolBar->setVisible(!_qnxToolbarsVisible); 2739 _editToolBar->setVisible(!_qnxToolbarsVisible); 2740 _toolsToolBar->setVisible(!_qnxToolbarsVisible); 2741 _rangeToolBar->setVisible(!_qnxToolbarsVisible); 2742 _modeToolBar->setVisible(!_qnxToolbarsVisible); 2743 _plotLayoutToolBar->setVisible(!_qnxToolbarsVisible); 2744 _annotationToolBar->setVisible(!_qnxToolbarsVisible); 2745 _qnxToolbarsVisible = !_qnxToolbarsVisible; 2746 } 2747 #endif 2748 2749 } 2750 2751 // vim: ts=2 sw=2 et