I am trying to measure diameter of holes on the button with DIPlib image processing library. I use GreyDimensionsEllipsoid and Mass to calculate diameter.
GreyDimensionsEllipsoid gave very precise results for hole diameters but Mass gave incorrect measurement results What am I doing wrong? You can see below my code
std::string fname = "/Users/tcc/Documents/ilk/ilk/cam1/125.jpg";
dip::Image img = dip::ImageReadJPEG(fname);
dip::ColorSpaceManager csm;
csm.Convert(img, img, "grey");
dip::Image binary;
dip::FixedThreshold(img, binary, 70, 0, 1);
dip::BinaryAreaOpening(binary, binary, 10000);
binary = ~binary;
dip::Image holes;
dip::EdgeObjectsRemove(binary, holes);
dip::Image labeledHoles;
dip::uint holeQty = dip::Label(holes, labeledHoles);
holes.Convert(dip::DT_UINT8);
dip::ChainCodeArray holeContours = dip::GetImageChainCodes(labeledHoles);
dip::MeasurementTool measurementTool;
auto holeMsr = measurementTool.Measure(
labeledHoles, labeledHoles,
{ "Mass", "Gravity", "GreyDimensionsEllipsoid", "Circularity" } );
for (dip::uint i = 1; i <= holeQty; i++)
{
double holeArea = holeMsr[ i ][ "Mass" ][ 0 ] ;
double holeDiameter = 2 * std::sqrt( holeArea / dip::pi );
double holeCentroidX = holeMsr[ i ][ "Gravity" ][ 0 ];
double holeCentroidY = holeMsr[ i ][ "Gravity" ][ 1 ];
double holeMajorAxis = holeMsr[ i ][ "GreyDimensionsEllipsoid" ][ 0 ]/2;
double holeMinorAxis = holeMsr[ i ][ "GreyDimensionsEllipsoid" ][ 1 ]/2;
double holeRoundness = holeMsr[ i ][ "Circularity" ][ 0 ];
// Output hole measurements
std::cout << i << " Diplib area base hole diameter : " << std::setprecision(15) << std::sqrt( holeArea / dip::pi ) * 2 << std::endl;
std::cout << i << " Diplib FitEllips base hole average diameter : " << std::setprecision(15) << (holeMinorAxis+holeMajorAxis) << std::endl;
}
To compute the area, use the “Size” feature (it counts pixels). “Mass” sums the gray-values over the area, and since you input the labeled image as the gray-scale image (the second input to measurementTool.Measure()
), what you get is the area multiplied by the label number.