图像的ROI(region of interest)是指图像中感兴趣区域。在OpenCV中图像设置图像ROI区域,实现只对ROI区域操作。
文章目录
- 前言
- 一、GUI
- 二、实现代码
- 1、Rubber
- 2、ROI
- 总结
前言
越来越多的开发人员选择基于开源的Qt框架与OpenCV来实现界面和算法,其原因不单单是无版权问题,更多是两个社区的发展蓬勃,可用来学习的资料与例程特别丰富。以下是关于利用Qt的rubberBand和OpenCV进行图像的ROI区域获取
软件版本:Qt-5.12.0/OpenCV-4.5.3
平台:Windows10/11–64
一、GUI
二、实现代码
1、Rubber
void MainWindow::on_graphicsView_1_rubberBandChanged(const QRect &viewportRect, const QPointF &fromScenePoint, const QPointF &toScenePoint)
{
rubberFunc(viewportRect, fromScenePoint, toScenePoint);
}
void MainWindow::rubberFunc(const QRect &viewportRect, const QPointF &fromScenePoint, const QPointF &toScenePoint)
{
size_t numView = ui->tabWidget->currentIndex() % 3;
QPoint topLeft = viewportRect.topLeft();
int x1 = topLeft.x();
double xFromScene = fromScenePoint.x();
double yFromScene = fromScenePoint.y();
double xToScene = toScenePoint.x();
double yToScene = toScenePoint.y();
if (x1 != 0)
{
ui->rubberX1Spin->setValue(static_cast<int>(xFromScene));
ui->rubberY1Spin->setValue(static_cast<int>(yFromScene));
ui->rubberX2Spin->setValue(static_cast<int>(xToScene));
ui->rubberY2Spin->setValue(static_cast<int>(yToScene));
*tmpMat = dispMat[numView]->clone();
cv::rectangle(*tmpMat, cv::Point(static_cast<int>(xFromScene), static_cast<int>(yFromScene)), \
cv::Point(static_cast<int>(xToScene), \
static_cast<int>(yToScene)), \
cv::Scalar(0, 0, 255), 1, 1, 0);
}
if (tmpMat->channels() == 3)
{
QImage tmpImage = QImage(tmpMat->data, tmpMat->cols,tmpMat->rows, \
static_cast<int>(tmpMat->step), \
QImage::Format_RGB888);
dispPixmap[numView]->setPixmap(QPixmap::fromImage(tmpImage.rgbSwapped()));
}
else
{
QImage tmpImage = QImage(tmpMat->data, tmpMat->cols,tmpMat->rows, \
static_cast<int>(tmpMat->step), \
QImage::Format_Grayscale8);
dispPixmap[numView]->setPixmap(QPixmap::fromImage(tmpImage.rgbSwapped()));
}
}
2、ROI
void MainWindow::on_maskBtn_clicked()
{
size_t numView = ui->tabWidget->currentIndex() % 3;
int x1 = ui->roiX1Spin->value();
int y1 = ui->roiY1Spin->value();
int x2 = ui->roiX2Spin->value();
int y2 = ui->roiY2Spin->value();
if ((x1 == 0)&&(y1 == 0)&&(x2 == 0)&&(y2 == 0))
{
outputInfo(2, tr("Please check the Points."));
return;
}
cv::Rect maskRect(x1, y1, x2 - x1, y2 - y1);
cv::Mat maskMat = cv::Mat::zeros(dispMat[numView]->size(), \
CV_8UC1);
tmpMat->zeros(dispMat[numView]->size(), \
dispMat[numView]->type());
maskMat(maskRect).setTo(255);
dispMat[numView]->copyTo(*tmpMat, maskMat);
if (ui->roiChkBox->isChecked())
{
*dispMat[numView] = tmpMat->clone();
cvtMatPixmap(dispMat, dispPixmap, numView);
}
else
{
if (tmpMat->channels() == 3)
{
QImage tmpImage = QImage(tmpMat->data, tmpMat->cols,tmpMat->rows, \
static_cast<int>(tmpMat->step), \
QImage::Format_RGB888);
dispPixmap[numView]->setPixmap(QPixmap::fromImage(tmpImage.rgbSwapped()));
}
else
{
QImage tmpImage = QImage(tmpMat->data, tmpMat->cols,tmpMat->rows, \
static_cast<int>(tmpMat->step), \
QImage::Format_Grayscale8);
dispPixmap[numView]->setPixmap(QPixmap::fromImage(tmpImage.rgbSwapped()));
}
}
outputInfo(1, tr("Mask done."));
}
void MainWindow::on_roiBtn_clicked()
{
size_t numView = ui->tabWidget->currentIndex() % 3;
int x1 = ui->roiX1Spin->value();
int y1 = ui->roiY1Spin->value();
int x2 = ui->roiX2Spin->value();
int y2 = ui->roiY2Spin->value();
if ((x1 == 0)&&(y1 == 0)&&(x2 == 0)&&(y2 == 0))
{
outputInfo(2, tr("Please check the Points."));
return;
}
cv::Rect maskRect(x1, y1, x2 - x1, y2 - y1);
cv::Mat roiMat = (*dispMat[numView])(maskRect);
*tmpMat = roiMat.clone();
if (ui->roiChkBox->isChecked())
{
*dispMat[numView] = tmpMat->clone();
cvtMatPixmap(dispMat, dispPixmap, numView);
}
else
{
if (tmpMat->channels() == 3)
{
QImage tmpImage = QImage(tmpMat->data, tmpMat->cols,tmpMat->rows, \
static_cast<int>(tmpMat->step), \
QImage::Format_RGB888);
dispPixmap[numView]->setPixmap(QPixmap::fromImage(tmpImage.rgbSwapped()));
}
else
{
QImage tmpImage = QImage(tmpMat->data, tmpMat->cols,tmpMat->rows, \
static_cast<int>(tmpMat->step), \
QImage::Format_Grayscale8);
dispPixmap[numView]->setPixmap(QPixmap::fromImage(tmpImage.rgbSwapped()));
}
}
outputInfo(1, tr("roiMat done."));
}
总结
以上是关于利用Qt进行GUI构建并使用rubberBandChanged进行roi区域获取,或者直接使用OpenCV的roiMat()进行感兴趣区域获取。
参考:
链接:前期其中疑问或错误,欢迎联系交流