I tried to modify the code given in http://stackoverflow.com/questions/1989987/my-own-ocr-program-in-python for finding the connected components in a gray scale image. Ive attached the code,sample image and output below.
Sample Image
Output:
But the connected components obtained is not correct. Please suggest some solution for this problem..Thanks.
import sys, numpy
from array import array
import OtsuAlgorithm
import pymorph
from OtsuAlgorithm import *
from PIL import Image, ImageDraw
import random
class Region():
def __init__(self, x, y):
self._pixels = [(x, y)]
self._min_x = x
self._max_x = x
self._min_y = y
self._max_y = y
def add(self, x, y):
self._pixels.append((x, y))
self._min_x = min(self._min_x, x)
self._max_x = max(self._max_x, x)
self._min_y = min(self._min_y, y)
self._max_y = max(self._max_y, y)
def box(self):
return [(self._min_x, self._min_y), (self._max_x, self._max_y)]
def find_regions(im): #im -> Binarized Image Array
height = len(im)
width=len(im[0])
#Height & Width of Image Array- > 510 x 520
regions = {}
pixel_region = [[0 for y in range(height)] for x in range(width)]
print 'Height& Width of pixel_region'
print len(pixel_region),len(pixel_region[0])
equivalences = {}
n_regions = 0
#first pass. find regions.
for x in xrange(width-1):
for y in xrange(height-1):
#look for a black pixel
if im[y][x]== 1: #BLACK
# get the region number from north or west
# or create new region
region_n = 0 if y == 0 else pixel_region[x][y-1]
region_w = 0 if x == 0 else pixel_region[x-1][y]
region_nw= 0 if (x == 0 or y == 0) else pixel_region[x-1][y-1]
wd = width-1
hd=height-1
region_ne= 0 if (x == hd ) else pixel_region[x+1][y-1]
region_e= 0 if (x==hd) else pixel_region[x+1][y]
region_s= 0 if (y==wd) else pixel_region[x][y+1]
max_region = max(region_n, region_w,region_ne,region_nw,region_e,region_s)
#max_region = max(region_n, region_w)
if max_region > 0:
new_region = min(filter(lambda i: i > 0, (region_n,region_w,region_ne,region_nw,region_e,region_s)))
#update equivalences
if max_region > new_region:
if max_region in equivalences:
equivalences[max_region].add(new_region)
else:
equivalences[max_region] = set((new_region,))
else:
#no neighbours uniquely label the region
n_regions += 1
new_region = n_regions
pixel_region[x][y] = new_region
#Scan image again, assigning all equivalent regions the same region value.
for x in xrange(width):
for y in xrange(height):
r = pixel_region[x][y]
if r > 0:
while r in equivalences:
r = min(equivalences[r])
pixel_region[x][y]=r
if not r in regions:
regions[r] = Region(x, y)
else:
regions[r].add(x, y)
for k, v in equivalences.iteritems():
print k, v
regionCords=list(regions.itervalues())
return regionCords
def main():
im = Image.open("/home/hsrd/Desktop/Images_OCR/Screenshot.tif")#Width:520 Height: 510
image_array= im.getdata()
width,height=im.size
pixdata=list(image_array)
otsu=OtsuAlgorithm()
threshold=otsu.calculateOptimalThreshold(width,height,pixdata)
a=pymorph.binary(im,threshold)#binarize Image
regions = find_regions(a)
draw = ImageDraw.Draw(im)
for r in regions:
draw.rectangle(r.box(), outline="red")
del draw
output = file("output.png", "wb")
im.save(output)
output.close()
if __name__ == "__main__":
main()