14#include <QApplication>
15#include <QCoreApplication>
16#include <QDesktopWidget>
31#include "Application.h"
33#include "IException.h"
35#include "Preference.h"
36#include "ProgramLauncher.h"
40#include "SessionLog.h"
41#include "UserInterface.h"
65 Display *xDisplay = XOpenDisplay(NULL);
67 std::cerr <<
"cannot connect to X server...\n\n"
68 "Do you have an X server running?\n\n"
70 " If you are trying to run this program remotely using ssh, then "
71 "did you enable X11 forwarding?\n\n"
72 "If the possible causes cited above have been ruled out and this "
73 "problem persists, then check your X settings or contact your "
74 "system administrator.\n\n";
79 XCloseDisplay(xDisplay);
89 PvlGroup &uiPref = Preference::Preferences().findGroup(
"UserInterface");
94 setlocale(LC_ALL,
"en_US");
96 QApplication::setQuitOnLastWindowClosed(
true);
97 QApplication::setApplicationName(
FileName(argv[0]).baseName());
104 QString style = uiPref[
"GuiStyle"];
105 QApplication::setStyle(style);
110 QString fontString = uiPref[
"GuiFontName"];
111 QFont font = QFont(fontString);
114 int pointSize = uiPref[
"GuiFontSize"];
115 font.setPointSize(pointSize);
118 QApplication::setFont(font);
135 QWidget::setWindowTitle(QApplication::applicationName());
138 for(
int group = 0; group < ui.
NumGroups(); group++) {
139 for(
int param = 0; param < ui.
NumParams(group); param++) {
140 p_parameters.push_back(AddParameter(ui, group, param));
145 for(
int p = 0; p < (int)p_parameters.size(); p++) {
153 p_scrollLayout->addStretch(1);
157 p_progressBar->setMinimum(0);
158 p_progressBar->setMaximum(100);
159 p_progressBar->setValue(0);
160 p_progressBar->setMinimumWidth(200);
162 p_statusText =
new QLabel(
"Ready");
164 statusBar()->setSizeGripEnabled(
true);
165 statusBar()->addWidget(p_progressBar, 0);
166 statusBar()->addWidget(p_statusText, 3);
176 for(
unsigned int i = 0; i < p_parameters.size(); i++) {
177 delete p_parameters[i];
180 p_parameters.clear();
184 void Gui::CreateAreas() {
186 QSplitter *split =
new QSplitter(Qt::Vertical,
this);
189 p_scrollArea =
new QScrollArea();
190 p_scrollWidget =
new QWidget();
191 p_scrollLayout =
new QVBoxLayout;
192 p_scrollWidget->setLayout(p_scrollLayout);
193 p_scrollArea->setWidget(p_scrollWidget);
194 p_scrollArea->setWidgetResizable(
true);
197 int height = QApplication::desktop()->height();
201 p_log->setMinimumHeight(10);
202 p_log->resize(p_log->width(), 250);
204 split->addWidget(p_scrollArea);
205 split->addWidget(p_log);
206 split->setChildrenCollapsible(
false);
207 split->setStretchFactor(0, 3);
208 split->setStretchFactor(1, 0);
209 setCentralWidget(split);
210 resize(720, (
int)(height / 2) + 350);
213 p_processAction = CreateProcessAction();
214 p_stopAction = CreateStopAction();
215 p_exitAction = CreateExitAction();
217 p_previousHistoryAction = CreatePreviousHistoryAction();
218 p_nextHistoryAction = CreateNextHistoryAction();
219 p_resetAction = CreateResetAction();
221 p_saveLogAction = CreateSaveLogAction();
222 p_clearLogAction = CreateClearLogAction();
224 QAction *whatsThisAction = CreateWhatsThisAction();
227 QMenu *fileMenu = menuBar()->addMenu(
"&File");
228 fileMenu->addAction(p_processAction);
229 fileMenu->addAction(p_stopAction);
230 fileMenu->addAction(p_exitAction);
233 QMenu *optionsMenu = menuBar()->addMenu(
"&Options");
234 optionsMenu->addAction(p_resetAction);
235 optionsMenu->addAction(p_previousHistoryAction);
236 optionsMenu->addAction(p_nextHistoryAction);
237 optionsMenu->addAction(p_saveLogAction);
238 optionsMenu->addAction(p_clearLogAction);
241 QToolBar *tb = addToolBar(
"Controls");
242 tb->setIconSize(QSize(22, 22));
243 tb->addAction(p_processAction);
244 tb->addAction(p_stopAction);
245 tb->addAction(p_exitAction);
248 tb->addAction(p_previousHistoryAction);
249 tb->addAction(p_nextHistoryAction);
250 tb->addAction(p_resetAction);
253 tb->addAction(p_saveLogAction);
254 tb->addAction(p_clearLogAction);
257 tb->addAction(whatsThisAction);
260 showControls->setText(
"Controls");
261 showControls->setCheckable(
true);
262 connect(showControls, SIGNAL(toggled(
bool)), tb, SLOT(setVisible(
bool)));
264 tb->installEventFilter(
this);
268 addToolBar(Qt::BottomToolBarArea, tb);
269 tb->setIconSize(QSize(22, 22));
270 tb->setAllowedAreas(Qt::BottomToolBarArea);
271 p_commandLineEdit =
new QLineEdit(tb);
272 p_commandLineEdit->setReadOnly(
true);
273 tb->addWidget(p_commandLineEdit);
275 showCommandLine->setText(
"Command Line");
276 showCommandLine->setCheckable(
true);
277 connect(showCommandLine, SIGNAL(toggled(
bool)), tb, SLOT(setVisible(
bool)));
281 QMenu *viewMenu = menuBar()->addMenu(
"&View");
282 viewMenu->addAction(showControls);
283 viewMenu->addAction(showCommandLine);
284 showControls->setChecked(
true);
285 showCommandLine->setChecked(
true);
288 QMenu *helpMenu = menuBar()->addMenu(
"&Help");
289 helpMenu->addAction(whatsThisAction);
292 aboutProgram->setMenuRole(QAction::AboutRole);
293 aboutProgram->setText(
"About this program");
294 aboutProgram->setShortcut(Qt::CTRL + Qt::Key_H);
295 helpMenu->addAction(aboutProgram);
296 connect(aboutProgram, SIGNAL(triggered(
bool)),
this, SLOT(AboutProgram()));
299 aboutIsis->setMenuRole(QAction::NoRole);
300 aboutIsis->setText(
"About Isis");
301 aboutIsis->setShortcut(Qt::CTRL + Qt::Key_I);
302 helpMenu->addAction(aboutIsis);
303 connect(aboutIsis, SIGNAL(triggered(
bool)),
this, SLOT(AboutIsis()));
308 QAction *Gui::CreateProcessAction() {
310 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
311 processAction->setIcon(QPixmap(baseDir +
"/guiRun.png"));
312 processAction->setText(
"&Run");
313 processAction->setToolTip(
"Run");
314 QString processActionWhatsThisText =
"<p><b>Function: </b> \
315 Runs the application with the current parameters</p> \
316 <p><b>Shortcut: </b> Ctrl+R</p>";
317 processAction->setShortcut(Qt::CTRL + Qt::Key_R);
318 processAction->setWhatsThis(processActionWhatsThisText);
320 connect(processAction, SIGNAL(triggered(
bool)),
this, SLOT(
StartProcess()));
322 return processAction;
336 p_processAction->setEnabled(
false);
344 for(
int p = 0; p < (int)p_parameters.size(); p++) {
348 QString value = param.Value().simplified().trimmed();
349 if(value.length() > 0) {
361 Isis::SessionLog::TheLog(
true);
362 QApplication::setOverrideCursor(Qt::WaitCursor);
364 QApplication::restoreOverrideCursor();
365 Isis::iApp->FunctionCleanup();
368 for(
int p = 0; p < (int)p_parameters.size(); p++) {
377 QApplication::restoreOverrideCursor();
382 Isis::iApp->FunctionError(e);
391 p_processAction->setEnabled(
true);
395 QAction *Gui::CreateExitAction() {
398 exitAction->setIcon(QPixmap(baseDir +
"/guiExit.png"));
399 exitAction->setText(
"&Exit");
400 exitAction->setToolTip(
"Exit");
401 QString exitWhatsThisText =
"<p><b>Function: </b> \
402 Closes the program window </p> <p><b>Shortcut: </b> Ctrl+Q</p>";
403 exitAction->setWhatsThis(exitWhatsThisText);
404 exitAction->setShortcut(Qt::CTRL + Qt::Key_Q);
405 connect(exitAction, SIGNAL(triggered()), qApp, SLOT(quit()));
410 QAction *Gui::CreateResetAction() {
412 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
413 resetAction->setIcon(QPixmap(baseDir +
"/guiReset.png"));
414 resetAction->setText(
"&Reset");
415 resetAction->setToolTip(
"Reset parameters");
416 QString resetWhatsThisText =
"<p><b>Function: </b> \
417 Resets the application parameters to their default values</p> \
418 <p><b>Shortcut: </b> F3</p>";
419 resetAction->setWhatsThis(resetWhatsThisText);
420 resetAction->setShortcut(Qt::Key_F3);
421 connect(resetAction, SIGNAL(triggered()),
this, SLOT(
ResetParameters()));
427 QAction *Gui::CreateStopAction() {
428 QAction *stopAction =
new QAction(
this);
429 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
430 stopAction->setIcon(QPixmap(baseDir +
"/guiStop.png"));
431 stopAction->setText(
"&Stop");
432 stopAction->setToolTip(
"Stop");
433 QString stopWhatsThisText =
"<p><b>Function: </b> \
434 Stops the application from running</p> \
435 <p><b>Shortcut: </b> Ctrl+E</p>";
436 stopAction->setShortcut(Qt::CTRL + Qt::Key_E);
437 stopAction->setWhatsThis(stopWhatsThisText);
438 connect(stopAction, SIGNAL(triggered()),
this, SLOT(
StopProcessing()));
444 QAction *Gui::CreateSaveLogAction() {
445 QAction *saveLogAction =
new QAction(
this);
446 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
447 saveLogAction->setIcon(QPixmap(baseDir +
"/guiSaveLog.png"));
448 saveLogAction->setText(
"&Save Log...");
449 saveLogAction->setToolTip(
"Save log");
450 QString saveWhatsThisText =
"<p><b>Function: </b> Saves the information \
451 currently in the log area to a file <p><b>Shortcut: </b> Ctrl+S</p>";
452 saveLogAction->setWhatsThis(saveWhatsThisText);
453 saveLogAction->setShortcut(Qt::CTRL + Qt::Key_S);
454 connect(saveLogAction, SIGNAL(triggered(
bool)), p_log, SLOT(Save()));
456 return saveLogAction;
460 QAction *Gui::CreateClearLogAction() {
461 QAction *clearlogAction =
new QAction(
this);
462 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
463 clearlogAction->setIcon(QPixmap(baseDir +
"/guiClearLog.png"));
464 clearlogAction->setText(
"&Clear Log");
465 clearlogAction->setToolTip(
"Clear log");
466 QString clearWhatsThisText =
"<p><b>Function: </b>Clears all information \
467 from the log area at the bottom of the application screen</p> \
468 <p><b>Shortcut: </b> Ctrl+L</p>";
469 clearlogAction->setWhatsThis(clearWhatsThisText);
470 clearlogAction->setShortcut(Qt::CTRL + Qt::Key_L);
471 connect(clearlogAction, SIGNAL(triggered(
bool)), p_log, SLOT(Clear()));
473 return clearlogAction;
477 QAction *Gui::CreatePreviousHistoryAction() {
478 QAction *previousHistoryAction =
new QAction(
this);
479 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
480 previousHistoryAction->setIcon(QPixmap(baseDir +
"/guiPrevHistory.png"));
481 previousHistoryAction->setText(
"&Previous");
482 previousHistoryAction->setToolTip(
"Previous parameters");
483 QString previousWhatsThisText =
"<p><b>Function: </b>Fills in parameter \
484 values using the previous history entry</p> \
485 <p><b>Shortcut: </b> F5</p>";
486 previousHistoryAction->setWhatsThis(previousWhatsThisText);
487 previousHistoryAction->setShortcut(Qt::Key_F5);
488 connect(previousHistoryAction, SIGNAL(triggered()),
this, SLOT(
PreviousHistory()));
490 return previousHistoryAction;
494 QAction *Gui::CreateNextHistoryAction() {
495 QAction *nextHistoryAction =
new QAction(
this);
496 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
497 nextHistoryAction->setIcon(QPixmap(baseDir +
"/guiNextHistory.png"));
498 nextHistoryAction->setText(
"&Next");
499 nextHistoryAction->setToolTip(
"Next parameters");
500 QString nextWhatsThisText =
"<p><b>Function: </b>Fills in parameter \
501 values using the next history entry</p> \
502 <p><b>Shortcut: </b>F6</p>";
503 nextHistoryAction->setWhatsThis(nextWhatsThisText);
504 nextHistoryAction->setShortcut(Qt::Key_F6);
505 connect(nextHistoryAction, SIGNAL(triggered()),
this, SLOT(
NextHistory()));
507 return nextHistoryAction;
511 QAction *Gui::CreateWhatsThisAction() {
512 QAction *action =
new QAction(
this);
513 QString baseDir = FileName(
"$ISISROOT/appdata/images/icons").expanded();
514 action->setIcon(QPixmap(baseDir +
"/contexthelp.png"));
515 action->setText(
"&What's This");
516 action->setToolTip(
"What's This");
517 QString whatsThisText =
"<p><b>Function: </b> Use this to get longer \
518 descriptions of button functions and parameter information</p> \
519 <p><b>Shortcut: </b> Shift+F1</p>";
520 action->setWhatsThis(whatsThisText);
521 action->setShortcut(Qt::SHIFT + Qt::Key_F1);
522 connect(action, SIGNAL(triggered(
bool)),
this, SLOT(WhatsThis()));
528 GuiParameter *Gui::AddParameter(Isis::UserInterface &ui,
int group,
int param) {
530 QGridLayout *gridLayout = NULL;
531 if(!p_grids.contains(ui.
GroupName(group))) {
533 QGroupBox *groupBox =
new QGroupBox(ui.
GroupName(group));
534 p_scrollLayout->addWidget(groupBox);
535 groupBox->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Fixed);
536 groupBox->setAlignment(Qt::AlignHCenter);
539 gridLayout =
new QGridLayout;
540 gridLayout->setColumnStretch(0, 0);
541 gridLayout->setColumnStretch(1, 0);
542 gridLayout->setColumnMinimumWidth(1, 10);
543 gridLayout->setColumnStretch(2, 10);
544 groupBox->setLayout(gridLayout);
545 p_grids[ui.
GroupName(group)] = gridLayout;
549 gridLayout = p_grids[ui.
GroupName(group)];
552 GuiParameter *p = GuiParameterFactory::Create(gridLayout, ui, group, param);
554 if (p->Type() == GuiParameter::ListWidget || p->Type() == GuiParameter::ComboWidget ||
555 p->Type() == GuiParameter::BooleanWidget) {
559 connect(p, SIGNAL(HelperTrigger(
const QString &)),
566 p_statusText->setText(text);
567 qApp->processEvents();
572 p_progressBar->setValue(percent);
573 qApp->processEvents();
588 QString m = QString(message).replace(
"\n",
"<br>");
591 if(message.contains(
"[") &&
592 message.contains(
"]") &&
593 (message.indexOf(
"[") < message.indexOf(
"]"))) {
596 while(m.indexOf(
"[", indx) != -1) {
597 m.insert(m.indexOf(
"[", indx) + 1,
"<font color=#ff0000>");
598 m.insert(m.indexOf(
"]", indx),
"</font>");
599 indx = m.indexOf(
"]", indx) + 1;
608 int status = QMessageBox::warning(
this,
611 "Ok",
"Abort",
"", 0, 1);
612 p_errorString.clear();
623 if(e->type() == QEvent::Enter) {
624 if(p_processAction->isEnabled()) {
634 if(p_processAction->isEnabled())
return;
637 switch(QMessageBox::information(
this,
639 QString(
"Program suspended, choose to ") +
640 QString(
"continue processing, stop ") +
641 QString(
"processing or exit the program"),
662 qApp->processEvents();
670 for(
int p = 0; p < (int)p_parameters.size(); p++) {
676 for(
int p = 0; p < (int)p_parameters.size(); p++) {
703 if(p_historyEntry < -1) {
705 QApplication::beep();
709 if(p_historyEntry == -1) {
723 QApplication::beep();
734 QString msg =
"A corrupt parameter history file [" + progHist.
expanded() +
735 "] has been detected. Please fix or remove this file";
745 for(
int i = 0; i < hist.
groups(); i++) {
750 if(p_historyEntry == entries) {
751 p_historyEntry = entries - 1;
752 QApplication::beep();
756 int useEntry = entries - p_historyEntry - 1;
763 for (
int k = 0; k < up.
keywords(); k++) {
764 QString key = up[k].
name();
768 if (up[k].size() > 1) {
770 for (
int i = 0; i < up[k].size(); i++) {
771 QString newVal = up[k][i];
772 if (newVal.contains(
",")) {
773 newVal =
'"' + newVal +
'"';
775 if (i == up[k].size() - 1) {
779 val += newVal +
", ";
785 QString newVal = up[k];
792 for(
unsigned int p = 0; p < p_parameters.size(); p++) {
799 p_historyEntry = entries - 1;
800 QApplication::beep();
810 for(
unsigned int p = 0; p < p_parameters.size(); p++) {
816 for(
unsigned int p = 0; p < p_parameters.size(); p++) {
818 std::vector<QString> excludeList = param.
Exclusions();
819 for(
int i = 0; i < (int)excludeList.size(); i++) {
820 for(
unsigned int e = 0; e < p_parameters.size(); e++) {
822 if(exclude.
Name() != excludeList[i])
continue;
823 exclude.
SetEnabled(
false, (param.Type()==GuiParameter::ComboWidget));
832 for(
int p = 0; p < (int)p_parameters.size(); p++) {
836 QString name = param.
Name().toLower();
839 QString value = param.Value();
840 if(param.Type() == GuiParameter::StringWidget) {
841 if(value.contains(
" ")) {
842 cline +=
"\"" + value +
"\"";
848 else if(param.Type() == GuiParameter::FileNameWidget ||
849 param.Type() == GuiParameter::CubeWidget) {
853 value = value.toLower();
858 p_commandLineEdit->setText(cline);
863 for(
unsigned int p = 0; p < p_parameters.size(); p++) {
870 void Gui::WhatsThis() {
871 QWhatsThis::enterWhatsThisMode();
875 void Gui::AboutIsis() {
876 Isis::PvlGroup &uig = Isis::Preference::Preferences().findGroup(
"UserInterface");
877#if defined(__linux__)
878 QString command = (QString) uig[
"GuiHelpBrowser"] +
879 " http://isis.astrogeology.usgs.gov >> /dev/null &";
880#elif defined(__APPLE__)
881 QString command =
"open -a" + (QString) uig[
"GuiHelpBrowser"] +
882 " http://isis.astrogeology.usgs.gov >> /dev/null &";
888 void Gui::AboutProgram() {
889 Isis::PvlGroup &uig = Isis::Preference::Preferences().
findGroup(
"UserInterface");
890#if defined(__linux__)
891 QString command = (QString) uig[
"GuiHelpBrowser"] +
892 " http://isis.astrogeology.usgs.gov/Application/presentation/Tabbed/" +
895#elif defined(__APPLE__)
896 QString command =
"open -a" + (QString) uig[
"GuiHelpBrowser"] +
897 " http://isis.astrogeology.usgs.gov/Application/presentation/Tabbed/" +
906 p_processAction->setEnabled(
false);
911 for(
int p = 0; p < (int)p_parameters.size(); p++) {
915 QString value = param.Value().simplified().trimmed();
916 if(value.length() > 0) {
923 void *ptr = Isis::iApp->GetGuiHelper(funct);
925 helper = (void ( *)())ptr;
929 Isis::iApp->GuiReportError(e);
934 p_processAction->setEnabled(
true);
static UserInterface & GetUserInterface()
Returns the UserInterface object.
File name manipulation and expansion.
bool fileExists() const
Returns true if the file exists; false otherwise.
QString expanded() const
Returns a QString of the full file name including the file path, excluding the attributes.
Gui for Isis Applications.
void StopProcessing()
The user pressed the stop button ... see what they want to do.
void ResetParameters()
Reset the parameters fields to the defaults.
void InvokeHelper(const QString &funct)
Activate helper buttons.
int Exec(void(*funct)())
Start the Gui and enter the main loop This routine only returns when the program is ready to exit.
void Log(const QString &text)
Write text to the gui log.
void ProgressText(const QString &text)
Change progress text.
int ShowWarning()
Show an error message and return if the user wants to continue/abort.
void UpdateParameters()
Update Parameters.
void NextHistory()
Goto the next history entry.
void UpdateExclusions()
Grey out parameters that should be excluded for radio buttons and checkboxes.
void PreviousHistory()
Goto the previous history entry.
void StartProcess()
The user pressed the go button.
void Progress(int percent)
Update the progress bar.
void LoadMessage(const QString &message)
Add more information to the error message.
bool eventFilter(QObject *o, QEvent *e)
Reset the Progress bar when the user moves the mouse onto the toolbar.
Gui(Isis::UserInterface &ui)
Constructor.
static Gui * p_gui
Singleton.
void UpdateHistory()
Changed the parameters based on the history pointer.
bool ProcessEvents()
Let the event loop have some time to see if we need to cancel.
void UpdateCommandLine()
Update the command line toolbar.
static void checkX11()
check to see if X is available
void Update()
Update the value on the GUI with the value in the UI.
bool IsEnabled() const
Is the parameter enabled.
virtual bool IsModified()
Return if the parameter value is different from the default value.
virtual std::vector< QString > Exclusions()
Return list of current exclusions.
void SetEnabled(bool enabled, bool isParentCombo=false)
Enable or disable the parameter.
QString Name() const
Return the name of the parameter.
QString toString() const
Returns a string representation of this exception.
Reads user preferences from a data file.
static void RunSystemCommand(QString commandLine)
This runs arbitrary system commands.
bool hasKeyword(const QString &name) const
Check to see if a keyword exists.
bool isNamed(const QString &match) const
Returns whether the given string is equal to the container name or not.
int keywords() const
Returns the number of keywords contained in the PvlContainer.
QString name() const
Returns the container name.
Contains multiple PvlContainers.
Container for cube-like labels.
void read(const QString &file)
Loads PVL information from a stream.
PvlGroup & group(const int index)
Return the group at the specified index.
int groups() const
Returns the number of groups contained.
@ Traverse
Search child objects.
PvlGroupIterator findGroup(const QString &name, PvlGroupIterator beg, PvlGroupIterator end)
Find a group with the specified name, within these indexes.
Command Line and Xml loader, validation, and access.
void SaveHistory()
Saves the user parameter information in the history of the program for later use.
int NumGroups() const
Returns the number of groups found in the XML.
int NumParams(const int &) const
Returns the number of parameters in a group.
QString GroupName(const int &group) const
Returns the group name of group[index].
QString ProgramName() const
Returns the Program name.
void Clear(const QString ¶mName)
Clears the value(s) in the named parameter.
void VerifyAll()
Verify all parameters.
void PutAsString(const QString ¶mName, const QString &value)
Allows the insertion of a value for any parameter.
This is free and unencumbered software released into the public domain.