#include <mil.h>
#include <malloc.h>
#define IMAGE_FILE M_IMAGE_PATH MIL_TEXT("BoltsNutsWashers.mim")
#define IMAGE_THRESHOLD_VALUE 26L
#define MIN_BLOB_AREA 50L
#define MAX_BLOB_AREA 50000L
#define MIN_BLOB_RADIUS 3L
#define MIN_COMPACTNESS 1.5
int MosMain(void)
{
MIL_ID MilApplication,
MilSystem,
MilDisplay,
MilImage,
MilGraphicList,
MilBinImage,
MilBlobResult,
MilBlobFeatureList;
MIL_INT TotalBlobs,
BlobsWithHoles,
BlobsWithRoughHoles,
n,
SizeX,
SizeY;
MIL_DOUBLE *CogX,
*CogY;
MappAllocDefault(M_DEFAULT, &MilApplication, &MilSystem, &MilDisplay, M_NULL, M_NULL);
MbufRestore(IMAGE_FILE, MilSystem, &MilImage);
MgraAllocList(MilSystem, M_DEFAULT, &MilGraphicList);
MdispControl(MilDisplay, M_ASSOCIATED_GRAPHIC_LIST_ID, MilGraphicList);
MdispSelect(MilDisplay, MilImage);
MbufInquire(MilImage, M_SIZE_X, &SizeX);
MbufInquire(MilImage, M_SIZE_Y, &SizeY);
MbufAlloc2d(MilSystem, SizeX, SizeY, 1+M_UNSIGNED, M_IMAGE+M_PROC, &MilBinImage);
MosPrintf(MIL_TEXT("\nBLOB ANALYSIS:\n"));
MosPrintf(MIL_TEXT("--------------\n\n"));
MosPrintf(MIL_TEXT("This program determines the number of bolts, nuts and washers\n"));
MosPrintf(MIL_TEXT("in the image and finds their center of gravity.\n"));
MosPrintf(MIL_TEXT("Press <Enter> to continue.\n\n"));
MosGetch();
MimBinarize(MilImage, MilBinImage, M_FIXED+M_GREATER_OR_EQUAL,
IMAGE_THRESHOLD_VALUE, M_NULL);
MimOpen(MilBinImage, MilBinImage, MIN_BLOB_RADIUS, M_BINARY);
MimClose(MilBinImage, MilBinImage, MIN_BLOB_RADIUS, M_BINARY);
MblobAllocFeatureList(MilSystem, &MilBlobFeatureList);
MblobSelectFeature(MilBlobFeatureList, M_AREA);
MblobSelectFeature(MilBlobFeatureList, M_CENTER_OF_GRAVITY);
MblobAllocResult(MilSystem, &MilBlobResult);
MblobCalculate(MilBinImage, M_NULL, MilBlobFeatureList, MilBlobResult);
MblobSelect(MilBlobResult, M_EXCLUDE, M_AREA, M_LESS_OR_EQUAL,
MIN_BLOB_AREA, M_NULL);
MblobGetNumber(MilBlobResult, &TotalBlobs);
MosPrintf(MIL_TEXT("There are %ld objects "), TotalBlobs);
if ((CogX = (MIL_DOUBLE *)malloc(TotalBlobs*sizeof(MIL_DOUBLE))) &&
(CogY = (MIL_DOUBLE *)malloc(TotalBlobs*sizeof(MIL_DOUBLE)))
)
{
MblobGetResult(MilBlobResult, M_CENTER_OF_GRAVITY_X, CogX);
MblobGetResult(MilBlobResult, M_CENTER_OF_GRAVITY_Y, CogY);
MosPrintf(MIL_TEXT("and their centers of gravity are:\n"));
for(n=0; n < TotalBlobs; n++)
MosPrintf(MIL_TEXT("Blob #%ld: X=%5.1f, Y=%5.1f\n"), n, CogX[n], CogY[n]);
free(CogX);
free(CogY);
}
else
MosPrintf(MIL_TEXT("\nError: Not enough memory.\n"));
MgraColor(M_DEFAULT, M_COLOR_RED);
MblobDraw(M_DEFAULT, MilBlobResult, MilGraphicList, M_DRAW_CENTER_OF_GRAVITY,
M_INCLUDED_BLOBS, M_DEFAULT);
MblobControl(MilBlobResult, M_FOREGROUND_VALUE, M_ZERO);
MblobSelectFeature(MilBlobFeatureList, M_COMPACTNESS);
MblobCalculate(MilBinImage, M_NULL, MilBlobFeatureList, MilBlobResult);
MblobSelect(MilBlobResult, M_EXCLUDE, M_AREA, M_OUT_RANGE,
MIN_BLOB_AREA, MAX_BLOB_AREA);
MblobGetNumber(MilBlobResult, &BlobsWithHoles);
MblobSelect(MilBlobResult, M_EXCLUDE, M_COMPACTNESS, M_LESS_OR_EQUAL,
MIN_COMPACTNESS, M_NULL);
MblobGetNumber(MilBlobResult, &BlobsWithRoughHoles);
MosPrintf(MIL_TEXT("\nIdentified objects:\n"));
MosPrintf(MIL_TEXT("%ld bolts\n"), TotalBlobs-BlobsWithHoles);
MosPrintf(MIL_TEXT("%ld nuts\n"), BlobsWithHoles - BlobsWithRoughHoles);
MosPrintf(MIL_TEXT("%ld washers\n\n"), BlobsWithRoughHoles);
MosPrintf(MIL_TEXT("Press <Enter> to end.\n\n"));
MosGetch();
MgraFree(MilGraphicList);
MblobFree(MilBlobResult);
MblobFree(MilBlobFeatureList);
MbufFree(MilBinImage);
MbufFree(MilImage);
MappFreeDefault(MilApplication, MilSystem, MilDisplay, M_NULL, M_NULL);
return 0;
}