@@ -48,11 +48,11 @@ MainWindow::MainWindow(QWidget *parent) :
48
48
ui->comboBox_grid_color ->addItem (tr (" White" ));
49
49
ui->comboBox_grid_color ->blockSignals (false );
50
50
51
- ui->comboBox_algorithm ->setCurrentIndex (4 );
51
+ ui->comboBox_algorithm ->setCurrentIndex (4 ); // SLIC
52
52
53
- InitializeValues ();
53
+ InitializeValues (); // init all indicators and zoom etc
54
54
55
- basedir = " /media/DataI5/Photos/" ;
55
+ basedir = " /media/DataI5/Photos/" ; // base path and file
56
56
basefile = " " ;
57
57
}
58
58
@@ -61,15 +61,15 @@ MainWindow::~MainWindow()
61
61
delete ui;
62
62
}
63
63
64
- // ///////////////// UI //////////////////////
64
+ // ///////////////// GUI //////////////////////
65
65
66
66
void MainWindow::on_Tabs_currentChanged (int ) // when a tab is clicked
67
67
{
68
68
if (ui->Tabs ->currentIndex ()==2 ) ui->label_segmentation ->setCursor (Qt::PointingHandCursor); // labels tab ? => labels view cursor
69
69
else ui->label_segmentation ->setCursor (Qt::ArrowCursor); // default cursor
70
70
}
71
71
72
- void MainWindow::InitializeValues ()
72
+ void MainWindow::InitializeValues () // initialize all sorts of indicators, zoom, etc
73
73
{
74
74
// Hide tabs
75
75
ui->Tabs ->setTabEnabled (1 , false );
@@ -111,13 +111,13 @@ void MainWindow::DeleteAllLabels(bool newLabel) // add a label to the list
111
111
112
112
void MainWindow::UnselectAllLabels () // unselect all labels in list
113
113
{
114
- for (int n = 0 ; n < ui->listWidget_labels ->count (); n++)
115
- ui->listWidget_labels ->item (n)->setSelected (false );
114
+ for (int n = 0 ; n < ui->listWidget_labels ->count (); n++) // for each label
115
+ ui->listWidget_labels ->item (n)->setSelected (false ); // unselect it
116
116
}
117
117
118
118
QListWidgetItem* MainWindow::AddNewLabel (QString newLabel) // add a label to the list
119
119
{
120
- UnselectAllLabels ();
120
+ UnselectAllLabels (); // the new one will be the only selected
121
121
122
122
QListWidgetItem *item = new QListWidgetItem ();
123
123
if (newLabel == " " ) item->setText (" Rename me!" ); // default text of the label
@@ -137,16 +137,16 @@ QListWidgetItem* MainWindow::AddNewLabel(QString newLabel) // add a label to the
137
137
138
138
void MainWindow::on_listWidget_labels_currentItemChanged (QListWidgetItem *currentItem) // show current label color
139
139
{
140
- QBrush brush = currentItem->background ();
141
- ShowCurrentColor (brush.color ().red (), brush.color ().green (), brush.color ().blue ());
140
+ QBrush brush = currentItem->background (); // the label color is stored in the background color of the list
141
+ ShowCurrentColor (brush.color ().red (), brush.color ().green (), brush.color ().blue ()); // show current color used
142
142
}
143
143
144
144
void MainWindow::on_listWidget_labels_itemChanged (QListWidgetItem *currentItem) // show current label text
145
145
{
146
- ui->label_color ->setText (currentItem->text ());
146
+ ui->label_color ->setText (currentItem->text ()); // show label name
147
147
}
148
148
149
- void MainWindow::on_pushButton_label_add_clicked () // add a new default label
149
+ void MainWindow::on_pushButton_label_add_clicked () // add new default label
150
150
{
151
151
if (!computed) { // if image not computed yet get out
152
152
QMessageBox::warning (this , " No cells found" ,
@@ -229,7 +229,7 @@ void MainWindow::on_pushButton_label_join_clicked() // join 2 or more labels, re
229
229
}
230
230
items[0 ]->setText (items[0 ]->text () + " (joined)" ); // add "join" to the first label name containing the result
231
231
232
- ShowSegmentation (); // show the result
232
+ ShowSegmentation (); // show result
233
233
}
234
234
235
235
void MainWindow::on_pushButton_label_create_clicked () // special mode to modify the cells (superpixels)
@@ -249,7 +249,7 @@ void MainWindow::on_pushButton_label_create_clicked() // special mode to modify
249
249
250
250
ui->label_segmentation ->setCursor (Qt::CrossCursor); // cursor change to show this is a special mode
251
251
252
- ui->frame_pick_colors ->setVisible (false ); // disable all the tabs/elements to keep the user in the special mode
252
+ ui->frame_pick_colors ->setVisible (false ); // disable all tabs/elements to keep the user in the special mode
253
253
ui->pushButton_label_add ->setVisible (false );
254
254
ui->pushButton_label_delete ->setVisible (false );
255
255
ui->pushButton_label_hide ->setVisible (false );
@@ -436,14 +436,13 @@ void MainWindow::on_button_image_clicked() // Load main image
436
436
return ;
437
437
}
438
438
439
- ui->label_thumbnail ->setPixmap (QPixmap ());
439
+ ui->label_thumbnail ->setPixmap (QPixmap ()); // unset all images in GUI
440
440
ui->label_segmentation ->setPixmap (QPixmap ());
441
441
ui->label_thumbnail ->setPixmap (Mat2QPixmapResized (mat, ui->label_thumbnail ->width (), ui->label_thumbnail ->height (), true )); // Show thumbnail
442
442
443
443
image = mat; // store the image for further use
444
444
mat.copyTo (image_backup); // for undo
445
- image.copyTo (selection); // selection mask
446
- selection = 0 ;
445
+ selection = Mat::zeros (image.rows , image.cols , CV_8UC3); // init selection mask
447
446
448
447
ui->label_segmentation ->setPixmap (QPixmap ()); // Delete the depthmap image
449
448
ui->label_segmentation ->setText (" Segmentation not computed" ); // Text in the segmentation area
@@ -458,7 +457,7 @@ void MainWindow::on_button_image_clicked() // Load main image
458
457
ui->label_image_width ->setText (QString::number (image.cols )); // display image dimensions
459
458
ui->label_image_height ->setText (QString::number (image.rows ));
460
459
461
- InitializeValues ();
460
+ InitializeValues (); // reset all variables
462
461
463
462
double zoomX = double (ui->label_segmentation ->width ()) / image.cols ; // try vertical and horizontal ratios
464
463
double zoomY = double (ui->label_segmentation ->height ()) / image.rows ;
@@ -592,8 +591,10 @@ void MainWindow::on_button_load_session_clicked() // load previous session
592
591
size_t pos = filesession.find (" -segmentation-data.xml" );
593
592
if (pos != std::string::npos) filesession.erase (pos, filesession.length ());
594
593
595
- InitializeValues ();
594
+ InitializeValues (); // reinit all variables
596
595
image.release ();
596
+ mask.release ();
597
+ grid.release ();
597
598
598
599
mask = cv::imread (filesession + " -segmentation-mask.png" , CV_LOAD_IMAGE_COLOR); // load mask
599
600
if (mask.empty ()) {
@@ -674,7 +675,7 @@ void MainWindow::on_button_load_session_clicked() // load previous session
674
675
675
676
fs.release (); // close file
676
677
677
- ui->label_thumbnail ->setPixmap (QPixmap ());
678
+ ui->label_thumbnail ->setPixmap (QPixmap ()); // reinit all images in GUI
678
679
ui->label_segmentation ->setPixmap (QPixmap ());
679
680
ui->label_thumbnail ->setPixmap (Mat2QPixmapResized (image, ui->label_thumbnail ->width (), ui->label_thumbnail ->height (), true )); // Show thumbnail
680
681
@@ -694,8 +695,7 @@ void MainWindow::on_button_load_session_clicked() // load previous session
694
695
selection.release ();
695
696
696
697
image.copyTo (image_backup); // for undo
697
- image.copyTo (selection); // selection mask
698
- selection = 0 ;
698
+ selection = Mat::zeros (image.rows , image.cols , CV_8UC3);
699
699
700
700
double min, max;
701
701
minMaxIdx (labels, &min, &max); // find the highest superpixel number
@@ -705,11 +705,11 @@ void MainWindow::on_button_load_session_clicked() // load previous session
705
705
ui->label_image_height ->setText (QString::number (image.rows ));
706
706
707
707
SaveUndo (); // for undo
708
- loaded = true ;
708
+ loaded = true ; // done !
709
709
computed = true ; // not really computed but necessary
710
710
711
711
ui->comboBox_grid_color ->setCurrentIndex (gridValue); // update grid color in ui
712
- UnselectAllLabels ();
712
+ UnselectAllLabels (); // only the first label must be selected
713
713
ui->listWidget_labels ->setCurrentRow (0 );
714
714
715
715
// QMessageBox::information(this, "Load segmentation session", "Session loaded with base name:\n" + QString::fromStdString(filesession));
@@ -1293,7 +1293,7 @@ void MainWindow::on_pushButton_color_laurel_clicked() // Laurel
1293
1293
1294
1294
// ///////////////// Key events //////////////////////
1295
1295
1296
- void MainWindow::keyReleaseEvent (QKeyEvent *keyEvent) // draw cell mode : when spacebar is released
1296
+ void MainWindow::keyReleaseEvent (QKeyEvent *keyEvent) // draw cell mode and move view
1297
1297
{
1298
1298
if (keyEvent->key () == Qt::Key_Space) { // spacebar = move the view
1299
1299
QPoint mouse_pos = QCursor::pos (); // current mouse position
@@ -1303,7 +1303,7 @@ void MainWindow::keyReleaseEvent(QKeyEvent *keyEvent) // draw cell mode : when s
1303
1303
1304
1304
SetViewportXY (viewport.x - double (decX) / zoom, viewport.y - double (decY) / zoom); // update viewport
1305
1305
1306
- ShowSegmentation (); // display the result
1306
+ ShowSegmentation (); // display result
1307
1307
1308
1308
QApplication::restoreOverrideCursor (); // Restore cursor
1309
1309
}
@@ -1320,9 +1320,6 @@ void MainWindow::keyReleaseEvent(QKeyEvent *keyEvent) // draw cell mode : when s
1320
1320
QPoint mouse_pos = ui->label_segmentation ->mapFromGlobal (QCursor::pos ()); // current mouse position
1321
1321
cv::Point pos = Viewport2Image (cv::Point (mouse_pos.x (), mouse_pos.y ())); // convert position from viewport to image coordinates
1322
1322
1323
- if ((pos.x >= 0 ) & (pos.x < image.cols )
1324
- & (pos.y >= 0 ) & (pos.y < image.rows ))
1325
-
1326
1323
mask_line_save.copyTo (mask); // erase line (mouse position can have changed a bit
1327
1324
SaveUndo (); // for undo
1328
1325
@@ -1331,6 +1328,7 @@ void MainWindow::keyReleaseEvent(QKeyEvent *keyEvent) // draw cell mode : when s
1331
1328
1332
1329
mask.copyTo (mask_line_save); // save result for next line
1333
1330
pos_save = pos; // the last pixel is the new line origin
1331
+
1334
1332
}
1335
1333
}
1336
1334
}
@@ -1368,7 +1366,7 @@ void MainWindow::mousePressEvent(QMouseEvent *eventPress) // event triggered by
1368
1366
{
1369
1367
if (!loaded) return ; // no image = get out
1370
1368
1371
- if (ui->label_segmentation ->underMouse ()) { // if the mouse is over the viewport
1369
+ if (ui->label_segmentation ->underMouse ()) { // mouse over the viewport ?
1372
1370
bool key_control = QGuiApplication::queryKeyboardModifiers ().testFlag (Qt::ControlModifier); // modifier keys pressed ? (shift control etc)
1373
1371
bool key_alt = QGuiApplication::queryKeyboardModifiers ().testFlag (Qt::AltModifier);
1374
1372
@@ -1381,7 +1379,7 @@ void MainWindow::mousePressEvent(QMouseEvent *eventPress) // event triggered by
1381
1379
return ;
1382
1380
}
1383
1381
1384
- if ((computed) & (ui->Tabs ->currentIndex () == 2 )) { // in labels tab ?
1382
+ if ((computed) & (ui->Tabs ->currentIndex () == 2 )) { // mouse in labels tab ?
1385
1383
if ((key_alt) & (mouseButton == Qt::LeftButton) & (pos.x >= 0 ) & (pos.x < image.cols )
1386
1384
& (pos.y >= 0 ) & (pos.y < image.rows )) { // <alt> pressed at the same time = label selection
1387
1385
int value = labels_mask.at <int >(pos.y , pos.x ); // get label mask value
@@ -1495,7 +1493,7 @@ void MainWindow::mouseMoveEvent(QMouseEvent *eventMove) // first mouse click has
1495
1493
1496
1494
mouse_origin = mouse_pos; // save mouse position
1497
1495
}
1498
- else if ((computed) & (ui->Tabs ->currentIndex () == 2 )) {
1496
+ else if ((computed) & (ui->Tabs ->currentIndex () == 2 )) { // mouse over tab 2 ?
1499
1497
cv::Point pos = Viewport2Image (cv::Point (mouse_pos.x (), mouse_pos.y ())); // convert position from viewport to image coordinates
1500
1498
1501
1499
if (ui->pushButton_label_create ->isChecked ()) { // direct draw pixel for new label
@@ -1516,7 +1514,7 @@ void MainWindow::mouseMoveEvent(QMouseEvent *eventMove) // first mouse click has
1516
1514
1517
1515
ShowSegmentation (); // show result
1518
1516
}
1519
- else if ((pos.x >= 0 ) & (pos.x < image.cols )
1517
+ else if ((pos.x >= 0 ) & (pos.x < image.cols ) // define cell color
1520
1518
& (pos.y >= 0 ) & (pos.y < image.rows )){
1521
1519
// Color already set before ? saves CPU time
1522
1520
// Vec3b pixel = mask.at<Vec3b>(pos.y,pos.x); // find mask pixel color
@@ -1574,7 +1572,7 @@ void MainWindow::DisplayThumbnail() // image thumnail with transparent viewport
1574
1572
p1x = 0 ;
1575
1573
p2x = ui->label_thumbnail ->pixmap ()->width ();
1576
1574
}
1577
- else {
1575
+ else { // partial view
1578
1576
p1x = double (viewport.x ) / image.cols ;
1579
1577
p2x = p1x + double (viewport.width ) / image.cols ;
1580
1578
p1x *= double (ui->label_thumbnail ->pixmap ()->width ());
@@ -1585,16 +1583,15 @@ void MainWindow::DisplayThumbnail() // image thumnail with transparent viewport
1585
1583
p1y = 0 ;
1586
1584
p2y= ui->label_thumbnail ->pixmap ()->height ();
1587
1585
}
1588
- else {
1586
+ else { // partial view
1589
1587
p1y = double (viewport.y ) / image.rows ;
1590
1588
p2y = p1y + double (viewport.height ) / image.rows ;
1591
1589
p1y *= double (ui->label_thumbnail ->pixmap ()->height ());
1592
1590
p2y *= double (ui->label_thumbnail ->pixmap ()->height ());
1593
1591
}
1594
1592
1595
1593
Mat thumbnail_temp;
1596
- thumbnail.copyTo (thumbnail_temp);
1597
- thumbnail_temp = 0 ;
1594
+ Mat thumbnail_temp = Mat::zeros (thumbnail.rows , thumbnail.cols , CV_8UC3);
1598
1595
rectangle (thumbnail_temp, cv::Point (p1x, p1y), cv::Point (p2x-1 , p2y-1 ), Scalar (92 ,92 ,92 ), -1 ); // draw filled rectangle representing the viewport position
1599
1596
rectangle (thumbnail_temp, cv::Point (p1x, p1y), cv::Point (p2x-1 , p2y-1 ), Scalar (255 ,255 ,255 ), 2 ); // draw rectangle with thick border
1600
1597
cv::addWeighted (thumbnail, 1 , thumbnail_temp, 0.25 , 0 , thumbnail_temp, -1 ); // with transparency
@@ -1603,23 +1600,23 @@ void MainWindow::DisplayThumbnail() // image thumnail with transparent viewport
1603
1600
1604
1601
void MainWindow::UpdateViewportDimensions () // recomputes the viewport width and height
1605
1602
{
1606
- viewport.width = double (ui->label_segmentation ->width ()) / zoom;
1603
+ viewport.width = double (ui->label_segmentation ->width ()) / zoom; // viewport width
1607
1604
if (viewport.width > image.cols ) {
1608
1605
viewport.width = image.cols ;
1609
1606
viewport.x = 0 ;
1610
1607
}
1611
- viewport.height = double (ui->label_segmentation ->height ()) / zoom;
1608
+ viewport.height = double (ui->label_segmentation ->height ()) / zoom; // viewport height
1612
1609
if (viewport.height > image.rows ) {
1613
1610
viewport.height = image.rows ;
1614
1611
viewport.y = 0 ;
1615
1612
}
1616
- if (viewport.x > image.cols - viewport.width ) viewport.x = image.cols - viewport.width ;
1613
+ if (viewport.x > image.cols - viewport.width ) viewport.x = image.cols - viewport.width ; // stay within image
1617
1614
if (viewport.y > image.rows - viewport.height ) viewport.y = image.rows - viewport.height ;
1618
1615
}
1619
1616
1620
1617
void MainWindow::SetViewportXY (int x, int y) // set viewport top-left to (x,y) new coordinates
1621
1618
{
1622
- viewport.x = x;
1619
+ viewport.x = x; // coordinates
1623
1620
viewport.y = y;
1624
1621
if (viewport.x < 0 ) viewport.x = 0 ;
1625
1622
if (viewport.x > image.cols - viewport.width ) viewport.x = image.cols - viewport.width ;
@@ -1683,11 +1680,11 @@ void MainWindow::ShowSegmentation() // show image + mask + grid
1683
1680
if (ui->checkBox_holes ->isChecked () & (!mask.empty ())) {// show holes in mask
1684
1681
Mat holes = cv::Mat::zeros (mask.rows , mask.cols , CV_8UC3); // to draw the holes
1685
1682
Mat1b holes_mask;
1686
- cv::inRange (mask, Vec3b (0 ,0 ,0 ), Vec3b (0 ,0 ,0 ), holes_mask); // extract mask = 0
1683
+ cv::inRange (mask, Vec3b (0 ,0 ,0 ), Vec3b (0 ,0 ,0 ), holes_mask); // extract mask = unset label zones
1687
1684
holes.setTo (Vec3b (255 ,255 ,255 ), holes_mask); // draw holes in white
1688
1685
cv::addWeighted (disp_color, 1 ,
1689
1686
CopyFromImage (holes, viewport), 1 ,
1690
- 0 , disp_color, -1 );
1687
+ 0 , disp_color, -1 ); // show the mask over the whole display
1691
1688
}
1692
1689
1693
1690
// display the viewport
@@ -1849,8 +1846,7 @@ void MainWindow::on_button_compute_clicked() // compute segmentation
1849
1846
seeds->getLabelContourMask (maskTemp, !ui->checkBox_thick ->isChecked ()); // contours
1850
1847
}
1851
1848
1852
- labels.copyTo (labels_mask);
1853
- labels_mask = 0 ;
1849
+ labels_mask = Mat::zeros (labels.rows , labels.cols , CV_8UC3); // new labels mask
1854
1850
1855
1851
// contours for displaying : grid & mask initialization
1856
1852
cv::cvtColor (maskTemp, mask, CV_GRAY2RGB); // at first the mask contains the grid, need to convert labels from gray to RGB
@@ -1866,7 +1862,7 @@ void MainWindow::on_button_compute_clicked() // compute segmentation
1866
1862
// convert the image to a QPixmap and display it
1867
1863
ShowSegmentation (); // update display
1868
1864
1869
- ui->Tabs ->setTabEnabled (2 , true );
1865
+ ui->Tabs ->setTabEnabled (2 , true ); // computed = we can edit labels
1870
1866
1871
1867
QApplication::restoreOverrideCursor (); // Restore cursor
1872
1868
}
0 commit comments