L_LTIMGCOR_API L_INT L_ExtractObjectsBitmap(pBitmap, pOptions, pData)
Extracts the connected groups of pixels from a bitmap using various options.
Pointer to the bitmap handle that references the bitmap to be processed.
Extraction options. This value cannot be null.
Pointer to be updated with the extracted objects.
Value | Meaning |
---|---|
SUCCESS | The function was successful. |
< 1 | An error occurred. Refer to Return Codes. |
Win32, x64, Linux.
This example shows how to use the various object extraction functions.
L_INT ExtractObjectsBitmapExample(L_VOID)
{
L_INT nRet = SUCCESS;
BITMAPHANDLE InputBitmap = { 0 };
BITMAPHANDLE OutputBitmap = { 0 };
pEXOBJ_DATA pData = NULL;
EXOBJ_OPTIONS ExtractOptions = { 0 };
EXOBJ_FILTER_OPTIONS FilterOptions = { 0 };
EXOBJ_CONTENTBOUND ContentBound = { 0 };
EXOBJ_CONTENTBOUND_OPTIONS ContentBoundOptions = { 0 };
EXOBJ_REGION_OPTIONS RegionOptions = { 0 };
pEXOBJ_OBJECT *pObjectArray = NULL; // Temporary array for L_ExtractObjects_CalcRegion
pEXOBJ_OBJECTLIST pObjectList = NULL; // Temporary variable for iterating
// Load the original image
nRet = L_LoadBitmap(MAKE_IMAGE_PATH(TEXT("demoicr2.tif")), &InputBitmap, sizeof(BITMAPHANDLE), 0, ORDER_BGRORGRAY, NULL, NULL);
if (nRet != SUCCESS)
goto cleanup;
// Setup the extraction options
ExtractOptions.uStructSize = sizeof(EXOBJ_OPTIONS);
ExtractOptions.uFlags = EXOBJ_8_CONNECTIVITY | EXOBJ_DETECT_CHILDREN | EXOBJ_OUTLINE;
// Extract the objects
nRet = L_ExtractObjectsBitmap(&InputBitmap, &ExtractOptions, &pData);
if (nRet != SUCCESS)
goto cleanup;
// Log the number of objects from the first list
pObjectList = pData->pHead->pObjects;
printf(TEXT("Number of objects (before filtering): %u\n"), pObjectList->uCount);
// Log the number of points around the first object (braces for scope)
{
pEXOBJ_OUTLINE_POINT pIter;
L_INT iCount;
for (pIter = pObjectList->pHead->pOutline->pHead, iCount = 0; pIter != NULL; pIter = pIter->pNext, iCount++)
{
// Nothing to do, just incrementing iCount
}
printf(TEXT("First object's outline length: %d\n"), iCount);
}
// Setup the filter options
FilterOptions.uStructSize = sizeof(EXOBJ_FILTER_OPTIONS);
// Filter the objects
nRet = L_ExtractObjects_FilterList(pData, pObjectList, &FilterOptions);
if (nRet != SUCCESS)
goto cleanup;
// Log the number of objects again
printf(TEXT("Number of objects (after filtering): %u\n"), pObjectList->uCount);
// Setup the content bound options
ContentBound.uStructSize = sizeof(EXOBJ_CONTENTBOUND);
L_Rect_Make(&ContentBound.rcInput, 192, 260, 323, 146);
ContentBoundOptions.uStructSize = sizeof(EXOBJ_CONTENTBOUND_OPTIONS);
ContentBoundOptions.pObjectsOfInterest = NULL; // Passing NULL to use every object in pData
ContentBoundOptions.uObjectsOfInterestCount = 0; // Passing 0 to use every object in pData
// Calculate the content bounds
nRet = L_ExtractObjects_CalcContentBound(pData, &ContentBound, 1, &ContentBoundOptions);
if (nRet != SUCCESS)
goto cleanup;
// Allocate a new array to hold the objects
pObjectArray = (pEXOBJ_OBJECT*)malloc(pObjectList->uCount * sizeof(pEXOBJ_OBJECT));
if (pObjectArray == NULL)
{
nRet = ERROR_NO_MEMORY;
goto cleanup;
}
// Convert the linked list to an array (braces for scope)
{
pEXOBJ_OBJECT pIter;
L_INT iIndex;
for (pIter = pObjectList->pHead, iIndex = 0; pIter != NULL; pIter = pIter->pNext, iIndex++)
pObjectArray[iIndex] = pIter;
}
// Setup the region options
RegionOptions.uStructSize = sizeof(EXOBJ_REGION_OPTIONS);
RegionOptions.uFlags = EXOBJ_REGION_HORIZONTAL;
// Calculate each object's region
nRet = L_ExtractObjects_CalcRegion(pData, pObjectArray, pObjectList->uCount, &RegionOptions);
if (nRet != SUCCESS)
goto cleanup;
// Create an output image
nRet = L_CreateBitmap(&OutputBitmap, sizeof(BITMAPHANDLE), TYPE_CONV, InputBitmap.Width, InputBitmap.Height, 24, ORDER_BGR, NULL, TOP_LEFT, NULL, 0);
if (nRet != SUCCESS)
goto cleanup;
// Fill the output image with white
nRet = L_FillBitmap(&OutputBitmap, RGB(255, 255, 255));
if (nRet != SUCCESS)
goto cleanup;
// Draw the content bound rects for the first word. Red for the input, green for the output.
nRet = L_SetBitmapRgnRect(&OutputBitmap, NULL, &ContentBound.rcInput, L_RGN_SET);
if (nRet != SUCCESS)
goto cleanup;
nRet = L_FillBitmap(&OutputBitmap, RGB(255, 0, 0));
if (nRet != SUCCESS)
goto cleanup;
nRet = L_SetBitmapRgnRect(&OutputBitmap, NULL, &ContentBound.rcContent, L_RGN_SET);
if (nRet != SUCCESS)
goto cleanup;
nRet = L_FillBitmap(&OutputBitmap, RGB(0, 255, 0));
if (nRet != SUCCESS)
goto cleanup;
// Populate the output image with each object's region (braces for scope)
{
pEXOBJ_OBJECT pObjectIter;
for (pObjectIter = pObjectList->pHead; pObjectIter != NULL; pObjectIter = pObjectIter->pNext)
{
pEXOBJ_SEGMENT pSegmentIter;
for (pSegmentIter = pObjectIter->pRegionHorizontal->pHead; pSegmentIter != NULL; pSegmentIter = pSegmentIter->pNext)
{
// Update the region to the current segment
nRet = L_SetBitmapRgnRect(&OutputBitmap, NULL, &pSegmentIter->rcBounds, L_RGN_SET);
if (nRet != SUCCESS)
goto cleanup;
// Fill the region with black
nRet = L_FillBitmap(&OutputBitmap, RGB(0, 0, 0));
if (nRet != SUCCESS)
goto cleanup;
}
}
}
// Clear the output image's region
nRet = L_FreeBitmapRgn(&OutputBitmap);
if (nRet != SUCCESS)
goto cleanup;
// Save the output image
nRet = L_SaveBitmap(MAKE_IMAGE_PATH(TEXT("ExtractObjects.png")), &OutputBitmap, FILE_PNG, 0, 0, NULL);
if (nRet != SUCCESS)
goto cleanup;
cleanup:
// Free the loaded images
if (InputBitmap.Flags.Allocated)
L_FreeBitmap(&InputBitmap);
if (OutputBitmap.Flags.Allocated)
L_FreeBitmap(&OutputBitmap);
// Free the results
if (pData != NULL)
L_ExtractObjects_FreeData(&pData);
// Free the array
if (pObjectArray != NULL)
free(pObjectArray);
return nRet;
}
Help Collections
Raster .NET | C API | C++ Class Library | HTML5 JavaScript
Document .NET | C API | C++ Class Library | HTML5 JavaScript
Medical .NET | C API | C++ Class Library | HTML5 JavaScript
Medical Web Viewer .NET
Multimedia
Direct Show .NET | C API | Filters
Media Foundation .NET | C API | Transforms
Supported Platforms
.NET, Java, Android, and iOS/macOS Assemblies
Imaging, Medical, and Document
C API/C++ Class Libraries
Imaging, Medical, and Document
HTML5 JavaScript Libraries
Imaging, Medical, and Document