13 #include <QMessageBox> 17 #include <QTableWidget> 18 #include <QTableWidgetItem> 27 #include "ControlPointEdit.h" 30 #include "MainWindow.h" 31 #include "MatchToolDeletePointDialog.h" 32 #include "MatchToolNewPointDialog.h" 36 #include "PvlEditDialog.h" 41 #include "ViewportMainWindow.h" 62 m_newPointDialog = NULL;
76 m_leftReference = NULL;
77 m_leftMeasureType = NULL;
78 m_leftGoodness = NULL;
79 m_rightReference = NULL;
80 m_rightMeasureType = NULL;
81 m_rightGoodness = NULL;
82 m_lockLeftMeasure = NULL;
83 m_ignoreLeftMeasure = NULL;
84 m_lockRightMeasure = NULL;
85 m_ignoreRightMeasure = NULL;
89 m_rightMeasure = NULL;
90 m_templateModified =
false;
91 m_measureWindow = NULL;
92 m_measureTable = NULL;
102 connect(
this, SIGNAL(toolActivated()),
this, SLOT(activateTool()));
108 if (parentMainWindow) {
109 connect(parent, SIGNAL(closeWindow()),
this, SLOT(
exiting()));
117 MatchTool::~MatchTool () {
123 delete m_pointEditor;
124 m_pointEditor = NULL;
125 delete m_newPointDialog;
126 m_newPointDialog = NULL;
129 delete m_leftMeasure;
130 m_leftMeasure = NULL;
131 delete m_rightMeasure;
132 m_rightMeasure = NULL;
168 m_matchTool->setWindowTitle(
"Match Tool");
169 m_matchTool->setObjectName(
"MatchTool");
170 connect(m_matchTool, SIGNAL(destroyed(
QObject *)),
this, SLOT(clearEditPoint()));
179 connect(
this, SIGNAL(newControlNetwork(
ControlNet *)),
180 m_pointEditor, SIGNAL(newControlNetwork(
ControlNet *)));
184 connect(
this, SIGNAL(measureChanged()),
187 m_savePoint =
new QPushButton (
"Save Point");
188 m_savePoint->setShortcut(Qt::Key_P);
189 m_savePoint->setToolTip(
"Save the edit control point to the control network. " 190 "<strong>Shortcut: P</strong>");
191 m_savePoint->setWhatsThis(
"Save the edit control point to the control " 192 "network which is loaded into memory in its entirety. " 193 "When a control point is selected for editing, " 194 "a copy of the point is made so that the original control " 195 "point remains in the network.");
196 m_saveDefaultPalette = m_savePoint->palette();
197 connect (m_savePoint,SIGNAL(clicked()),
this,SLOT(
savePoint()));
199 QHBoxLayout * addMeasureLayout =
new QHBoxLayout;
200 addMeasureLayout->addStretch();
201 addMeasureLayout->addWidget(m_savePoint);
204 m_cnetFileNameLabel =
new QLabel(
"Control Network: " + m_cnetFileName);
205 m_cnetFileNameLabel->setToolTip(
"Name of opened control network file.");
206 m_cnetFileNameLabel->setWhatsThis(
"Name of opened control network file.");
208 m_templateFileNameLabel =
new QLabel(
"Template File: " +
209 m_pointEditor->templateFileName());
210 m_templateFileNameLabel->setToolTip(
"Sub-pixel registration template File.");
214 m_templateFileNameLabel->setWhatsThis(
"FileName of the sub-pixel " 215 "registration template. Refer to $ISISROOT/doc/documents/" 216 "PatternMatch/PatternMatch.html for a description of the " 217 "contents of this file.");
219 QVBoxLayout * centralLayout =
new QVBoxLayout;
221 centralLayout->addWidget(m_cnetFileNameLabel);
222 centralLayout->addWidget(m_templateFileNameLabel);
224 centralLayout->addStretch();
225 centralLayout->addWidget(m_pointEditor);
226 centralLayout->addLayout(addMeasureLayout);
228 centralWidget->setLayout(centralLayout);
230 QScrollArea *scrollArea =
new QScrollArea();
231 scrollArea->setObjectName(
"MatchToolScroll");
232 scrollArea->setWidget(centralWidget);
233 scrollArea->setWidgetResizable(
true);
234 centralWidget->adjustSize();
235 m_matchTool->setCentralWidget(scrollArea);
239 connect(
this, SIGNAL(editPointChanged()),
249 QHBoxLayout * measureLayout =
new QHBoxLayout;
253 QVBoxLayout * groupBoxesLayout =
new QVBoxLayout;
255 groupBoxesLayout->addStretch();
256 groupBoxesLayout->addLayout(measureLayout);
259 groupBoxesWidget->setLayout(groupBoxesLayout);
263 QSplitter * topSplitter =
new QSplitter;
264 topSplitter->addWidget(groupBoxesWidget);
265 topSplitter->addWidget(m_templateEditorWidget);
266 topSplitter->setStretchFactor(0, 4);
267 topSplitter->setStretchFactor(1, 3);
269 m_templateEditorWidget->hide();
279 m_ptIdValue =
new QLabel;
280 m_numMeasures =
new QLabel;
281 QVBoxLayout * leftLayout =
new QVBoxLayout;
282 leftLayout->addWidget(m_ptIdValue);
283 leftLayout->addWidget(m_numMeasures);
286 m_lockPoint =
new QCheckBox(
"Edit Lock Point");
287 connect(m_lockPoint, SIGNAL(clicked(
bool)),
this, SLOT(
setLockPoint(
bool)));
288 m_ignorePoint =
new QCheckBox(
"Ignore Point");
289 connect(m_ignorePoint, SIGNAL(clicked(
bool)),
291 connect(
this, SIGNAL(ignorePointChanged()), m_ignorePoint, SLOT(toggle()));
293 QVBoxLayout * rightLayout =
new QVBoxLayout;
294 rightLayout->addWidget(m_lockPoint);
295 rightLayout->addWidget(m_ignorePoint);
297 QHBoxLayout * mainLayout =
new QHBoxLayout;
298 mainLayout->addLayout(leftLayout);
299 mainLayout->addStretch();
300 mainLayout->addLayout(rightLayout);
303 QGroupBox * groupBox =
new QGroupBox(
"Control Point");
304 groupBox->setLayout(mainLayout);
314 m_leftCombo->view()->installEventFilter(
this);
315 m_leftCombo->setToolTip(
"Choose left control measure");
316 m_leftCombo->setWhatsThis(
"Choose left control measure identified by " 318 connect(m_leftCombo, SIGNAL(activated(
int)),
320 m_lockLeftMeasure =
new QCheckBox(
"Edit Lock Measure");
321 connect(m_lockLeftMeasure, SIGNAL(clicked(
bool)),
323 m_ignoreLeftMeasure =
new QCheckBox(
"Ignore Measure");
324 connect(m_ignoreLeftMeasure, SIGNAL(clicked(
bool)),
326 connect(
this, SIGNAL(ignoreLeftChanged()),
327 m_ignoreLeftMeasure, SLOT(toggle()));
328 m_leftReference =
new QLabel();
329 m_leftMeasureType =
new QLabel();
330 m_leftSampShift =
new QLabel();
331 m_leftSampShift->setToolTip(
"Sample shift between apriori and current");
332 m_leftSampShift->setWhatsThis(
"The shift between the apriori sample and " 333 "the current sample. The apriori sample is set " 334 "when creating a new measure.");
335 m_leftLineShift =
new QLabel();
336 m_leftLineShift->setToolTip(
"Line shift between apriori and current");
337 m_leftLineShift->setWhatsThis(
"The shift between the apriori line and " 338 "the current line. The apriori line is set " 339 "when creating a new measure.");
340 m_leftGoodness =
new QLabel();
341 m_leftGoodness->setToolTip(
"Goodness of Fit result from sub-pixel " 343 m_leftGoodness->setWhatsThis(
"Resulting Goodness of Fit from sub-pixel " 345 QVBoxLayout * leftLayout =
new QVBoxLayout;
346 leftLayout->addWidget(m_leftCombo);
347 leftLayout->addWidget(m_lockLeftMeasure);
348 leftLayout->addWidget(m_ignoreLeftMeasure);
349 leftLayout->addWidget(m_leftReference);
350 leftLayout->addWidget(m_leftMeasureType);
351 leftLayout->addWidget(m_leftSampShift);
352 leftLayout->addWidget(m_leftLineShift);
353 leftLayout->addWidget(m_leftGoodness);
355 QGroupBox * leftGroupBox =
new QGroupBox(
"Left Measure");
356 leftGroupBox->setLayout(leftLayout);
375 m_rightCombo->view()->installEventFilter(
this);
379 QShortcut *nextMeasure =
new QShortcut(Qt::Key_PageDown, m_matchTool);
381 QShortcut *prevMeasure =
new QShortcut(Qt::Key_PageUp, m_matchTool);
384 m_rightCombo->setToolTip(
"Choose right control measure. " 385 "<strong>Shorcuts: PageUp/PageDown</strong>");
386 m_rightCombo->setWhatsThis(
"Choose right control measure identified by " 388 "Note: PageUp selects previous measure; " 389 "PageDown selects next measure.");
390 connect(m_rightCombo, SIGNAL(activated(
int)),
392 m_lockRightMeasure =
new QCheckBox(
"Edit Lock Measure");
393 connect(m_lockRightMeasure, SIGNAL(clicked(
bool)),
395 m_ignoreRightMeasure =
new QCheckBox(
"Ignore Measure");
396 connect(m_ignoreRightMeasure, SIGNAL(clicked(
bool)),
398 connect(
this, SIGNAL(ignoreRightChanged()),
399 m_ignoreRightMeasure, SLOT(toggle()));
400 m_rightReference =
new QLabel();
401 m_rightMeasureType =
new QLabel();
402 m_rightSampShift =
new QLabel();
403 m_rightSampShift->setToolTip(m_leftSampShift->toolTip());
404 m_rightSampShift->setWhatsThis(m_leftSampShift->whatsThis());
405 m_rightLineShift =
new QLabel();
406 m_rightLineShift->setToolTip(m_leftLineShift->toolTip());
407 m_rightLineShift->setWhatsThis(m_leftLineShift->whatsThis());
408 m_rightGoodness =
new QLabel();
409 m_rightGoodness->setToolTip(m_leftGoodness->toolTip());
410 m_rightGoodness->setWhatsThis(m_leftGoodness->whatsThis());
413 QVBoxLayout * rightLayout =
new QVBoxLayout;
414 rightLayout->addWidget(m_rightCombo);
415 rightLayout->addWidget(m_lockRightMeasure);
416 rightLayout->addWidget(m_ignoreRightMeasure);
417 rightLayout->addWidget(m_rightReference);
418 rightLayout->addWidget(m_rightMeasureType);
419 rightLayout->addWidget(m_rightSampShift);
420 rightLayout->addWidget(m_rightLineShift);
421 rightLayout->addWidget(m_rightGoodness);
423 QGroupBox * rightGroupBox =
new QGroupBox(
"Right Measure");
424 rightGroupBox->setLayout(rightLayout);
426 return rightGroupBox;
435 toolBar->addAction(m_openTemplateFile);
436 toolBar->addSeparator();
437 toolBar->addAction(m_saveTemplateFile);
438 toolBar->addAction(m_saveTemplateFileAs);
440 m_templateEditor =
new QTextEdit;
441 connect(m_templateEditor, SIGNAL(textChanged()),
this,
444 QVBoxLayout *mainLayout =
new QVBoxLayout;
445 mainLayout->addWidget(toolBar);
446 mainLayout->addWidget(m_templateEditor);
448 m_templateEditorWidget =
new QWidget;
449 m_templateEditorWidget->setLayout(mainLayout);
463 "Save Control Network ...",
465 m_saveNet->setShortcut(Qt::CTRL + Qt::Key_S);
466 m_saveNet->setToolTip(
"Save current control network");
467 m_saveNet->setStatusTip(
"Save current control network");
468 QString whatsThis =
"<b>Function:</b> Saves the current <i>" 469 "control network</i>";
470 m_saveNet->setWhatsThis(whatsThis);
471 connect(m_saveNet, SIGNAL(triggered()),
this, SLOT(
saveNet()));
474 "Save Control Network &As...",
476 m_saveAsNet->setToolTip(
"Save current control network to chosen file");
477 m_saveAsNet->setStatusTip(
"Save current control network to chosen file");
478 whatsThis =
"<b>Function:</b> Saves the current <i>" 479 "control network</i> under chosen filename";
480 m_saveAsNet->setWhatsThis(whatsThis);
481 connect(m_saveAsNet, SIGNAL(triggered()),
this, SLOT(
saveAsNet()));
486 m_closeMatchTool->setToolTip(
"Close this window");
487 m_closeMatchTool->setStatusTip(
"Close this window");
488 m_closeMatchTool->setShortcut(Qt::ALT + Qt::Key_F4);
489 whatsThis =
"<b>Function:</b> Closes the Match Tool window for this point " 490 "<p><b>Shortcut:</b> Alt+F4 </p>";
491 m_closeMatchTool->setWhatsThis(whatsThis);
492 connect(m_closeMatchTool, SIGNAL(triggered()), m_matchTool, SLOT(close()));
495 "&View/edit registration template",
497 m_showHideTemplateEditor->setCheckable(
true);
498 m_showHideTemplateEditor->setToolTip(
"View and/or edit the registration template");
499 m_showHideTemplateEditor->setStatusTip(
"View and/or edit the registration template");
500 whatsThis =
"<b>Function:</b> Displays the curent registration template. " 501 "The user may edit and save changes under a chosen filename.";
502 m_showHideTemplateEditor->setWhatsThis(whatsThis);
503 connect(m_showHideTemplateEditor, SIGNAL(triggered()),
this,
504 SLOT(showHideTemplateEditor()));
507 "Save registration chips",
509 m_saveChips->setToolTip(
"Save registration chips");
510 m_saveChips->setStatusTip(
"Save registration chips");
511 whatsThis =
"<b>Function:</b> Save registration chips to file. " 512 "Each chip: pattern, search, fit will be saved to a separate file.";
513 m_saveChips->setWhatsThis(whatsThis);
514 connect(m_saveChips, SIGNAL(triggered()),
this, SLOT(
saveChips()));
517 "&Open registration template",
519 m_openTemplateFile->setToolTip(
"Set registration template");
520 m_openTemplateFile->setStatusTip(
"Set registration template");
521 whatsThis =
"<b>Function:</b> Allows user to select a new file to set as " 522 "the registration template";
523 m_openTemplateFile->setWhatsThis(whatsThis);
524 connect(m_openTemplateFile, SIGNAL(triggered()),
this, SLOT(
openTemplateFile()));
527 "&Save template file",
529 m_saveTemplateFile->setToolTip(
"Save the template file");
530 m_saveTemplateFile->setStatusTip(
"Save the template file");
531 m_saveTemplateFile->setWhatsThis(
"Save the registration template file");
532 connect(m_saveTemplateFile, SIGNAL(triggered()),
this,
536 "&Save template as...",
538 m_saveTemplateFileAs->setToolTip(
"Save the template file as");
539 m_saveTemplateFileAs->setStatusTip(
"Save the template file as");
540 m_saveTemplateFileAs->setWhatsThis(
"Save the registration template file as");
541 connect(m_saveTemplateFileAs, SIGNAL(triggered()),
this,
547 m_whatsThis->setShortcut(Qt::SHIFT | Qt::Key_F1);
548 m_whatsThis->setToolTip(
"Activate What's This and click on items on " 549 "user interface to see more information.");
550 connect(m_whatsThis, SIGNAL(triggered()),
this, SLOT(enterWhatsThisMode()));
552 m_showHelp =
new QAction(QPixmap(
toolIconDir() +
"/help-contents.png"),
"Help", m_matchTool);
553 m_showHelp->setToolTip(
"Help");
554 connect(m_showHelp, SIGNAL(triggered()),
this, SLOT(showHelp()));
571 QMenu *fileMenu = m_matchTool->menuBar()->addMenu(
"&File");
572 fileMenu->addAction(m_saveNet);
573 fileMenu->addAction(m_saveAsNet);
574 fileMenu->addAction(m_closeMatchTool);
576 QMenu * regMenu = m_matchTool->menuBar()->addMenu(
"&Registration");
577 regMenu->addAction(m_openTemplateFile);
578 regMenu->addAction(m_showHideTemplateEditor);
579 regMenu->addAction(m_saveChips);
581 QMenu *helpMenu = m_matchTool->menuBar()->addMenu(
"&Help");
582 helpMenu->addAction(m_whatsThis);
586 void MatchTool::createToolBars() {
589 toolBar->setObjectName(
"TemplateEditorToolBar");
590 toolBar->setFloatable(
false);
591 toolBar->addAction(m_saveNet);
592 toolBar->addSeparator();
593 toolBar->addAction(m_showHideTemplateEditor);
594 toolBar->addAction(m_saveChips);
595 toolBar->addAction(m_showHelp);
596 toolBar->addAction(m_whatsThis);
598 m_matchTool->addToolBar(Qt::TopToolBarArea, toolBar);
616 action->setIcon(QPixmap(
toolIconDir()+
"/stock_draw-connector-with-arrows.png"));
617 action->setToolTip(
"Match Tool - Control Point Editor (T)");
618 action->setShortcut(Qt::Key_T);
624 QWidget *MatchTool::createToolBarWidget(QStackedWidget *parent) {
628 QToolButton *openNetButton =
new QToolButton(hbox);
629 openNetButton->setIcon(QPixmap(
toolIconDir() +
"/fileopen.png"));
630 openNetButton->setIconSize(QSize(22,22));
631 openNetButton->setToolTip(
"Open control network");
632 openNetButton->setEnabled(
true);
633 connect(openNetButton, SIGNAL(clicked()),
this, SLOT(openNet()));
635 QToolButton *saveAsNetButton =
new QToolButton(hbox);
636 saveAsNetButton->setDefaultAction(m_saveAsNet);
637 saveAsNetButton->setIconSize(QSize(22,22));
639 QToolButton *saveNetButton =
new QToolButton(hbox);
640 saveNetButton->setDefaultAction(m_saveNet);
641 saveNetButton->setIconSize(QSize(22,22));
643 QToolButton *helpButton =
new QToolButton(hbox);
644 helpButton->setDefaultAction(m_showHelp);
645 helpButton->setIconSize(QSize(22, 22));
647 QHBoxLayout *layout =
new QHBoxLayout;
648 layout->setMargin(0);
649 layout->addWidget(openNetButton);
650 layout->addWidget(saveAsNetButton);
651 layout->addWidget(saveNetButton);
652 layout->addStretch();
653 layout->addWidget(helpButton);
654 hbox->setLayout(layout);
661 void MatchTool::activateTool() {
664 m_controlNet =
new ControlNet();
714 QString serialNumber;
720 catch (IException &e) {
721 serialNumber =
"Unknown";
797 if (*origLeftMeasure == *m_leftMeasure && *origRightMeasure == *m_rightMeasure) {
801 if (m_editPoint->IsIgnored()) {
802 QString message =
"You are saving changes to a measure on an ignored ";
803 message +=
"point. Do you want to set Ignore = False on the point and ";
804 message +=
"both measures?";
805 switch (QMessageBox::question(m_matchTool,
"Match Tool Save Measure",
806 message,
"&Yes",
"&No", 0, 0)) {
810 emit ignorePointChanged();
811 if (m_leftMeasure->IsIgnored()) {
812 m_leftMeasure->SetIgnored(
false);
813 emit ignoreLeftChanged();
815 if (m_rightMeasure->IsIgnored()) {
816 m_rightMeasure->SetIgnored(
false);
817 emit ignoreRightChanged();
825 bool savedAMeasure =
false;
827 bool leftChangeOk = validateMeasureChange(m_leftMeasure);
830 *origLeftMeasure = *m_leftMeasure;
831 savedAMeasure =
true;
833 bool rightChangeOk = validateMeasureChange(m_rightMeasure);
836 *origRightMeasure = *m_rightMeasure;
837 savedAMeasure =
true;
842 *m_leftMeasure = *m_rightMeasure;
845 m_editPoint->
GetId());
853 emit editPointChanged();
874 if (*m == *origMeasure)
return false;
878 QString side =
"right";
891 QString message =
"The " + side +
" measure is editLocked ";
892 message +=
"for editing. Do you want to set EditLock = False for this ";
893 message +=
"measure?";
894 int response = QMessageBox::question(m_matchTool,
"Match Tool Save Measure",
895 message, QMessageBox::Yes | QMessageBox::No);
897 if (response == QMessageBox::Yes) {
898 m->SetEditLock(
false);
899 if (side ==
"left") {
900 m_lockLeftMeasure->setChecked(
false);
903 m_lockRightMeasure->setChecked(
false);
912 if (origMeasure->IsIgnored() && m->IsIgnored()) {
913 QString message =
"The " + side +
"measure is ignored. ";
914 message +=
"Do you want to set Ignore = False on the measure?";
915 switch(QMessageBox::question(m_matchTool,
"Match Tool Save Measure",
916 message,
"&Yes",
"&No", 0, 0)){
919 m->SetIgnored(
false);
920 if (side ==
"left") {
921 emit ignoreLeftChanged();
924 emit ignoreRightChanged();
936 if (m->GetSample() != origMeasure->GetSample() || m->GetLine() != origMeasure->GetLine()) {
937 QString message =
"You are making a change to the reference measure. You ";
938 message +=
"may need to move all of the other measures to match the new ";
939 message +=
" coordinate of the reference measure. Do you really want to ";
940 message +=
" change the reference measure's location? ";
941 switch(QMessageBox::question(m_matchTool,
"Match Tool Save Measure",
942 message,
"&Yes",
"&No", 0, 0)){
954 else if (side ==
"left" && (refMeasure->GetCubeSerialNumber() != m->
GetCubeSerialNumber())) {
956 QString message =
"This control network was created by the <i>coreg</i> program, and the " 957 "reference measure needs to remain the same as what <i>coreg</i> set. " 958 "Therefore, you cannot change which measure is the reference. To " 959 "save this point, move the reference measure (measure in BOLD) back " 961 QMessageBox::information(m_matchTool,
"Cannot change reference", message);
964 QString message =
"This point already contains a reference measure. ";
965 message +=
"Would you like to replace it with the measure on the left?";
966 int response = QMessageBox::question(m_matchTool,
967 "Match Tool Save Measure", message,
968 QMessageBox::Yes | QMessageBox::No,
971 if (response == QMessageBox::Yes) {
975 QString fname = FileName(file).name();
976 int iref = m_leftCombo->findText(fname);
979 QVariant font = m_leftCombo->itemData(iref,Qt::FontRole);
980 m_leftCombo->setItemData(iref,QFont(
"DejaVu Sans", 12, QFont::Bold), Qt::FontRole);
981 iref = m_rightCombo->findText(fname);
982 m_rightCombo->setItemData(iref,QFont(
"DejaVu Sans", 12, QFont::Bold), Qt::FontRole);
985 fname = FileName(file).name();
986 iref = m_leftCombo->findText(fname);
987 m_leftCombo->setItemData(iref,font,Qt::FontRole);
988 iref = m_rightCombo->findText(fname);
989 m_rightCombo->setItemData(iref,font,Qt::FontRole);
998 if (side ==
"left") {
1020 void MatchTool::checkReference() {
1027 QString message =
"This point already contains a reference measure. ";
1028 message +=
"Would you like to replace it with the measure on the left?";
1029 int response = QMessageBox::question(m_matchTool,
1030 "Match Tool Save Measure", message,
1031 QMessageBox::Yes | QMessageBox::No,
1034 if (response == QMessageBox::Yes) {
1038 QString fname = FileName(file).name();
1039 int iref = m_leftCombo->findText(fname);
1042 QVariant font = m_leftCombo->itemData(iref,Qt::FontRole);
1043 m_leftCombo->setItemData(iref,QFont(
"DejaVu Sans", 12, QFont::Bold), Qt::FontRole);
1044 iref = m_rightCombo->findText(fname);
1045 m_rightCombo->setItemData(iref,QFont(
"DejaVu Sans", 12, QFont::Bold), Qt::FontRole);
1048 fname = FileName(file).name();
1049 iref = m_leftCombo->findText(fname);
1050 m_leftCombo->setItemData(iref,font,Qt::FontRole);
1051 iref = m_rightCombo->findText(fname);
1052 m_rightCombo->setItemData(iref,font,Qt::FontRole);
1084 *updatePoint = *m_editPoint;
1088 if (m_controlNet->ContainsPoint(updatePoint->
GetId())) {
1090 p = m_controlNet->GetPoint(QString(updatePoint->
GetId()));
1096 m_controlNet->AddPoint(updatePoint);
1100 m_savePoint->setPalette(m_saveDefaultPalette);
1103 emit editPointChanged();
1105 m_netChanged =
true;
1107 m_pointEditor->refreshChips();
1122 if (m_editPoint == NULL)
return;
1141 if (m_editPoint == NULL)
return;
1145 m_ignorePoint->setChecked(m_editPoint->IsIgnored());
1146 QString message =
"Unable to change Ignored on point. Set EditLock ";
1147 message +=
" to False.";
1148 QMessageBox::critical(m_matchTool,
"Error", message);
1174 if (m_editPoint->IsEditLocked()) {
1175 m_lockLeftMeasure->setChecked(m_leftMeasure->
IsEditLocked());
1176 QMessageBox::warning(m_matchTool,
"Point Locked",
"Point is Edit Locked. You must un-lock point" 1177 " before changing a measure.");
1178 m_lockLeftMeasure->setChecked(m_leftMeasure->
IsEditLocked());
1182 if (m_leftMeasure != NULL) m_leftMeasure->SetEditLock(lock);
1186 if (m_rightMeasure != NULL) {
1188 m_rightMeasure->SetEditLock(lock);
1189 m_lockRightMeasure->setChecked(lock);
1192 emit measureChanged();
1214 if (m_leftMeasure != NULL) m_leftMeasure->SetIgnored(ignore);
1218 if (m_rightMeasure != NULL) {
1220 m_rightMeasure->SetIgnored(ignore);
1221 m_ignoreRightMeasure->setChecked(ignore);
1224 emit measureChanged();
1245 if (m_editPoint->IsEditLocked()) {
1246 m_lockRightMeasure->setChecked(m_rightMeasure->
IsEditLocked());
1247 QMessageBox::warning(m_matchTool,
"Point Locked",
"Point is Edit Locked. You must un-lock point" 1248 " before changing a measure.");
1249 m_lockRightMeasure->setChecked(m_rightMeasure->
IsEditLocked());
1253 if (m_rightMeasure != NULL) m_rightMeasure->SetEditLock(lock);
1256 if (m_leftMeasure != NULL) {
1258 m_leftMeasure->SetEditLock(lock);
1259 m_lockLeftMeasure->setChecked(lock);
1262 emit measureChanged();
1284 if (m_rightMeasure != NULL) m_rightMeasure->SetIgnored(ignore);
1288 if (m_leftMeasure != NULL) {
1290 m_leftMeasure->SetIgnored(ignore);
1291 m_ignoreLeftMeasure->setChecked(ignore);
1294 emit measureChanged();
1299 void MatchTool::openNet() {
1302 if (m_controlNet->GetNumPoints() != 0 && m_netChanged) {
1303 QString message =
"A control net has already been created. Do you want to save before " 1304 "opening a new control net?";
1305 int response = QMessageBox::question(m_matchTool,
"Save current control net?",
1307 QMessageBox::Yes | QMessageBox::No,
1310 if (response == QMessageBox::Yes) {
1313 m_matchTool->setVisible(
false);
1315 delete m_controlNet;
1316 m_controlNet = NULL;
1319 m_newPointDialog = NULL;
1323 m_netChanged =
false;
1325 QApplication::restoreOverrideCursor();
1326 QString filter =
"Control net (*.net *.cnet *.ctl);;";
1327 filter +=
"Pvl file (*.pvl);;";
1328 filter +=
"Text file (*.txt);;";
1329 filter +=
"All (*)";
1330 m_cnetFileName = QFileDialog::getOpenFileName((
QWidget *)parent(),
1331 "Select a control network",
1334 QApplication::setOverrideCursor(Qt::WaitCursor);
1335 if (!m_cnetFileName.isEmpty()) {
1338 m_controlNet =
new ControlNet(m_cnetFileName, &progress);
1340 m_coregReferenceSN =
"";
1341 if (m_controlNet->GetNetworkId() ==
"Coreg") {
1345 m_coregReferenceSN = m_controlNet->GetPoint(0)->GetReferenceSN();
1348 catch (IException &e) {
1349 QApplication::restoreOverrideCursor();
1350 QString message =
"Invalid control network. \n";
1351 message += e.toString();
1352 QMessageBox::critical(m_matchTool,
"Error", message);
1353 m_cnetFileName.clear();
1354 delete m_controlNet;
1355 m_controlNet = NULL;
1359 QApplication::restoreOverrideCursor();
1360 m_matchTool->setWindowTitle(
"Match Tool - Control Network File: " + m_cnetFileName);
1361 m_cnetFileNameLabel->setText(
"Control Network: " + m_cnetFileName);
1374 if (m_cnetFileName.isEmpty()) {
1375 QString message =
"This is a new network, you must select " 1376 "\"Save As\" under the File Menu or on the toolbar.";
1377 QMessageBox::critical(m_matchTool,
"Error", message);
1381 m_controlNet->Write(m_cnetFileName);
1382 m_netChanged =
false;
1385 QMessageBox::critical(m_matchTool, tr(
"Error Writing Control Net"), e.
what());
1402 QString fn = QFileDialog::getSaveFileName(m_matchTool,
1403 "Choose filename to save under",
1405 "Control Files (*.net)");
1410 m_controlNet->Write(fn);
1411 m_netChanged =
false;
1414 QMessageBox::critical(m_matchTool, tr(
"Error Writing Control Net"), e.
what());
1417 m_cnetFileName = fn;
1418 m_matchTool->setWindowTitle(
"Match Tool - Control Network File: " + m_cnetFileName);
1419 m_cnetFileNameLabel->setText(
"Control Network: " + m_cnetFileName);
1459 if (mvp == NULL)
return;
1467 if (s == Qt::LeftButton) {
1469 if (!m_controlNet || m_controlNet->GetNumPoints() == 0) {
1470 QString message =
"No points exist for editing. Create points ";
1471 message +=
"using the right mouse button.";
1472 QMessageBox::warning(m_matchTool,
"Warning", message);
1480 point = m_controlNet->FindClosest(sn, samp, line);
1483 QString message =
"Cannot find point for editing.";
1485 QMessageBox::warning(m_matchTool,
"Warning", message);
1491 else if (s == Qt::MidButton) {
1492 if (!m_controlNet || m_controlNet->GetNumPoints() == 0) {
1493 QString message =
"No points exist for deleting. Create points ";
1494 message +=
"using the right mouse button.";
1495 QMessageBox::warning(m_matchTool,
"Warning", message);
1500 ControlPoint *point = m_controlNet->FindClosest(sn, samp, line);
1502 if (point == NULL) {
1503 QString message =
"No points exist for deleting. Create points ";
1504 message +=
"using the right mouse button.";
1505 QMessageBox::warning(m_matchTool,
"Warning", message);
1511 else if (s == Qt::RightButton) {
1512 if (m_newPointDialog) {
1513 addMeasure(mvp, samp, line);
1521 QString message =
"Cannot create control point.\n\n";
1523 QMessageBox::critical(m_matchTool,
"Error", message);
1536 for (
int i=0; i<point->GetNumMeasures(); i++) {
1542 return missingCubes;
1556 connect(m_newPointDialog, SIGNAL(measuresFinished()),
this, SLOT(doneWithMeasures()));
1557 connect(m_newPointDialog, SIGNAL(newPointCanceled()),
this, SLOT(cancelNewPoint()));
1562 images<<cubeFile.
name();
1564 m_newPointDialog->
setFiles(images);
1565 m_newPointDialog->show();
1569 m_newPointDialog->highlightFile(current);
1588 void MatchTool::addMeasure(
MdiCubeViewport *cvp,
double sample,
double line) {
1592 m_newPointDialog->highlightFile(current);
1593 m_newPointDialog->raise();
1613 void MatchTool::doneWithMeasures() {
1615 m_lastUsedPointId = m_newPointDialog->pointId();
1616 m_newPoint->
SetId(m_lastUsedPointId);
1627 QString message =
"This is a coreg network which needs the cube with serial number " +
1628 m_coregReferenceSN +
" as the reference measure. This new control point does " 1629 "not have a measure for that serial number, so this point cannot be created until " 1630 "the cube listed above is added (Right-click on cube).";
1631 QMessageBox::critical(m_matchTool,
"Error", message);
1632 m_newPointDialog->show();
1640 if (m_editPoint != NULL && m_editPoint->Parent() == NULL) {
1644 m_editPoint = m_newPoint;
1647 delete m_newPointDialog;
1648 m_newPointDialog = NULL;
1652 m_matchTool->setVisible(
true);
1653 m_matchTool->raise();
1655 emit editPointChanged();
1661 void MatchTool::cancelNewPoint() {
1663 delete m_newPointDialog;
1664 m_newPointDialog = NULL;
1696 if (mCubes.size() > 0) {
1697 QString msgTitle =
"Missing Cubes";
1698 QString message =
"This point is missing cubes for the following measures and cannot be ";
1699 message +=
"loaded into the editor. Do you still want to delete this point?\n\n";
1700 for (
int i=0; i<mCubes.size(); i++) {
1701 message += mCubes.at(i) +
"\n";
1703 QMessageBox msgBox(QMessageBox::Critical, msgTitle, message, 0, m_matchTool,
1705 QPushButton *yesButton = msgBox.addButton(
"Yes", QMessageBox::AcceptRole);
1706 QPushButton *noButton = msgBox.addButton(
"No", QMessageBox::RejectRole);
1707 msgBox.setDefaultButton(yesButton);
1709 if (msgBox.clickedButton() == noButton) {
1713 m_matchTool->setVisible(
false);
1720 if (m_editPoint != NULL && m_editPoint->Parent() == NULL) {
1725 *m_editPoint = *point;
1728 if (mCubes.size() == 0) {
1734 emit editPointChanged();
1737 MatchToolDeletePointDialog *deletePointDialog =
new MatchToolDeletePointDialog;
1738 QString CPId = m_editPoint->
GetId();
1739 deletePointDialog->pointIdValue->setText(CPId);
1741 for (
int i=0; i<m_editPoint->GetNumMeasures(); i++) {
1750 deletePointDialog->fileList->addItem(file);
1753 if (deletePointDialog->exec()) {
1755 int numDeleted = deletePointDialog->fileList->selectedItems().count();
1758 if (deletePointDialog->deleteAllCheckBox->isChecked() ||
1759 numDeleted == m_editPoint->GetNumMeasures()) {
1762 if (!deletePointDialog->deleteAllCheckBox->isChecked()) {
1763 QString message =
"You have selected all measures in this point to be deleted. This " 1764 "control point will be deleted. Do you want to delete this control point?";
1765 int response = QMessageBox::question(m_matchTool,
1766 "Delete control point", message,
1767 QMessageBox::Yes | QMessageBox::No,
1770 if (response == QMessageBox::No) {
1775 m_matchTool->setVisible(
false);
1778 QMessageBox::information(m_matchTool,
"EditLocked Point",
1779 "This point is EditLocked and cannot be deleted.");
1782 if (m_editPoint != NULL && m_editPoint->Parent() == NULL) {
1791 int lockedMeasures = 0;
1792 for (
int i=0; i<deletePointDialog->fileList->count(); i++) {
1793 QListWidgetItem *item = deletePointDialog->fileList->item(i);
1794 if (!deletePointDialog->fileList->isItemSelected(item))
continue;
1799 (*m_editPoint)[i]->GetCubeSerialNumber())) {
1800 QString message =
"You are trying to delete the Reference measure." 1801 " Do you really want to delete the Reference measure?";
1802 switch (QMessageBox::question(m_matchTool,
1803 "Delete Reference measure?", message,
1804 "&Yes",
"&No", 0, 0)) {
1812 if (numDeleted == 1) {
1819 if (m_editPoint->
Delete(i) == ControlMeasure::MeasureLocked) {
1824 if (lockedMeasures > 0) {
1825 QMessageBox::information(m_matchTool,
"EditLocked Measures",
1826 QString::number(lockedMeasures) +
" / " 1828 deletePointDialog->fileList->selectedItems().size()) +
1829 " measures are EditLocked and were not deleted.");
1832 if (mCubes.size() == 0) {
1834 m_matchTool->setVisible(
true);
1835 m_matchTool->raise();
1838 m_pointEditor->templateFileName());
1846 if (m_editPoint != NULL && m_editPoint->Parent() == NULL) {
1855 m_netChanged =
true;
1860 emit editPointChanged();
1877 if (point->GetNumMeasures() == 0) {
1878 QString message =
"This point has no measures.";
1879 QMessageBox::warning(m_matchTool,
"Warning", message);
1880 emit editPointChanged();
1886 if (mCubes.size() > 0) {
1887 QString msgTitle =
"Missing Cubes";
1888 QString message =
"This point is missing cubes and cannot be loaded into the editor. Open ";
1889 message +=
"the cubes for the following measures before selecting this point.\n\n";
1890 for (
int i=0; i<mCubes.size(); i++) {
1891 message += mCubes.at(i) +
"\n";
1893 QMessageBox msgBox(QMessageBox::Critical, msgTitle, message, 0, m_matchTool,
1901 if (m_editPoint != NULL && m_editPoint->Parent() == NULL) {
1906 *m_editPoint = *point;
1909 m_matchTool->setVisible(
true);
1910 m_matchTool->raise();
1912 m_pointEditor->templateFileName());
1915 emit editPointChanged();
1918 m_savePoint->setPalette(m_saveDefaultPalette);
1943 QString CPId = m_editPoint->
GetId();
1944 QString ptId(
"Point ID: ");
1945 ptId += (QString) CPId;
1946 m_ptIdValue->setText(ptId);
1949 QString ptsize =
"Number of Measures: " +
1950 QString::number(m_editPoint->GetNumMeasures());
1951 m_numMeasures->setText(ptsize);
1954 m_lockPoint->setChecked(m_editPoint->IsEditLocked());
1957 m_ignorePoint->setChecked(m_editPoint->IsIgnored());
1960 m_leftCombo->clear();
1961 m_rightCombo->clear();
1962 m_pointFiles.clear();
1965 for (
int i=0; i<m_editPoint->GetNumMeasures(); i++) {
1970 m_leftCombo->addItem(tempFileName);
1971 m_rightCombo->addItem(tempFileName);
1974 m_leftCombo->setItemData(i,QFont(
"DejaVu Sans", 12, QFont::Bold), Qt::FontRole);
1975 m_rightCombo->setItemData(i,QFont(
"DejaVu Sans", 12, QFont::Bold), Qt::FontRole);
1994 if (!m_leftFile.isEmpty()) {
1995 leftIndex = m_leftCombo->findText(
FileName(m_leftFile).name());
1997 if (leftIndex < 0 ) leftIndex = 0;
2002 if (leftIndex == 0) {
2011 if (rightIndex > m_editPoint->GetNumMeasures()-1) rightIndex = 0;
2012 m_rightCombo->setCurrentIndex(rightIndex);
2013 m_leftCombo->setCurrentIndex(leftIndex);
2031 if (m_measureWindow == NULL) {
2033 m_measureTable =
new QTableWidget();
2034 m_measureTable->setMinimumWidth(1600);
2035 m_measureTable->setAlternatingRowColors(
true);
2036 m_measureWindow->setCentralWidget(m_measureTable);
2039 m_measureTable->clear();
2040 m_measureTable->setSortingEnabled(
false);
2042 m_measureTable->setRowCount(m_editPoint->GetNumMeasures());
2043 m_measureTable->setColumnCount(NUMCOLUMNS);
2046 for (
int i=0; i<NUMCOLUMNS; i++) {
2047 labels<<measureColumnToString((MeasureColumns)i);
2049 m_measureTable->setHorizontalHeaderLabels(labels);
2052 for (
int row=0; row<m_editPoint->GetNumMeasures(); row++) {
2057 QTableWidgetItem *tableItem =
new QTableWidgetItem(QString(file));
2058 m_measureTable->setItem(row,column++,tableItem);
2061 m_measureTable->setItem(row,column++,tableItem);
2063 tableItem =
new QTableWidgetItem();
2064 tableItem->setData(0,m.GetSample());
2065 m_measureTable->setItem(row,column++,tableItem);
2067 tableItem =
new QTableWidgetItem();
2068 tableItem->setData(0,m.GetLine());
2069 m_measureTable->setItem(row,column++,tableItem);
2071 if (m.GetAprioriSample() ==
Null) {
2072 tableItem =
new QTableWidgetItem(
"Null");
2075 tableItem =
new QTableWidgetItem();
2076 tableItem->setData(0,m.GetAprioriSample());
2078 m_measureTable->setItem(row,column++,tableItem);
2080 if (m.GetAprioriLine() ==
Null) {
2081 tableItem =
new QTableWidgetItem(
"Null");
2084 tableItem =
new QTableWidgetItem();
2085 tableItem->setData(0,m.GetAprioriLine());
2087 m_measureTable->setItem(row,column++,tableItem);
2089 if (m.GetSampleResidual() ==
Null) {
2090 tableItem =
new QTableWidgetItem(QString(
"Null"));
2093 tableItem =
new QTableWidgetItem();
2094 tableItem->setData(0,m.GetSampleResidual());
2096 m_measureTable->setItem(row,column++,tableItem);
2098 if (m.GetLineResidual() ==
Null) {
2099 tableItem =
new QTableWidgetItem(QString(
"Null"));
2102 tableItem =
new QTableWidgetItem();
2103 tableItem->setData(0,m.GetLineResidual());
2105 m_measureTable->setItem(row,column++,tableItem);
2108 tableItem =
new QTableWidgetItem(QString(
"Null"));
2111 tableItem =
new QTableWidgetItem();
2114 m_measureTable->setItem(row,column++,tableItem);
2116 double sampleShift = m.GetSampleShift();
2117 if (sampleShift ==
Null) {
2118 tableItem =
new QTableWidgetItem(QString(
"Null"));
2121 tableItem =
new QTableWidgetItem();
2122 tableItem->setData(0,sampleShift);
2124 m_measureTable->setItem(row,column++,tableItem);
2126 double lineShift = m.GetLineShift();
2127 if (lineShift ==
Null) {
2128 tableItem =
new QTableWidgetItem(QString(
"Null"));
2131 tableItem =
new QTableWidgetItem();
2132 tableItem->setData(0,lineShift);
2134 m_measureTable->setItem(row,column++,tableItem);
2136 double pixelShift = m.GetPixelShift();
2137 if (pixelShift ==
Null) {
2138 tableItem =
new QTableWidgetItem(QString(
"Null"));
2141 tableItem =
new QTableWidgetItem();
2142 tableItem->setData(0,pixelShift);
2144 m_measureTable->setItem(row,column++,tableItem);
2146 double goodnessOfFit = m.GetLogData(
2148 if (goodnessOfFit ==
Null) {
2149 tableItem =
new QTableWidgetItem(QString(
"Null"));
2152 tableItem =
new QTableWidgetItem();
2153 tableItem->setData(0,goodnessOfFit);
2155 m_measureTable->setItem(row,column++,tableItem);
2157 if (m.IsIgnored()) tableItem =
new QTableWidgetItem(
"True");
2158 if (!m.IsIgnored()) tableItem =
new QTableWidgetItem(
"False");
2159 m_measureTable->setItem(row,column++,tableItem);
2162 tableItem =
new QTableWidgetItem(
"True");
2164 tableItem =
new QTableWidgetItem(
"False");
2165 m_measureTable->setItem(row,column++,tableItem);
2167 tableItem =
new QTableWidgetItem(
2169 m_measureTable->setItem(row,column,tableItem);
2177 for (
int col=0; col<m_measureTable->columnCount(); col++)
2178 m_measureTable->item(row, col)->setFont(font);
2183 m_measureTable->resizeColumnsToContents();
2184 m_measureTable->resizeRowsToContents();
2185 m_measureTable->setSortingEnabled(
true);
2186 m_measureWindow->show();
2191 QString MatchTool::measureColumnToString(MatchTool::MeasureColumns column) {
2201 case SAMPLERESIDUAL:
2202 return "Sample Residual";
2204 return "Line Residual";
2205 case RESIDUALMAGNITUDE:
2206 return "Residual Magnitude";
2208 return "Sample Shift";
2210 return "Line Shift";
2212 return "Pixel Shift";
2214 return "Goodness of Fit";
2220 return "Measure Type";
2222 return "Apriori Sample";
2224 return "Apriori Line";
2227 "Invalid measure column passed to measureColumnToString",
_FILEINFO_);
2242 int curIndex = m_rightCombo->currentIndex();
2243 if (curIndex < m_rightCombo->count() - 1) {
2245 m_rightCombo->setCurrentIndex(curIndex + 1);
2261 int curIndex = m_rightCombo->currentIndex();
2264 m_rightCombo->setCurrentIndex(curIndex - 1);
2285 QString file = m_pointFiles[index];
2292 QString message =
"Make sure the correct cube is opened.\n\n";
2294 QMessageBox::critical(m_matchTool,
"Error", message);
2299 int i = m_leftCombo->findText(
FileName(file).name());
2301 m_leftCombo->setCurrentIndex(i);
2307 if (m_leftMeasure != NULL) {
2308 delete m_leftMeasure;
2309 m_leftMeasure = NULL;
2313 *m_leftMeasure = *((*m_editPoint)[serial]);
2316 if (m_leftCube != NULL)
delete m_leftCube;
2317 m_leftCube =
new Cube();
2318 m_leftCube->
open(file);
2322 m_editPoint->
GetId());
2341 QString file = m_pointFiles[index];
2348 QString message =
"Make sure the correct cube is opened.\n\n";
2350 QMessageBox::critical(m_matchTool,
"Error", message);
2355 int i = m_rightCombo->findText(
FileName(file).name());
2357 m_rightCombo->setCurrentIndex(i);
2363 if (m_rightMeasure != NULL) {
2364 delete m_rightMeasure;
2365 m_rightMeasure = NULL;
2369 *m_rightMeasure = *((*m_editPoint)[serial]);
2372 if (m_rightCube != NULL)
delete m_rightCube;
2373 m_rightCube =
new Cube();
2374 m_rightCube->
open(file);
2378 m_editPoint->
GetId());
2407 m_ignoreLeftMeasure->setChecked(m_leftMeasure->IsIgnored());
2409 QString s =
"Reference: ";
2417 m_leftReference->setText(s);
2419 s =
"Measure Type: ";
2424 m_leftMeasureType->setText(s);
2426 if (m_leftMeasure->GetSampleShift() ==
Null) {
2427 s =
"Sample Shift: Null";
2430 s =
"Sample Shift: " + QString::number(m_leftMeasure->GetSampleShift());
2432 m_leftSampShift->setText(s);
2434 if (m_leftMeasure->GetLineShift() ==
Null) {
2435 s =
"Line Shift: Null";
2438 s =
"Line Shift: " + QString::number(m_leftMeasure->GetLineShift());
2440 m_leftLineShift->setText(s);
2442 double goodnessOfFit = m_leftMeasure->GetLogData(
2444 if (goodnessOfFit ==
Null) {
2445 s =
"Goodness of Fit: Null";
2448 s =
"Goodness of Fit: " + QString::number(goodnessOfFit);
2450 m_leftGoodness->setText(s);
2480 m_ignoreRightMeasure->setChecked(m_rightMeasure->IsIgnored());
2482 QString s =
"Reference: ";
2491 m_rightReference->setText(s);
2493 s =
"Measure Type: ";
2498 m_rightMeasureType->setText(s);
2500 if (m_rightMeasure->GetSampleShift() ==
Null) {
2501 s =
"Sample Shift: Null";
2504 s =
"Sample Shift: " + QString::number(m_rightMeasure->GetSampleShift());
2506 m_rightSampShift->setText(s);
2508 if (m_rightMeasure->GetLineShift() ==
Null) {
2509 s =
"Line Shift: Null";
2512 s =
"Line Shift: " + QString::number(m_rightMeasure->GetLineShift());
2514 m_rightLineShift->setText(s);
2516 double goodnessOfFit = m_rightMeasure->GetLogData(
2518 if (goodnessOfFit ==
Null) {
2519 s =
"Goodness of Fit: Null";
2522 s =
"Goodness of Fit: " + QString::number(goodnessOfFit);
2524 m_rightGoodness->setText(s);
2541 if(e->type() != QEvent::Leave)
return false;
2542 if(o == m_leftCombo->view()) {
2544 m_leftCombo->hidePopup();
2546 if (o == m_rightCombo->view()) {
2548 m_rightCombo->hidePopup();
2588 mvp->viewport()->update();
2617 if ( (m_controlNet == NULL || m_controlNet->GetNumPoints() == 0) && m_newPoint == NULL &&
2618 m_editPoint == NULL)
2621 QString sn = serialNumber(mvp);
2625 if (m_newPoint != NULL) {
2629 double samp = (*m_newPoint)[sn]->GetSample();
2630 double line = (*m_newPoint)[sn]->GetLine();
2634 QBrush brush(Qt::red);
2638 painter->setPen(pen);
2639 painter->drawLine(x - 5, y, x + 5, y);
2640 painter->drawLine(x, y - 5, x, y + 5);
2645 if (!m_controlNet->GetCubeSerials().contains(
2653 m_controlNet->GetMeasuresInCube(sn);
2655 for (
int i = 0; i < measures.count(); i++) {
2658 double samp = m->GetSample();
2659 double line = m->GetLine();
2663 if (m->Parent()->IsIgnored()) {
2664 painter->setPen(QColor(255, 255, 0));
2667 else if (m->IsIgnored()) {
2668 painter->setPen(QColor(255, 255, 0));
2671 painter->setPen(Qt::green);
2674 painter->drawLine(x - 5, y, x + 5, y);
2675 painter->drawLine(x, y - 5, x, y + 5);
2678 if (m_editPoint != NULL && m_newPoint == NULL) {
2682 double samp = (*m_editPoint)[sn]->GetSample();
2683 double line = (*m_editPoint)[sn]->GetLine();
2687 QBrush brush(Qt::red);
2691 painter->setPen(pen);
2692 painter->drawLine(x - 5, y, x + 5, y);
2693 painter->drawLine(x, y - 5, x, y + 5);
2715 if (m_templateModified) {
2716 int r = QMessageBox::warning(m_matchTool, tr(
"OK to continue?"),
2717 tr(
"The currently opened registration template has been modified.\n" 2719 QMessageBox::Yes | QMessageBox::No | QMessageBox::Cancel,
2722 if (r == QMessageBox::Yes)
2724 else if (r == QMessageBox::Cancel)
2743 QString filename = QFileDialog::getOpenFileName(m_matchTool,
2744 "Select a registration template",
".",
2745 "Registration template files (*.def *.pvl);;All files (*)");
2747 if (filename.isEmpty())
2764 QFile file(
FileName((QString) fn).expanded());
2765 if (!file.open(QIODevice::ReadOnly)) {
2766 QString msg =
"Failed to open template file \"" + fn +
"\"";
2767 QMessageBox::warning(m_matchTool,
"IO Error", msg);
2771 QTextStream stream(&file);
2772 m_templateEditor->setText(stream.readAll());
2775 QScrollBar * sb = m_templateEditor->verticalScrollBar();
2776 sb->setValue(sb->minimum());
2778 m_templateModified =
false;
2779 m_saveTemplateFile->setEnabled(
false);
2780 m_templateFileNameLabel->setText(
"Template File: " + fn);
2787 m_templateModified =
true;
2788 m_saveTemplateFile->setEnabled(
true);
2796 if (!m_templateModified)
2800 m_pointEditor->templateFileName();
2810 QString filename = QFileDialog::getSaveFileName(m_matchTool,
2811 "Save registration template",
".",
2812 "Registration template files (*.def *.pvl);;All files (*)");
2814 if (filename.isEmpty())
2829 QString contents = m_templateEditor->toPlainText();
2840 QMessageBox::warning(m_matchTool,
"Error", message);
2844 QString expandedFileName(
2845 FileName((QString) fn).expanded());
2847 QFile file(expandedFileName);
2849 if (!file.open(QIODevice::WriteOnly | QIODevice::Truncate)) {
2850 QString msg =
"Failed to save template file to \"" + fn +
"\"\nDo you " 2852 QMessageBox::warning(m_matchTool,
"IO Error", msg);
2857 QTextStream stream(&file);
2862 m_templateModified =
false;
2863 m_saveTemplateFile->setEnabled(
false);
2864 m_templateFileNameLabel->setText(
"Template File: " + fn);
2886 Pvl templatePvl(m_pointEditor->templateFileName());
2890 registrationDialog.setWindowTitle(
"View or Edit Template File: " 2891 + templatePvl.fileName());
2892 registrationDialog.resize(550,360);
2893 registrationDialog.exec();
2897 QMessageBox::information(m_matchTool,
"Error", message);
2915 void MatchTool::showHideTemplateEditor() {
2917 if (!m_templateEditorWidget)
2920 m_templateEditorWidget->setVisible(!m_templateEditorWidget->isVisible());
2938 if (m_editPoint == NULL)
return;
2939 if (pointId != m_editPoint->
GetId())
return;
2944 ControlPoint *updatedPoint = m_controlNet->GetPoint(pointId);
2945 m_editPoint->
SetEditLock(updatedPoint->IsEditLocked());
2946 m_editPoint->
SetIgnored(updatedPoint->IsIgnored());
2949 m_lockPoint->setChecked(m_editPoint->IsEditLocked());
2952 m_ignorePoint->setChecked(m_editPoint->IsIgnored());
2977 if (m_editPoint != NULL) {
2979 QString
id = m_ptIdValue->text().remove(
"Point ID: ");
2980 m_controlNet->GetPoint(
id);
2985 emit editPointChanged();
3003 QColor qc = Qt::red;
3004 QPalette p = m_savePoint->palette();
3005 p.setColor(QPalette::ButtonText,qc);
3006 m_savePoint->setPalette(p);
3026 if (m_editPoint == NULL)
return false;
3048 FileName config(
"$HOME/.Isis/qview/MatchTool.config");
3049 QSettings settings(config.
expanded(),
3050 QSettings::NativeFormat);
3051 QPoint pos = settings.value(
"pos", QPoint(300, 100)).toPoint();
3052 QSize size = settings.value(
"size", QSize(900, 500)).toSize();
3053 m_matchTool->resize(size);
3054 m_matchTool->move(pos);
3067 if (!m_matchTool->isVisible())
return;
3068 FileName config(
"$HOME/.Isis/qview/MatchTool.config");
3069 QSettings settings(config.
expanded(),
3070 QSettings::NativeFormat);
3071 settings.setValue(
"pos", m_matchTool->pos());
3072 settings.setValue(
"size", m_matchTool->size());
3077 void MatchTool::enterWhatsThisMode() {
3078 QWhatsThis::enterWhatsThisMode();
3082 void MatchTool::clearEditPoint() {
3088 void MatchTool::showHelp() {
3091 helpDialog->setWindowTitle(
"Match Tool Help");
3093 QVBoxLayout *mainLayout =
new QVBoxLayout;
3094 helpDialog->setLayout(mainLayout);
3096 QLabel *matchTitle =
new QLabel(
"<h2>Match Tool</h2>");
3097 mainLayout->addWidget(matchTitle);
3099 QLabel *matchSubtitle =
new QLabel(
"A tool for interactively measuring and editing sample/line " 3100 "registration points between cubes. These " 3101 "points contain sample, line postions only, no latitude or " 3102 "longitude values are used or recorded.");
3103 matchSubtitle->setWordWrap(
true);
3104 mainLayout->addWidget(matchSubtitle);
3106 QTabWidget *tabArea =
new QTabWidget;
3107 tabArea->setDocumentMode(
true);
3108 mainLayout->addWidget(tabArea);
3111 QScrollArea *overviewTab =
new QScrollArea;
3112 overviewTab->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
3113 overviewTab->setWidgetResizable(
true);
3115 QVBoxLayout *overviewLayout =
new QVBoxLayout;
3116 overviewContainer->setLayout(overviewLayout);
3118 QLabel *purposeTitle =
new QLabel(
"<h2>Purpose</h2>");
3119 overviewLayout->addWidget(purposeTitle);
3121 QLabel *purposeText =
new QLabel(
"<p>This tool is for recording and editing registration " 3122 "points measured between cubes displayed in the <i>qview</i> main window.</p> <p>The " 3123 "recorded registration points are sample and line pixel coordinates only. Therefore, this " 3124 "tool can be used on any images including ones that do not contain a camera model " 3125 "(i.e, The existence of the Isis Instrument Group on the image labels is not required). " 3126 "This also means that the tool differs from the <i>qnet</i> control point network " 3127 "application in that no latitude or longitude values are ever used or recorded " 3128 "(regardless if the image has a camera model in Isis).</p>" 3129 "<p>The output control point network that this tool generates is primarily used 1) as " 3130 "input for an image-wide sample/line translation to register one image to another by " 3131 "'moving' pixel locations - refer to the documentation for applications such as " 3132 "<i>translate</i> and <i>warp</i>, or 2) to export the file and use the recorded " 3133 "measurements in other spreadsheet or plotting packages to visualize magnitude " 3134 "and direction of varying translations of the images relative to one another.</p> " 3135 "<p>An automated version of this match tool is the <i>coreg</i> application. This tool " 3136 "can be used to visually evaluate and edit the control point network created by " 3137 "<i>coreg</i>.</p> " 3138 "<p>The format of the output point network file is binary. This tool uses the Isis control " 3139 " network framework to create, co-register and save all control points and pixel " 3140 "measurements. The application <i>cnetbin2pvl</i> can be used to convert from binary to " 3141 "a readable PVL format." 3142 "<p>The Mouse Button functions are: (same as <i>qnet</i>)<ul><li>Modify Point=Left</li> " 3143 "<li>Delete Point=Middle</li><li>Create New Point=Right</li></ul></p>" 3144 "<p>Control Points are drawn on the associated displayed cubes with the following colors: " 3145 "Green=Valid registration point; Yellow=Ignored point; Red=Active point being edited");
3146 purposeText->setWordWrap(
true);
3147 overviewLayout->addWidget(purposeText);
3149 overviewTab->setWidget(overviewContainer);
3152 QScrollArea *quickTab =
new QScrollArea;
3153 quickTab->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
3154 quickTab->setWidgetResizable(
true);
3156 QVBoxLayout *quickLayout =
new QVBoxLayout;
3157 quickContainer->setLayout(quickLayout);
3159 QLabel *quickTitle =
new QLabel(
"<h2>Quick Start</h2>");
3160 quickLayout->addWidget(quickTitle);
3162 QLabel *quickSubTitle =
new QLabel(
"<h3>Preparation:</h3>");
3163 quickLayout->addWidget(quickSubTitle);
3165 QLabel *quickPrep =
new QLabel(
"<p><ul>" 3166 "<li>Open the cubes with overlapping areas for choosing control points</li>" 3167 "<li>Choose the match tool <img src=\"" +
toolIconDir() +
3168 "/stock_draw-connector-with-arrows.png\" width=22 height=22> " 3169 "from the toolpad on the right side of the <i>qview</i> main window</li>");
3170 quickPrep->setWordWrap(
true);
3171 quickLayout->addWidget(quickPrep);
3173 QLabel *morePrep =
new QLabel(
"<p>Once the Match tool is activated the tool bar at the top " 3174 "of the main window contains file action buttons and a help button:");
3175 morePrep->setWordWrap(
true);
3176 quickLayout->addWidget(morePrep);
3178 QLabel *fileButtons =
new QLabel(
"<p><ul>" 3179 "<li><img src=\"" +
toolIconDir() +
"/fileopen.png\" width=22 height=22> Open an existing " 3180 "control network <b>Note:</b> If you do not open an existing network, a new one will " 3182 "<li><img src=\"" +
toolIconDir() +
"/mActionFileSaveAs.png\" width=22 height=22> Save " 3183 "control network as ...</li>" 3184 "<li><img src=\"" +
toolIconDir() +
"/mActionFileSave.png\" width=22 height=22> Save " 3185 "control network to current file</li>" 3186 "<li><img src=\"" +
toolIconDir() +
"/help-contents.png\" width=22 height=22> Show Help " 3188 fileButtons->setWordWrap(
true);
3189 quickLayout->addWidget(fileButtons);
3191 QLabel *quickFunctionTitle =
new QLabel(
"<h3>Cube Viewport Functions:</h3>");
3192 quickLayout->addWidget(quickFunctionTitle);
3194 QLabel *quickFunction =
new QLabel(
3195 "The match tool window will be shown once " 3196 "you click in a cube viewport window using one of the following " 3197 "mouse functions. <b>Note:</b> Existing control points are drawn on the cube viewports");
3198 quickFunction->setWordWrap(
true);
3199 quickLayout->addWidget(quickFunction);
3201 QLabel *quickDesc =
new QLabel(
"<p><ul>" 3202 "<li>Left Click - Modify the control point closest to the click <b>Note:</b> " 3203 "All cubes in the control point must be displayed before loading the point</li>" 3204 "<li>Middle Click - Delete the control point closest to the click</li>" 3205 "<li>Right Click - Create a new control point at the click location</li></ul></p>");
3206 quickDesc->setWordWrap(
true);
3207 quickDesc->setOpenExternalLinks(
true);
3208 quickLayout->addWidget(quickDesc);
3210 quickTab->setWidget(quickContainer);
3213 QScrollArea *controlPointTab =
new QScrollArea;
3214 controlPointTab->setWidgetResizable(
true);
3215 controlPointTab->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
3217 QVBoxLayout *controlPointLayout =
new QVBoxLayout;
3218 controlPointContainer->setLayout(controlPointLayout);
3220 QLabel *controlPointTitle =
new QLabel(
"<h2>Control Point Editing</h2>");
3221 controlPointLayout->addWidget(controlPointTitle);
3223 QLabel *mouseLabel =
new QLabel(
"<p><h3>When the \"Match\" tool " 3224 "is activated, the mouse buttons have the following function in the " 3225 "cube viewports of the main qview window:</h3>");
3226 mouseLabel->setWordWrap(
true);
3227 mouseLabel->setScaledContents(
true);
3228 controlPointLayout->addWidget(mouseLabel);
3230 QLabel *controlPointDesc =
new QLabel(
"<ul>" 3231 "<li>Left click - Edit the closest control point <b>Note:</b> " 3232 "All cubes in the control point must be displayed before loading the point</li>" 3233 "<li>Middle click - Delete the closest control point</li>" 3234 "<li>Right click - Create new control point at cursor location. This will bring up a new " 3235 "point dialog which allows you to enter a point id and will list all cube viewports, " 3236 "highlighting cubes where the point has been chosen by clicking on the cube's viewport. " 3237 "When the desired cubes have been chosen, select the \"Done\" button which will load the " 3238 "control point into the control point editor window which will allow the control measure " 3239 "positions to be refined.</li>");
3240 controlPointDesc->setWordWrap(
true);
3241 controlPointLayout->addWidget(controlPointDesc);
3243 QLabel *controlPointEditing =
new QLabel(
3244 "<h4>Changing Control Measure Locations</h4>" 3245 "<p>Both the left and right control measure positions can be adjusted by:" 3247 "<li>Move the cursor location under the crosshair by clicking the left mouse " 3249 "<li>Move 1 pixel at a time by using arrow keys on the keyboard</li>" 3250 "<li>Move 1 pixel at a time by using arrow buttons above the right and left views</li>" 3252 "<h4>Other Point Editor Functions</h4>" 3253 "<p>Along the right border of the window:</p>" 3255 "<li><strong>Link Zoom</strong> This will link the two small viewports together when " 3256 "zooming (ie. If this is checked, if the left view is zoomed, the right view will " 3257 "match the left view's zoom factor. " 3258 "<b>Note:</b> Zooming is controlled from the left view.</li>" 3259 "<li><strong>No Rotate:</strong> Turn off the rotation and bring right view back to " 3260 "its original orientation</li>" 3261 "<li><strong>Rotate:</strong> Rotate the right view using either the dial " 3262 "or entering degrees </li>" 3263 "<li><strong>Show control points:</strong> Draw crosshairs at all control " 3264 "point locations visible within the view</li>" 3265 "<li><strong>Show crosshair:</strong> Show a red crosshair across the entire " 3267 "<li><strong>Circle:</strong> Draw circle which may help center measure " 3268 "on a crater</li></ul" 3269 "<p>Below the left view:</p>" 3270 "<ul><li><strong>Blink controls:</strong> Blink the left and right view in the " 3271 "left view window using the \"Blink Start\" button <img src=\"" +
toolIconDir() +
3272 "/blinkStart.png\" width=22 height=22> and \"Blink Stop\" button <img src=\"" +
3273 toolIconDir() +
"/blinkStop.png\" width=22 height=22>. The arrow keys above the left " 3274 "and right views and the keyboard arrow keys may be used to move the both views while " 3276 "<li><strong>Register:</strong> Sub-pixel register the right view to " 3277 "the left view. A default registration template is used for setting parameters " 3278 "passed to the sub-pixel registration tool. The user may load in a predefined " 3279 "template or edit the current loaded template to influence successful " 3280 "co-registration results. For more information regarding the pattern matching " 3281 "functionlity or how to create a parameter template, refer to the Isis PatternMatch " 3282 "document and the <i>autoregtemplate</i> application. <strong>Shortcut: R.</strong>" 3284 "<li><strong>Save Measures:</strong> Save the two control measures using the sample, " 3285 "line positions under the crosshairs. <strong>Shortcut: M.</strong></li>" 3286 "<li><strong>Save Point:</strong> Save the control point to the control network. " 3287 "<strong>Shortcut: P.</strong></li>" 3289 controlPointEditing->setWordWrap(
true);
3290 controlPointLayout->addWidget(controlPointEditing);
3292 controlPointTab->setWidget(controlPointContainer);
3295 QScrollArea *coregTab =
new QScrollArea;
3296 coregTab->setWidgetResizable(
true);
3297 coregTab->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
3299 QVBoxLayout *coregLayout =
new QVBoxLayout;
3300 coregContainer->setLayout(coregLayout);
3302 QLabel *coregTitle =
new QLabel(
"<h2>Coreg Guidance</h2>");
3303 coregLayout->addWidget(coregTitle);
3305 QLabel *coregDesc =
new QLabel(
"<p>When opening control networks created by <i>coreg</i>, " 3306 "there are some things to keep in mind. First, all control points must have the same " 3307 "reference measure (this is the image filename passed to the <i>coreg</i> 'match' parameter)." 3308 "<p>In order to retain the integrity of the input <i>coreg</i> network, you cannot change " 3309 "which image is the reference measure on any of the existing points. " 3310 "<p>When creating a new control point to add to the <i>coreg</i> network, this tool will " 3311 "automatically set the reference measure to the same image as the other control points in " 3312 "the network as long as the reference image was one of the images selected with " 3313 "the right mouse button from the new point dialog. If this image was not selected when " 3314 "creating a new point, it " 3315 "does not contain a required measurement, therefore, you will get an error and the new " 3316 "point will not be created.</p> <p>The reference measure is always loaded on the left side " 3317 "of the control point editor. If you load a measure that is not the reference measure " 3318 "on the left side and try to save the point, you will receive an error message. You will " 3319 "need to move the reference measure back to the left side before saving the control point." 3320 "</p><p><b>Note:</b> This error checking will not happen on control networks created by " 3321 "<i>coreg</i> prior to Isis3.4.2. For older <i>coreg</i> control networks the user must be " 3322 "aware and make sure the correct image is set to the same <i>coreg</i> reference measure.");
3323 coregDesc->setWordWrap(
true);
3324 coregDesc->setScaledContents(
true);
3325 coregLayout->addWidget(coregDesc);
3327 coregTab->setWidget(coregContainer);
3329 tabArea->addTab(overviewTab,
"&Overview");
3330 tabArea->addTab(quickTab,
"&Quick Start");
3331 tabArea->addTab(controlPointTab,
"&Control Point Editing");
3332 tabArea->addTab(coregTab,
"&Coreg Guidance");
3334 QHBoxLayout *buttonsLayout =
new QHBoxLayout;
3336 buttonsLayout->addStretch();
3338 QPushButton *closeButton =
new QPushButton(
"&Close");
3339 closeButton->setIcon(QPixmap(
toolIconDir() +
"/guiStop.png"));
3340 closeButton->setDefault(
true);
3341 connect(closeButton, SIGNAL(clicked()),
3342 helpDialog, SLOT(close()));
3343 buttonsLayout->addWidget(closeButton);
3345 mainLayout->addLayout(buttonsLayout);
3364 if ( m_controlNet->GetNumPoints() == 0 ||
3365 !m_controlNet->ContainsPoint(m_editPoint->
GetId())) {
3366 QString message =
"\n\nDo you want to save the point in the editor?";
3367 int response = QMessageBox::question(m_matchTool,
"Save point in editor", message,
3368 QMessageBox::Yes | QMessageBox::No,
3370 if (response == QMessageBox::Yes) {
3376 if (m_controlNet && m_controlNet->GetNumPoints() != 0 && m_netChanged) {
3377 QString message =
"The currently open control net has changed. Do you want to save?";
3378 int response = QMessageBox::question(m_matchTool,
"Save current control net?",
3380 QMessageBox::Yes | QMessageBox::No,
3383 if (response == QMessageBox::Yes) {
Status SetType(MeasureType type)
Set how the coordinate was obtained.
Cube display widget for certain Isis MDI applications.
bool HasSerialNumber(QString serialNumber) const
Return true if given serial number exists in point.
const char * what() const
Returns a string representation of this exception in its current state.
const double Null
Value for an Isis Null pixel.
bool IsReferenceExplicit() const
void Add(ControlMeasure *measure)
Add a measurement to the control point, taking ownership of the measure in the process.
(e.g., autoseed, interest) AKA predicted, unmeasured, unverified
bool hasSerialNumber(QString sn)
Determines whether or not the requested serial number exists in the list.
File name manipulation and expansion.
void add(const QString &filename, bool def2filename=false)
Adds a new filename / serial number pair to the SerialNumberList.
const ControlMeasure * GetMeasure(QString serialNumber) const
Get a control measure based on its cube's serial number.
Status SetIgnored(bool newIgnoreStatus)
Set whether to ignore or use control point.
QString serialNumber(const QString &filename)
Return a serial number given a filename.
double GetResidualMagnitude() const
Return Residual magnitude.
QString GetReferenceSN() const
Namespace for the standard library.
QString name() const
Returns the name of the file excluding the path and the attributes in the file name.
Status SetChooserName(QString name)
Set the point's chooser name.
void saveChips()
Slot to save registration chips to files and fire off qview.
Widget to display Isis cubes for qt apps.
void cubeToViewport(double sample, double line, int &x, int &y) const
Turns a cube into a viewport.
Registered to whole pixel (e.g.,pointreg)
Registered to sub-pixel (e.g., pointreg)
This error is for when a programmer made an API call that was illegal.
Status SetEditLock(bool editLock)
Set the EditLock state.
A Free point is a Control Point that identifies common measurements between two or more cubes...
static QString Compose(Pvl &label, bool def2filename=false)
Compose a SerialNumber from a PVL.
QString fileName(const QString &sn)
Return a filename given a serial number.
This was called the Qisis MainWindow.
void setRightMeasure(ControlMeasure *rightMeasure, Cube *rightCube, QString pointId)
Set the measure displayed in the right ChipViewport.
bool setTemplateFile(QString)
Allows user to choose a new template file by opening a window from which to select a filename...
Hand Measured (e.g., qnet)
QString GetId() const
Return the Id of the control point.
#define _FILEINFO_
Macro for the filename and line number.
Status SetRefMeasure(ControlMeasure *cm)
Set the point's reference measure.
QString expanded() const
Returns a QString of the full file name including the file path, excluding the attributes.
void open(const QString &cfile, QString access="r")
This method will open an isis cube for reading or reading/writing.
void remove(const QString &sn)
Remove the specified serial number from the list.
Container for cube-like labels.
Status SetType(PointType newType)
Updates the control point's type.
Status SetId(QString id)
Sets the Id of the control point.
const ControlMeasure * GetRefMeasure() const
Get the reference control measure.
Status
This is a return status for many of the mutating (setter) method calls.
GoodnessOfFit is pointreg information for reference measures.
QString toString() const
Returns a string representation of this exception.
int IndexOfRefMeasure() const
virtual QString fileName() const
Returns the opened cube's filename.
static QString UserName()
Returns the user name.
Status SetChooserName()
Set chooser name to a user who last changed the coordinate.
Namespace for ISIS/Bullet specific routines.
bool IsEditLocked() const
Return value for p_editLock or implicit lock on reference measure.
PvlEditDialog creates a QDialog window in which a QTextEdit box displays the contents of a pvl file...
Status SetCubeSerialNumber(QString newSerialNumber)
Set cube serial number.
Status SetCoordinate(double sample, double line)
Set the coordinate of the measurement.
int Delete(ControlMeasure *measure)
Remove a measurement from the control point, deleting reference measure is allowed.
Status SetDateTime()
Date Time - Creation Time.
double GetNumericalValue() const
Get the value associated with this log data.
Serial Number list generator.
void viewportToCube(int x, int y, double &sample, double &line) const
Turns a viewport into a cube.
QString GetCubeSerialNumber() const
Return the serial number of the cube containing the coordinate.
static QString MeasureTypeToString(MeasureType type)
Return the String Control Measure type.
void setLeftMeasure(ControlMeasure *leftMeasure, Cube *leftCube, QString pointId)
Set the measure displayed in the left ChipViewport.
This is returned when the operation requires Edit Lock to be false but it is currently true...
IO Handler for Isis Cubes.