Path: blob/master/Model-5/ocr/words.py
427 views
# -*- coding: utf-8 -*-1"""2Detect words on the page3return array of words' bounding boxes4"""5import numpy as np6import matplotlib.pyplot as plt7import cv28from .helpers import *910def detection(image, join=False):11""" Detecting the words bounding boxes """12# Preprocess image for word detection13blurred = cv2.GaussianBlur(image, (5, 5), 18)14edgeImg = edgeDetect(blurred)15ret, edgeImg = cv2.threshold(edgeImg, 50, 255, cv2.THRESH_BINARY)16bwImage = cv2.morphologyEx(edgeImg, cv2.MORPH_CLOSE,17np.ones((15,15), np.uint8))18# Return detected bounding boxes19return textDetect(bwImage, image, join)202122def edgeDetect(im):23"""24Edge detection25Sobel operator is applied for each image layer (RGB)26"""27return np.max(np.array([sobelDetect(im[:,:, 0]),28sobelDetect(im[:,:, 1]),29sobelDetect(im[:,:, 2])]), axis=0)303132def sobelDetect(channel):33""" Sobel operator """34sobelX = cv2.Sobel(channel, cv2.CV_16S, 1, 0)35sobelY = cv2.Sobel(channel, cv2.CV_16S, 0, 1)36sobel = np.hypot(sobelX, sobelY)37sobel[sobel > 255] = 25538return np.uint8(sobel)394041def textDetect(img, image, join=False):42small = resize(img, 2000)4344# Finding contours45mask = np.zeros(small.shape, np.uint8)46im2, cnt, hierarchy = cv2.findContours(np.copy(small),47cv2.RETR_CCOMP,48cv2.CHAIN_APPROX_SIMPLE)49index = 050boundingBoxes = np.array([0,0,0,0])51bBoxes = []5253# image for drawing bounding boxes54small = cv2.cvtColor(small, cv2.COLOR_GRAY2RGB)5556# Go through all contours in top level57while (index >= 0):58x,y,w,h = cv2.boundingRect(cnt[index])59cv2.drawContours(mask, cnt, index, (255, 255, 255), cv2.FILLED)60maskROI = mask[y:y+h, x:x+w]61# Ratio of white pixels to area of bounding rectangle62r = cv2.countNonZero(maskROI) / (w * h)6364# Limits for text65if r > 0.1 and 1600 > w > 10 and 1600 > h > 10 and h/w < 3 and w/h < 10 and (60 // h) * w < 1000:66bBoxes += [[x, y, w, h]]6768index = hierarchy[0][index][0]6970# Need more work71if join:72bBoxes = groupRectangles(bBoxes)73for (x, y, w, h) in bBoxes:74cv2.rectangle(small, (x, y),(x+w,y+h), (0, 255, 0), 2)75boundingBoxes = np.vstack((boundingBoxes,76np.array([x, y, x+w, y+h])))7778implt(small, t='Bounding rectangles')7980bBoxes = boundingBoxes.dot(ratio(image, small.shape[0])).astype(np.int64)81return bBoxes[1:]828384def textDetectWatershed(thresh):85""" Text detection using watershed algorithm - NOT IN USE """86# According to: http://docs.opencv.org/trunk/d3/db4/tutorial_py_watershed.html87img = cv2.cvtColor(cv2.imread("data/textdet/%s.jpg" % IMG),88cv2.COLOR_BGR2RGB)89img = resize(img, 3000)90thresh = resize(thresh, 3000)91# noise removal92kernel = np.ones((3,3),np.uint8)93opening = cv2.morphologyEx(thresh,cv2.MORPH_OPEN,kernel, iterations = 3)9495# sure background area96sure_bg = cv2.dilate(opening,kernel,iterations=3)9798# Finding sure foreground area99dist_transform = cv2.distanceTransform(opening,cv2.DIST_L2,5)100ret, sure_fg = cv2.threshold(dist_transform,1010.01*dist_transform.max(), 255, 0)102103# Finding unknown region104sure_fg = np.uint8(sure_fg)105unknown = cv2.subtract(sure_bg,sure_fg)106107# Marker labelling108ret, markers = cv2.connectedComponents(sure_fg)109110# Add one to all labels so that sure background is not 0, but 1111markers += 1112113# Now, mark the region of unknown with zero114markers[unknown == 255] = 0115116markers = cv2.watershed(img, markers)117implt(markers, t='Markers')118image = img.copy()119gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)120121for mark in np.unique(markers):122# mark == 0 --> background123if mark == 0:124continue125126# Draw it on mask and detect biggest contour127mask = np.zeros(gray.shape, dtype="uint8")128mask[markers == mark] = 255129130cnts = cv2.findContours(mask.copy(),131cv2.RETR_EXTERNAL,132cv2.CHAIN_APPROX_SIMPLE)[-2]133c = max(cnts, key=cv2.contourArea)134135# Draw a bounding rectangle if it contains text136x,y,w,h = cv2.boundingRect(c)137cv2.drawContours(mask, c, 0, (255, 255, 255), cv2.FILLED)138maskROI = mask[y:y+h, x:x+w]139# Ratio of white pixels to area of bounding rectangle140r = float(cv2.countNonZero(maskROI)) / (w * h)141142# Limits for text143if r > 0.2 and 2000 > w > 15 and 1500 > h > 15:144cv2.rectangle(image, (x, y),(x+w,y+h), (0, 255, 0), 2)145146implt(image)147148149