|
|
@@ -1312,9 +1312,9 @@ namespace OTSIMGPROC
|
|
|
Mat cvcopyImg = Mat(nHeightImg, nWidthImg, CV_8UC1, pPixel);
|
|
|
//Mat blurImg;
|
|
|
//medianBlur(cvcopyImg, blurImg, 5);//get rid of the noise point.
|
|
|
-
|
|
|
- Mat labels, stats, centroids;
|
|
|
- int number = connectedComponentsWithStats(cvcopyImg, labels, stats, centroids, 8, CV_16U);
|
|
|
+ Mat labels = Mat::zeros(cvcopyImg.size(), CV_32S);
|
|
|
+ Mat stats, centroids;
|
|
|
+ int number = connectedComponentsWithStats(cvcopyImg, labels, stats, centroids, 8, CV_32S);
|
|
|
|
|
|
double rMin = a_pImageProcessParam->GetIncArea().GetStart()/2.0;
|
|
|
double rMax = a_pImageProcessParam->GetIncArea().GetEnd()/2.0;
|
|
|
@@ -1341,31 +1341,55 @@ namespace OTSIMGPROC
|
|
|
|
|
|
|
|
|
Rect rectMax = Rect(x, y, w, h);
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
Mat rectROI = labels(rectMax).clone();
|
|
|
- Mat imageROI = cvcopyImg(rectMax).clone();
|
|
|
+ Mat imageROI = Mat::zeros(rectMax.size(), cvcopyImg.type());
|
|
|
|
|
|
//exclude the point which intersect into this bounding box but is not in this group.
|
|
|
- int curlabel = i;
|
|
|
- for (int nX = 0; nX < rectROI.rows; nX++)
|
|
|
+ int label = i;
|
|
|
+ for (int row = 0; row < rectROI.rows; row++)
|
|
|
{
|
|
|
- for (int nY = 0; nY < rectROI.cols; nY++)
|
|
|
+ for (int col = 0; col < rectROI.cols; col++)
|
|
|
{
|
|
|
- int v = rectROI.data[nX, nY];
|
|
|
-
|
|
|
- if (v == curlabel)
|
|
|
+ int v = rectROI.at<int>(row, col);
|
|
|
+
|
|
|
+ if (v == label)
|
|
|
{
|
|
|
- imageROI.data[nX, nY] = 255;
|
|
|
+ imageROI.at<uchar>(row, col) = 255;
|
|
|
}
|
|
|
else
|
|
|
{
|
|
|
- imageROI.data[nX, nY] = 0;//set the value to 0,so we won't consider it when we find segment and feature in this ROI.
|
|
|
+ imageROI.at<uchar>(row, col) = 0;//set the value to 0,so we won't consider it when we find segment and feature in this ROI.
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
-
|
|
|
+ //COTSParticleList listParticleInROI;
|
|
|
GetParticles(rectMax.x, rectMax.y, rectMax.width, rectMax.height, imageROI.data, listParticleOut);
|
|
|
+
|
|
|
+ //if (listParticleInROI.size() >= 1)
|
|
|
+ //{
|
|
|
+ //
|
|
|
+ // //find the biggest particle in this group.
|
|
|
+ // COTSParticlePtr bigP = listParticleInROI[0];
|
|
|
+ // for (auto p : listParticleInROI)
|
|
|
+ // {
|
|
|
+ // //double partArea = p->GetArea()* a_pixelSize* a_pixelSize;
|
|
|
+ // if (p->GetArea() > bigP->GetArea())
|
|
|
+ // {
|
|
|
+ // bigP = p;
|
|
|
+ // }
|
|
|
+ // /*if (partArea >= partAreaMin && partArea < partAreaMax)
|
|
|
+ // {
|
|
|
+ // listParticleOut.push_back(p);
|
|
|
+ // }*/
|
|
|
+ // }
|
|
|
+ // listParticleOut.push_back(bigP);
|
|
|
+
|
|
|
+ //}
|
|
|
|
|
|
}
|
|
|
|
|
|
@@ -1403,7 +1427,7 @@ namespace OTSIMGPROC
|
|
|
}
|
|
|
BYTE nAveGray = (BYTE)(nPixelAll / nPixelNum);
|
|
|
pParticle->SetAveGray(nAveGray);
|
|
|
- pParticle->SetArea(nPixelNum);
|
|
|
+
|
|
|
|
|
|
|
|
|
}
|
|
|
@@ -1416,7 +1440,7 @@ namespace OTSIMGPROC
|
|
|
|
|
|
return TRUE;
|
|
|
}
|
|
|
- BOOL COTSImageProcess::GetParticlesBySpecialGrayRange(CBSEImgPtr a_pBSEImg, CIntRangePtr a_grayRange, COTSFieldDataPtr m_pFieldData)
|
|
|
+ BOOL COTSImageProcess::GetParticlesBySpecialGrayRange(CBSEImgPtr a_pBSEImg, CIntRangePtr a_grayRange,CIntRangePtr a_diameterRange,double a_pixelSize, COTSFieldDataPtr m_pFieldData)
|
|
|
{
|
|
|
ASSERT(m_pFieldData);
|
|
|
|
|
|
@@ -1465,14 +1489,16 @@ namespace OTSIMGPROC
|
|
|
|
|
|
|
|
|
Mat cvcopyImg = Mat(nHeightImg, nWidthImg, CV_8UC1, pPixel);
|
|
|
- //Mat blurImg;
|
|
|
- //medianBlur(cvcopyImg, blurImg, 3);//smooth the edge
|
|
|
-
|
|
|
-
|
|
|
- Mat labels, stats, centroids;
|
|
|
- int number = connectedComponentsWithStats(cvcopyImg, labels, stats, centroids, 8, CV_16U);
|
|
|
+
|
|
|
|
|
|
+ Mat labels = Mat::zeros(cvcopyImg.size(), CV_32S);
|
|
|
+ Mat stats, centroids;
|
|
|
+ int number = connectedComponentsWithStats(cvcopyImg, labels, stats, centroids, 8, CV_32S);
|
|
|
|
|
|
+ double rStart = a_diameterRange->GetStart() / 2.0;
|
|
|
+ double rEnd = a_diameterRange->GetEnd() / 2.0;
|
|
|
+ double areaStart = rStart * rStart * 3.14159;
|
|
|
+ double areaEnd = rEnd * rEnd * 3.14159;
|
|
|
|
|
|
COTSParticleList listParticleOut;
|
|
|
for (size_t i = 1; i < number; i++)
|
|
|
@@ -1486,99 +1512,111 @@ namespace OTSIMGPROC
|
|
|
int h = stats.at<int>(i, CC_STAT_HEIGHT);
|
|
|
int area = stats.at<int>(i, CC_STAT_AREA);
|
|
|
|
|
|
+ double actualArea = area * a_pixelSize * a_pixelSize;
|
|
|
|
|
|
+
|
|
|
|
|
|
- Rect rectMax = Rect(x, y, w, h);
|
|
|
- Mat rectROI = labels(rectMax).clone();
|
|
|
- Mat imageROI = cvcopyImg(rectMax).clone();
|
|
|
-
|
|
|
- //exclude the point which intersect into this bounding box but is not in this group.
|
|
|
- int label = i;
|
|
|
- for (int nX = 0; nX < rectROI.rows; nX++)
|
|
|
+ if (actualArea >= areaStart && actualArea < areaEnd)
|
|
|
{
|
|
|
- for (int nY = 0; nY < rectROI.cols; nY++)
|
|
|
- {
|
|
|
- int v = rectROI.data[nX, nY];
|
|
|
+ Rect rectMax = Rect(x, y, w, h);
|
|
|
+
|
|
|
+
|
|
|
|
|
|
- if (v == label)
|
|
|
- {
|
|
|
- imageROI.data[nX, nY] = 255;
|
|
|
- }
|
|
|
- else
|
|
|
+ Mat rectROI = labels(rectMax).clone();
|
|
|
+ Mat imageROI = Mat::zeros(rectMax.size(), cvcopyImg.type());
|
|
|
+
|
|
|
+ //exclude the point which intersect into this bounding box but is not in this group.
|
|
|
+ int label = i;
|
|
|
+ for (int row = 0; row < rectROI.rows; row++)
|
|
|
+ {
|
|
|
+ for (int col = 0; col < rectROI.cols; col++)
|
|
|
{
|
|
|
- imageROI.data[nX, nY] = 0;//set the value to 0,so we won't consider it when we find segment and feature in this ROI.
|
|
|
+ int v = rectROI.at<int>(row, col);
|
|
|
+
|
|
|
+ if (v == label)
|
|
|
+ {
|
|
|
+ imageROI.at<uchar>(row, col) = 255;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ imageROI.at<uchar>(row, col) = 0;//set the value to 0,so we won't consider it when we find segment and feature in this ROI.
|
|
|
+ }
|
|
|
+
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
- }
|
|
|
|
|
|
- GetParticles(rectMax.x, rectMax.y, rectMax.width, rectMax.height, imageROI.data, listParticleOut);
|
|
|
+
|
|
|
+
|
|
|
+ //COTSParticleList listParticleInROI;
|
|
|
+ GetParticles(rectMax.x, rectMax.y, rectMax.width, rectMax.height, imageROI.data, listParticleOut);//We will find more than one particle in one ROI. and We cann't decide which are the valid and not valid.So we will do another filter again later.
|
|
|
+ //if (listParticleInROI.size() >= 1)
|
|
|
+ //{
|
|
|
+ // //find the biggest particle in this group.
|
|
|
+ // COTSParticlePtr bigP = listParticleInROI[0];
|
|
|
+ // for (auto p : listParticleInROI)
|
|
|
+ // {
|
|
|
+ // if (p->GetArea() > bigP->GetArea())
|
|
|
+ // {
|
|
|
+ // bigP = p;
|
|
|
+ // }
|
|
|
+ // }
|
|
|
+ // listParticleOut.push_back(bigP);
|
|
|
+
|
|
|
+ //}
|
|
|
+ }
|
|
|
+
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// form a image only have particles on
|
|
|
- COTSSegmentsList listImage;
|
|
|
+ //COTSSegmentsList listImage;
|
|
|
+ COTSParticleList listParticleOut2;
|
|
|
for (auto pParticle : listParticleOut)
|
|
|
{
|
|
|
- COTSFeaturePtr pFeature = pParticle->GetFeature();
|
|
|
- COTSSegmentsList listSegment = pFeature->GetSegmentsList();
|
|
|
-
|
|
|
- long nPixelNum = 0;
|
|
|
- long nPixelAll = 0;
|
|
|
- int nStartS = 0;
|
|
|
- int nHeightS = 0;
|
|
|
- int nLengthS = 0;
|
|
|
- for (auto pSegment : listSegment)
|
|
|
+ int area = pParticle->GetArea();
|
|
|
+ double pActualArea = area * a_pixelSize * a_pixelSize;
|
|
|
+ if (pActualArea >= areaStart && pActualArea < areaEnd)// do the second filter to remove invalid particles.
|
|
|
{
|
|
|
- // update image list
|
|
|
- COTSSegmentPtr pSegNew = COTSSegmentPtr(new COTSSegment(*pSegment.get()));
|
|
|
- listImage.push_back(pSegNew);
|
|
|
+ COTSFeaturePtr pFeature = pParticle->GetFeature();
|
|
|
+ COTSSegmentsList listSegment = pFeature->GetSegmentsList();
|
|
|
|
|
|
+ long nPixelNum = 0;
|
|
|
+ long nPixelAll = 0;
|
|
|
+ int nStartS = 0;
|
|
|
+ int nHeightS = 0;
|
|
|
+ int nLengthS = 0;
|
|
|
+ for (auto pSegment : listSegment)
|
|
|
+ {
|
|
|
|
|
|
- // get particle average gray
|
|
|
- nStartS = pSegment->GetStart();
|
|
|
- nHeightS = pSegment->GetHeight();
|
|
|
- nLengthS = pSegment->GetLength();
|
|
|
- nPixelNum += (long)nLengthS;
|
|
|
+ // get particle average gray
|
|
|
+ nStartS = pSegment->GetStart();
|
|
|
+ nHeightS = pSegment->GetHeight();
|
|
|
+ nLengthS = pSegment->GetLength();
|
|
|
+ nPixelNum += (long)nLengthS;
|
|
|
|
|
|
|
|
|
- if (nHeightS > nHeightImg)
|
|
|
- {
|
|
|
- //LogErrorTrace(__FILE__, __LINE__, _T("seg height is wrong."));
|
|
|
- return FALSE;
|
|
|
- }
|
|
|
- if ((nStartS + nLengthS - 1) > nWidthImg)
|
|
|
- {
|
|
|
- //LogErrorTrace(__FILE__, __LINE__, _T("seg starst and length is wrong."));
|
|
|
- return FALSE;
|
|
|
- }
|
|
|
-
|
|
|
- for (unsigned int i = 0; i < nLengthS; i++)
|
|
|
- {
|
|
|
- if ((nStartS + i) > nWidthImg)
|
|
|
- {
|
|
|
- //LogErrorTrace(__FILE__, __LINE__, _T("seg start is wrong."));
|
|
|
- return FALSE;
|
|
|
- }
|
|
|
- else if (nHeightS > nHeightImg)
|
|
|
+ for (unsigned int i = 0; i < nLengthS; i++)
|
|
|
{
|
|
|
- //LogErrorTrace(__FILE__, __LINE__, _T("seg height is wrong."));
|
|
|
- return FALSE;
|
|
|
- }
|
|
|
|
|
|
- long nValueTemp = (long)*(pSrcImg + nHeightS * nWidthImg + nStartS + i);
|
|
|
- nPixelAll += nValueTemp;
|
|
|
+
|
|
|
+ long nValueTemp = (long)*(pSrcImg + nHeightS * nWidthImg + nStartS + i);
|
|
|
+ nPixelAll += nValueTemp;
|
|
|
+ }
|
|
|
}
|
|
|
+ BYTE nAveGray = (BYTE)(nPixelAll / nPixelNum);
|
|
|
+ pParticle->SetAveGray(nAveGray);
|
|
|
+
|
|
|
+ listParticleOut2.push_back(pParticle);
|
|
|
}
|
|
|
- BYTE nAveGray = (BYTE)(nPixelAll / nPixelNum);
|
|
|
- pParticle->SetAveGray(nAveGray);
|
|
|
- pParticle->SetArea(nPixelNum);
|
|
|
+
|
|
|
+
|
|
|
|
|
|
}
|
|
|
- m_pFieldData->SetParticleList(listParticleOut);
|
|
|
+ m_pFieldData->SetParticleList(listParticleOut2);
|
|
|
}
|
|
|
|
|
|
|
|
|
@@ -1714,9 +1752,10 @@ namespace OTSIMGPROC
|
|
|
}
|
|
|
/*COTSImageProcess::BErode3(pPixel, pTempImg, 5, nHeightImg, nWidthImg);
|
|
|
COTSImageProcess::BDilate3(pTempImg, pPixel, 5, nHeightImg, nWidthImg);*/
|
|
|
- Mat cvcopyImg = Mat(nHeightImg, nWidthImg, CV_8UC1, pPixel);// use the medianblur method to achieve the same effect as open morphology(errod and dialate).
|
|
|
- medianBlur(cvcopyImg, cvcopyImg, 3);
|
|
|
- pPixel = cvcopyImg.data;
|
|
|
+
|
|
|
+ //Mat cvcopyImg = Mat(nHeightImg, nWidthImg, CV_8UC1, pPixel);// use the medianblur method to achieve the same effect as open morphology(errod and dialate).
|
|
|
+ //medianBlur(cvcopyImg, cvcopyImg, 3);
|
|
|
+ //pPixel = cvcopyImg.data;
|
|
|
a_pBinImgOut->SetImageData(pPixel, nWidthImg, nHeightImg);
|
|
|
|
|
|
foundedPixelNum = nNumParticle;
|
|
|
@@ -1774,11 +1813,11 @@ namespace OTSIMGPROC
|
|
|
pPixel[i] = 0;
|
|
|
}
|
|
|
}
|
|
|
- COTSImageProcess::BErode3(pPixel, pTempImg, 3, nHeightImg, nWidthImg);
|
|
|
- COTSImageProcess::BDilate3(pTempImg, pPixel, 3, nHeightImg, nWidthImg);
|
|
|
- Mat cvcopyImg = Mat(nHeightImg, nWidthImg, CV_8UC1, pPixel);// use the medianblur method to achieve the same effect as open morphology(errod and dialate).
|
|
|
- medianBlur(cvcopyImg, cvcopyImg, 5);
|
|
|
- pPixel = cvcopyImg.data;
|
|
|
+ //COTSImageProcess::BErode3(pPixel, pTempImg, 3, nHeightImg, nWidthImg);
|
|
|
+ //COTSImageProcess::BDilate3(pTempImg, pPixel, 3, nHeightImg, nWidthImg);
|
|
|
+ //Mat cvcopyImg = Mat(nHeightImg, nWidthImg, CV_8UC1, pPixel);// use the medianblur method to achieve the same effect as open morphology(errod and dialate).
|
|
|
+ //medianBlur(cvcopyImg, cvcopyImg, 5);
|
|
|
+ //pPixel = cvcopyImg.data;
|
|
|
|
|
|
|
|
|
}
|
|
|
@@ -1838,11 +1877,11 @@ namespace OTSIMGPROC
|
|
|
default:
|
|
|
break;
|
|
|
}
|
|
|
- COTSImageProcess::BErode3(pPixel, pTempImg, 3, nHeightImg, nWidthImg);
|
|
|
+ /*COTSImageProcess::BErode3(pPixel, pTempImg, 3, nHeightImg, nWidthImg);
|
|
|
COTSImageProcess::BDilate3(pTempImg, pPixel, 3, nHeightImg, nWidthImg);
|
|
|
Mat cvcopyImg = Mat(nHeightImg, nWidthImg, CV_8UC1, pPixel);
|
|
|
medianBlur(cvcopyImg, cvcopyImg, 5);
|
|
|
- pPixel = cvcopyImg.data;
|
|
|
+ pPixel = cvcopyImg.data;*/
|
|
|
}
|
|
|
a_pBinImgOut->SetImageData(pPixel,nWidthImg,nHeightImg);
|
|
|
|
|
|
@@ -2079,6 +2118,21 @@ namespace OTSIMGPROC
|
|
|
{
|
|
|
return FALSE;
|
|
|
}
|
|
|
+
|
|
|
+ COTSSegmentsList listSegment = pFeature->GetSegmentsList();
|
|
|
+
|
|
|
+ long nPixelNum = 0;
|
|
|
+
|
|
|
+ int nLengthS = 0;
|
|
|
+ for (auto pSegment : listSegment)
|
|
|
+ {
|
|
|
+
|
|
|
+ nLengthS = pSegment->GetLength();
|
|
|
+ nPixelNum += (long)nLengthS;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ pParticle->SetArea(nPixelNum);
|
|
|
a_listParticle.push_back(pParticle);
|
|
|
}
|
|
|
|