Example #1
0
def imgHandle(img, feature):
    resultArr = []
    # 灰度
    grayImg = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)

    # 二值
    ret, th = cv2.threshold(
        grayImg, 0, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU)

    # 膨胀
    kernel = np.ones((3, 3), np.uint8)
    dilation = cv2.dilate(th.copy(), kernel)  # 膨胀
    # cv_show('dilation', dilation)
    # 轮廓
    refCnts, hierarchy = cv2.findContours(
        dilation, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

    refCnts = utils.sort_contours(
        refCnts, method="left-to-right")[0]  # 排序从左到右,从上到下

    for(i, c) in enumerate(refCnts):
        # 计算外接矩形并且resize成合适大小
        (x, y, w, h) = cv2.boundingRect(c)
        if w > 20 and w < 26 and h > 18 and h < 26:
            cv2.rectangle(th, (x, y), (x + w, y + h), (0, 0, 0), 1)
            # cv_show('img', th[y:y+h, x:x+w])
            resultArr.append(discriminate(th[y:y+h, x:x+w], feature))
    # cv_show('img', th)
    # 分割

    # 识别方向

    # 返回结果

    return resultArr
def encontraTabelasAlunos(img, linhas):
    #Procura todos os contornos externos da imagem com as linhas
    contours = cv2.findContours(linhas, cv2.RETR_EXTERNAL,
                                cv2.CHAIN_APPROX_SIMPLE)[0]
    contours = utils.sort_contours(contours, method="top-to-bottom")[0]

    if len(contours) > 0:
        todosContornos = []
        todosContornosLinhas = []
        roiAlunos = []
        roiAlunosLinhas = []
        for c in contours:
            perimetro = cv2.arcLength(c, True)
            area = cv2.contourArea(c)
            if (perimetro > 1000 and area > 50000):
                (x, y, w, h) = cv2.boundingRect(c)
                roi = img[y:y + h, x:x + w]
                todosContornos.append(roi)
                todosContornosLinhas.append((x, y, w, h))

        if len(todosContornos) > 0:
            todosContornosLinhas.pop(0)
            todosContornos.pop(0)
            roiAlunosLinhas = todosContornosLinhas
            roiAlunos = todosContornos

            if len(roiAlunos) > 1:
                (x1, _, _, _) = todosContornosLinhas[0]
                (x2, _, _, _) = todosContornosLinhas[1]
                if (x1 > x2):
                    temp = roiAlunos[0]
                    roiAlunos[0] = roiAlunos[1]
                    roiAlunos[1] = temp
                    temp = roiAlunosLinhas[0]
                    roiAlunosLinhas[0] = roiAlunosLinhas[1]
                    roiAlunosLinhas[1] = temp

        if (roiAlunos[0].shape[1] > IMGX * 0.65):
            largura = roiAlunos[0].shape[1]
            altura = roiAlunos[0].shape[0]
            roi1 = roiAlunos[0][0:altura, 0:int(largura / 2)]
            roi2 = roiAlunos[0][0:altura, int(largura / 2):largura]
            roiAlunos = []
            roiAlunos.append(roi1)
            roiAlunos.append(roi2)

            (x, y, w, h) = roiAlunosLinhas[0]
            roiLinhas1 = (x, y, int(w / 2), h)
            roiLinhas2 = (int(w / 2), y, w, h)
            roiAlunosLinhas = []
            roiAlunosLinhas.append(roiLinhas1)
            roiAlunosLinhas.append(roiLinhas2)
    else:
        quit(
            "Folha ilegível, não foi possivel encontrar nenhuma tabela de alunos"
        )

    return roiAlunos, roiAlunosLinhas
def get_sub_answer_card_cnts(img_path):
    """ 获得答题卡的子区域
    # findContours 函数详解:https://blog.csdn.net/laobai1015/article/details/76400725
    # approxPolyDP 多边形近似 https://blog.csdn.net/kakiebu/article/details/79824856
    
    Args:
        img ([type]): 图片
    Returns:
        [type]: 答题卡的左右答题区域轮廓
    """
    image = cv2.imread(img_path)
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
    # warped_answer_image_1 = four_point_transform(gray, answer_contour_1.reshape(4, 2))

    # 二值化
    thresh = cv2.threshold(gray, 0, 255,
                           cv2.THRESH_BINARY_INV | cv2.THRESH_OTSU)[1]
    # 在二值图像中查找轮廓,包括内围、外围轮廓,但是检测到的轮廓不建立等级关系,彼此之间独立
    thresh_cnts, _ = cv2.findContours(thresh.copy(), cv2.RETR_LIST,
                                      cv2.CHAIN_APPROX_SIMPLE)

    cnt_size = 0
    sub_answer_cnts = []
    if len(thresh_cnts) > 0:
        # 将轮廓按大小, 降序排序
        thresh_cnts = sorted(thresh_cnts, key=cv2.contourArea, reverse=True)
        for c in thresh_cnts:
            cnt_size = cnt_size + 1

            # arcLength 计算周长
            peri = cv2.arcLength(c, True)

            # 计算轮廓的边界框
            (x, y, w, h) = cv2.boundingRect(c)
            print((x, y, w, h))

            # 之前寻找到的轮廓可能是多边形,现在通过寻找近似轮廓,得到期望的四边形
            approx = cv2.approxPolyDP(c, 0.02 * peri, True)

            # 只提取近似轮廓为四边形的区域, 且轮廓长度大于指定长度
            if len(approx) == 4 and w > 1300:
                print("轮廓周长:", peri, '宽:', w)
                print('原始轮廓的边数:', len(c), ', 近似轮廓的边数:', len(approx))
                sub_answer_cnts.append(approx)

            # 只处理前20个最大轮廓
            if cnt_size >= 20:
                break

    # 从上到下,将轮廓排序
    print(type(sub_answer_cnts))
    sub_answer_cnts = sort_contours(sub_answer_cnts, method="top-to-bottom")[0]
    print(type(sub_answer_cnts))
    return sub_answer_cnts
def corrigeAlinhamento(img):
    imgGray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    ret, thresh = cv2.threshold(imgGray, 150, 255, cv2.THRESH_BINARY_INV)
    contours = cv2.findContours(thresh, cv2.RETR_EXTERNAL,
                                cv2.CHAIN_APPROX_SIMPLE)[0]
    contours = utils.sort_contours(contours, method="top-to-bottom")[0]

    if len(contours) > 0:
        todosContornos = []
        for c in contours:
            perimetro = cv2.arcLength(c, True)
            area = cv2.contourArea(c)
            if (perimetro > 1000 and area > 100000):
                (x, y, w, h) = cv2.boundingRect(c)
                roi = img[y:y + h, x:x + w]
                todosContornos.append(roi)

        cabecalho = todosContornos[0]

        grayCabecalho = cv2.cvtColor(cabecalho, cv2.COLOR_BGR2GRAY)
        grayCabecalho = np.float32(grayCabecalho)
        corners = cv2.goodFeaturesToTrack(grayCabecalho, 500, 0.02, 20)
        corners = np.int0(corners)
        if len(corners) > 0:
            leftCorners = []
            rightCorners = []
            larguraCabecalho = cabecalho.shape[1]

            for corner in corners:
                x, y = corner.ravel()
                if x < 50:
                    leftCorners.append(y)
                if x > (larguraCabecalho - 50):
                    rightCorners.append(y)
            leftCorners.sort()
            rightCorners.sort()
            leftCorner = leftCorners[0]
            rightCorner = rightCorners[0]
            correcao = 0
            if leftCorner > rightCorner:
                correcao = -leftCorner
            if rightCorner > leftCorner:
                correcao = rightCorner

            correcao = correcao * 0.033
            print("correcao ->" + str(correcao))
            img = imutils.rotate(img, correcao)
            img = img[int(IMGY * 0.05):IMGY - int(IMGY * 0.05),
                      int(IMGX * 0.02):IMGX - int(IMGX * 0.02)]

    else:
        quit("Folha ilegível, falha no alinhamento")
    return img
def get_answer_card_cnts(img):
    """ 获得答题卡的左右答题区域
    # findContours 函数详解:https://blog.csdn.net/laobai1015/article/details/76400725
    # approxPolyDP 多边形近似 https://blog.csdn.net/kakiebu/article/details/79824856
    
    Args:
        img ([type]): 图片
    Returns:
        [type]: 答题卡的左右答题区域轮廓
    """

    # 检测图片中的最外围轮廓
    cnts, _ = cv2.findContours(img.copy(), cv2.RETR_EXTERNAL,
                               cv2.CHAIN_APPROX_SIMPLE)
    print("原始图片检测的轮廓总数:", len(cnts))
    if len(cnts) == 0:
        return None

    # 提取的轮廓总数
    contour_size = 0
    # 检测到的左右答题区域轮廓
    answer_cnts = []

    # 将轮廓按大小, 降序排序
    cnts = sorted(cnts, key=cv2.contourArea, reverse=True)
    for c in cnts:
        # arcLength 计算周长
        peri = cv2.arcLength(c, True)
        # print("轮廓周长:", peri)

        # 之前寻找到的轮廓可能是多边形,现在通过寻找近似轮廓,得到期望的四边形
        approx = cv2.approxPolyDP(c, 0.02 * peri, True)
        # print('原始轮廓的边数:', len(c), ', 近似轮廓的边数:', len(approx))

        # 当近似轮廓为4时,代表是需要提取的矩形区域
        if len(approx) == 4:
            contour_size = contour_size + 1
            answer_cnts.append(approx)

        # 只提取答题卡中的最大两个轮廓
        if contour_size == 2:
            break

    answer_cnts = sort_contours(answer_cnts, method="left-to-right")[0]
    return answer_cnts
Example #6
0
cv_show('ref',ref)
#二值图像
ref=cv2.threshold(ref,10,255,cv2.THRESH_BINARY_INV)[1]
cv_show('ref',ref)

#计算轮廓
#cv2.findContours()函数接受的参数为二值图,即黑白的(不是灰度图)
#cv2.RETR_EXTERNAL只检测外轮廓,cv2.CHAIN_APPROX_SIMPLE只保留终点坐标
#返回的list中每个元素都是图像中的一个轮廓

# ref_,
refCnts,hierarchy=cv2.findContours(ref.copy(),cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(img,refCnts,-1,(0,0,255),3)
cv_show('img',img)
print(np.array(refCnts).shape)
refCnts=utils.sort_contours(refCnts,method="left-to-right")[0]#排序从左到右,从上到下
digits={}

'''
第一个参数:img是原图
第二个参数:(x,y)是矩阵的左上点坐标
第三个参数:(x+w,y+h)是矩阵的右下点坐标
第四个参数:(0,255,0)是画线对应的rgb颜色
'''
#遍历每一个轮廓
for(i,c) in enumerate(refCnts):
    #计算外接矩形并且resize成合适大小
    (x,y,w,h)=cv2.boundingRect(c)
    roi=ref[y:y+h,x:x+w]
    roi=cv2.resize(roi,(57,58))
Example #7
0
def refine_accNum(file_name, img_for_box_extraction_path, dir_path, img):
    og_img = img
    height, width = img.shape[:2]
    (thresh, img) = cv2.threshold(img, 160, 255, cv2.THRESH_BINARY)
    # Invert the image
    img_bin_inv = 255 - img

    # Defining a kernel length
    kernel_length = np.array(img).shape[1] // 20
    kernel_length_vertical = height // 2
    kernel_length_horizontal = width // 4
    # A verticle kernel of (1 X kernel_length), which will detect all the verticle lines from the image.
    verticle_kernel = cv2.getStructuringElement(cv2.MORPH_RECT,
                                                (1, kernel_length_vertical))
    # A horizontal kernel of (kernel_length X 1), which will help to detect all the horizontal line from the image.
    hori_kernel = cv2.getStructuringElement(cv2.MORPH_RECT,
                                            (kernel_length_horizontal, 1))
    # A kernel of (3 X 3) ones.
    kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))

    # Morphological operation to detect vertical lines from an image
    img_temp1 = cv2.erode(img, verticle_kernel, iterations=1)
    # utils.display_image('display_image', img_temp1)

    verticle_lines_img = cv2.dilate(img_temp1, verticle_kernel, iterations=1)
    (thresh, verticle_lines_img) = cv2.threshold(verticle_lines_img, 32, 255,
                                                 cv2.THRESH_BINARY)
    # utils.display_image('display_image', verticle_lines_img)

    # Morphological operation to detect horizontal lines from an image
    img_temp2 = cv2.erode(img, hori_kernel, iterations=1)
    # utils.display_image('display_image', img_temp2)

    horizontal_lines_img = cv2.dilate(img_temp2, hori_kernel, iterations=1)
    (thresh, horizontal_lines_img) = cv2.threshold(horizontal_lines_img, 32,
                                                   255, cv2.THRESH_BINARY)
    # utils.display_image('display_image', horizontal_lines_img)

    # Weighting parameters, this will decide the quantity of an image to be added to make a new image.
    alpha = 0.5
    beta = 1.0 - alpha
    # This function helps to add two image with specific weight parameter to get a third image as summation of two image.
    img_final_bin = cv2.addWeighted(verticle_lines_img, alpha,
                                    horizontal_lines_img, beta, 0.0)
    # utils.display_image('display_image', img_final_bin)

    # Find contours for image, which will detect all the boxes
    im2, contours, hierarchy = cv2.findContours(img_final_bin, cv2.RETR_TREE,
                                                cv2.CHAIN_APPROX_SIMPLE)

    # Sort all the contours by top to bottom.
    if (len(contours) != 0):
        (contours, boundingBoxes) = utils.sort_contours(contours,
                                                        method="top-to-bottom")

        idx = 0
        for c in contours:
            # Returns the location and width,height for every contour
            x, y, w, h = cv2.boundingRect(c)
            if w < width // 5 or h < height // 5:
                continue

            new_img = img_final_bin[y:y + h, x:x + w]
            # utils.display_image('display_image', new_img)
            # utils.store_img(dir_path, file_name, new_img, "date")
            # cv2.imwrite(dir_path + "/date/" + img_for_box_extraction_path + '.tif', new_img)
            # (thresh, new_img) = cv2.threshold(new_img, 32, 255,cv2.THRESH_BINARY)

            # utils.display_image('display_image', new_img)
            final_img = og_img[y:y + h, x:x + w] - new_img
            # utils.display_image('display_image', final_img)
            (thresh, final_img) = cv2.threshold(final_img, 32, 255,
                                                cv2.THRESH_BINARY)
            # utils.display_image('display_image', final_img)
            idx = idx + 1
            print(file_name)
            # tess.test(file_name, img)
            # utils.store_img(dir_path, file_name, img, "refined_acc")
            utils.display_image('display_image', final_img)
            # remove_lines(final_img)
            # if idx == 2:
            break
Example #8
0
def find_boxes(file_name, img_for_box_extraction_path, dir_path, img):
    # Read the image
    # path = file_name
    # print(path)
    # img = cv2.imread(path , 0)
    # height, width = img.shape[:2]

    # img = cv2.resize(img,(width//2, height//2), interpolation = cv2.INTER_AREA)
    height, width = img.shape[:2]
    og_img = img
    # Thresholding the image
    (thresh, img_bin) = cv2.threshold(img, 160, 255, cv2.THRESH_BINARY)
    # Invert the image
    img_bin = 255 - img_bin
    #utils.display_image('display_image', img_bin)
    extraction_img = img_bin

    kernel = cv2.getStructuringElement(
        cv2.MORPH_CROSS, (3, 3)
    )  # to manipulate the orientation of dilution , large x means horizonatally dilating  more, large y means vertically dilating more
    dilated = cv2.dilate(
        img_bin, kernel,
        iterations=2)  # dilate , more the iteration more the dilation
    # utils.display_image('display_image', dilated)
    # utils.store_img(dir_path, "1" + file_name, dilated, "boxes_temp")

    img_bin = dilated

    img_bin = cv2.GaussianBlur(img_bin, (5, 5), 0)
    # utils.display_image('display_image', img_bin)
    # utils.store_img(dir_path, "2" + file_name, img_bin, "boxes_temp")

    # Defining a kernel length
    kernel_length = np.array(img).shape[1] // 80

    # A verticle kernel of (1 X kernel_length), which will detect all the verticle lines from the image.
    verticle_kernel = cv2.getStructuringElement(cv2.MORPH_RECT,
                                                (1, kernel_length))
    # A horizontal kernel of (kernel_length X 1), which will help to detect all the horizontal line from the image.
    hori_kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (kernel_length, 1))
    # A kernel of (3 X 3) ones.
    kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))

    # Morphological operation to detect vertical lines from an image
    img_temp1 = cv2.erode(img_bin, verticle_kernel, iterations=2)
    # utils.display_image('display_image', img_temp1)

    verticle_lines_img = cv2.dilate(img_temp1, verticle_kernel, iterations=2)
    (thresh, verticle_lines_img) = cv2.threshold(verticle_lines_img, 127, 255,
                                                 cv2.THRESH_BINARY)
    # utils.display_image('display_image', verticle_lines_img)
    # utils.store_img(dir_path, "3" + file_name, verticle_lines_img, "boxes_temp")

    # Morphological operation to detect horizontal lines from an image
    img_temp2 = cv2.erode(img_bin, hori_kernel, iterations=2)
    # utils.display_image('display_image', img_temp2)

    horizontal_lines_img = cv2.dilate(img_temp2, hori_kernel, iterations=2)
    (thresh, horizontal_lines_img) = cv2.threshold(horizontal_lines_img, 127,
                                                   255, cv2.THRESH_BINARY)
    # utils.display_image('display_image', horizontal_lines_img)
    # utils.store_img(dir_path, "4" + file_name, horizontal_lines_img, "boxes_temp")

    # Weighting parameters, this will decide the quantity of an image to be added to make a new image.
    alpha = 0.5
    beta = 1.0 - alpha
    # This function helps to add two image with specific weight parameter to get a third image as summation of two image.
    img_final_bin = cv2.addWeighted(verticle_lines_img, alpha,
                                    horizontal_lines_img, beta, 0.0)
    # utils.display_image('display_image', img_final_bin)

    img_final_bin = cv2.erode(~img_final_bin, kernel, iterations=2)
    # utils.display_image('display_image', img_final_bin)

    (thresh,
     img_final_bin) = cv2.threshold(img_final_bin, 128, 255,
                                    cv2.THRESH_BINARY | cv2.THRESH_OTSU)
    # utils.display_image('display_image', img_final_bin)
    # utils.store_img(dir_path, "5" + file_name, img_final_bin, "boxes_temp")

    # Find contours for image, which will detect all the boxes
    im2, contours, hierarchy = cv2.findContours(img_final_bin, cv2.RETR_TREE,
                                                cv2.CHAIN_APPROX_SIMPLE)
    #utils.display_image('display_image', im2)

    # Sort all the contours by top to bottom.
    (contours, boundingBoxes) = utils.sort_contours(contours,
                                                    method="top-to-bottom")

    idx = 0
    account_no_flag = False
    date_flag = False
    amount_flag = False
    account_number_list = []
    amount_list = []
    for c in contours:
        # Returns the location and width,height for every contour
        x, y, w, h = cv2.boundingRect(c)
        if w < width // 20 or h < height // 20:
            continue
        if (isAccountNumber(width, height, x, y, w, h)):
            account_number_list.append(c)
            # print("Account Number")
            new_img = extraction_img[y:y + h, x:x + w]
        if (isAmount(width, height, x, y, w, h)):
            amount_list.append(c)
            new_img = extraction_img[y:y + h, x:x + w]
        if (isDate(width, height, x, y, w, h) and not date_flag):
            print("Date")
            date_flag = True
            new_img = og_img[y:y + h, x:x + w]
            # new_img = extraction_img[y:y+h, x:x+w]
            # utils.display_image('display_image', new_img)
            utils.store_img(dir_path, file_name, new_img, "date1")

    account_number_list = utils.sort_contours_area(account_number_list)
    amount_list = utils.sort_contours_area(amount_list)
    if len(account_number_list) != 0:
        for i in range(len(account_number_list)):
            x, y, w, h = cv2.boundingRect(account_number_list[0])
            new_img = extraction_img[y:y + h, x:x + w]
            # utils.display_image('display_image', new_img)
            # utils.store_img(dir_path, file_name, new_img, "accNum")
    if len(amount_list) != 0:
        x, y, w, h = cv2.boundingRect(amount_list[0])
        new_img = extraction_img[y:y + h, x:x + w]
Example #9
0
def refine_date(file_name, img_for_box_extraction_path, dir_path, img):

    height, width = img.shape[:2]
    img = cv2.resize(img, (width * 2, height * 2),
                     interpolation=cv2.INTER_LINEAR)
    height, width = img.shape[:2]
    (thresh, img) = cv2.threshold(img, 160, 255, cv2.THRESH_BINARY_INV)
    # utils.display_image('display_image', img)
    og_img = img
    # Invert the image
    img_bin_inv = 255 - img

    # Defining a kernel length
    kernel_length = np.array(img).shape[1] // 20
    kernel_length_vertical = height // 2
    kernel_length_horizontal = width // 4
    # A verticle kernel of (1 X kernel_length), which will detect all the verticle lines from the image.
    verticle_kernel = cv2.getStructuringElement(cv2.MORPH_RECT,
                                                (1, kernel_length_vertical))
    # A horizontal kernel of (kernel_length X 1), which will help to detect all the horizontal line from the image.
    hori_kernel = cv2.getStructuringElement(cv2.MORPH_RECT,
                                            (kernel_length_horizontal, 1))
    # A kernel of (3 X 3) ones.
    kernel = cv2.getStructuringElement(cv2.MORPH_CROSS, (2, 2))
    img_temp = cv2.dilate(img, kernel, iterations=1)
    # utils.display_image('display_image', img_temp)

    # Morphological operation to detect horizontal lines from an image
    img_temp2 = cv2.erode(img_temp, hori_kernel, iterations=1)
    # utils.display_image('display_image', img_temp2)

    horizontal_lines_img = cv2.dilate(img_temp2, hori_kernel, iterations=1)
    (thresh, horizontal_lines_img) = cv2.threshold(horizontal_lines_img, 160,
                                                   255, cv2.THRESH_BINARY)
    # utils.display_image('display_image', horizontal_lines_img)

    im2, contours, hierarchy = cv2.findContours(horizontal_lines_img,
                                                cv2.RETR_TREE,
                                                cv2.CHAIN_APPROX_SIMPLE)

    # Sort all the contours by top to bottom.
    (contours, boundingBoxes) = utils.sort_contours(contours,
                                                    method="top-to-bottom")

    if len(contours) > 1:

        x1, y1, w1, h1 = cv2.boundingRect(contours[0])
        x2, y2, w2, h2 = cv2.boundingRect(contours[len(contours) - 1])
        print(cv2.boundingRect(contours[0]))
        print(cv2.boundingRect(contours[len(contours) - 1]))
        new_img = img_temp[y1 + h1:y2, x2:x1 + w2]
        # utils.display_image('display_image', new_img)
        # utils.store_img(dir_path, file_name, new_img, "date")
        # cv2.imwrite(dir_path + "/date/" + img_for_box_extraction_path + '.tif', new_img)
        # (thresh, new_img) = cv2.threshold(new_img, 32, 255,cv2.THRESH_BINARY)
        # utils.display_image('display_image', new_img)
        final_img = new_img
        # utils.display_image('display_image', final_img)
        # (thresh, final_img) = cv2.threshold(final_img, 32, 255,cv2.THRESH_BINARY)
        # utils.display_image('display_image', final_img)
        #final_image = remove_lines(final_img)
        # utils.store_img(dir_path, file_name, final_img, "date8")
        utils.store_img(dir_path, file_name, final_img, "date2")
        img_temp = final_img
Example #10
0
def get_underline(img_for_extraction_path, file_name, dir_path, img):
    # height, width = og_img.shape[:2]

    # og_img = cv2.resize(og_img,(width//2, height//2), interpolation = cv2.INTER_AREA)
    height, width = img.shape[:2]
    og_img = slicing.slice_image_get_remaining(img)
    og_image_contours = og_img

    utils.display_image('display_image', og_img)

    # Thresholding the image
    (thresh, img_bin) = cv2.threshold(og_img, 160, 255, cv2.THRESH_BINARY)
    # Invert the image
    utils.display_image('display_image', img_bin)

    img_bin_inv = 255 - img_bin
    img_bin_inv_final = 255 - img_bin
    utils.display_image('display_image', img_bin_inv)
    # utils.store_img(dir_path, str(1) + "_" + img_for_extraction_path, img_bin_inv, "images_for_paper")

    img_bin_inv_blur = cv2.GaussianBlur(img_bin_inv, (3, 3), 0)
    utils.display_image('display_image', img_bin_inv_blur)

    kernel = cv2.getStructuringElement(
        cv2.MORPH_CROSS, (5, 2)
    )  # to manipulate the orientation of dilution , large x means horizonatally dilating  more, large y means vertically dilating more
    img_bin_inv_blur_dilated = cv2.dilate(
        img_bin_inv_blur, kernel,
        iterations=3)  # dilate , more the iteration more the dilation
    utils.display_image('display_image', img_bin_inv_blur_dilated)

    # utils.store_img(dir_path, str(2) + "_" + img_for_extraction_path, img_bin_inv_blur_dilated, "images_for_paper")

    kernel_length = np.array(img_bin).shape[1] // 5
    hori_kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (kernel_length, 1))

    img_temp_horizontal = cv2.erode(img_bin_inv_blur_dilated,
                                    hori_kernel,
                                    iterations=1)
    utils.display_image('display_image', img_temp_horizontal)

    # utils.store_img(dir_path, str(3) + "_" + img_for_extraction_path, img_temp_horizontal, "images_for_paper")

    horizontal_lines_img = cv2.dilate(img_temp_horizontal,
                                      hori_kernel,
                                      iterations=1)
    utils.display_image('display_image', horizontal_lines_img)
    # utils.store_img(dir_path, img_for_extraction_path, horizontal_lines_img, "handwritten")

    (thresh, horizontal_lines_img) = cv2.threshold(horizontal_lines_img, 32,
                                                   255, cv2.THRESH_BINARY)
    utils.display_image('display_image', horizontal_lines_img)
    utils.store_img(dir_path,
                    str("3a") + "_" + img_for_extraction_path,
                    horizontal_lines_img, "images_for_paper")

    horizontal_lines_img = cv2.GaussianBlur(horizontal_lines_img, (5, 5), 0)
    utils.display_image('display_image', horizontal_lines_img)

    edges = cv2.Canny(horizontal_lines_img, 127, 255)
    lines = cv2.HoughLinesP(edges,
                            1,
                            np.pi / 180,
                            30,
                            minLineLength=height // 1.5)

    img_bin_inv_contours = img_bin_inv

    # if lines is None:
    # 	return
    # for line in lines:
    # 	x1, y1, x2, y2 = line[0]
    # 	cv2.line(img_bin_inv_contours, (x1, y1), (x2, y2), (0, 255, 0), 3)

    image, contours, hierarchy = cv2.findContours(edges, cv2.RETR_EXTERNAL,
                                                  cv2.CHAIN_APPROX_NONE)
    utils.display_image('display_image', image)

    # utils.store_img(dir_path, str(4) + "_" + img_for_extraction_path, image, "images_for_paper")

    cv2.drawContours(img_bin_inv_contours, contours, -1, (255, 255, 255), 3)
    utils.display_image('display_image', img_bin_inv_contours)

    # Sort all the contours by top to bottom.
    (contours, boundingBoxes) = utils.sort_contours(contours,
                                                    method="top-to-bottom")
    idx = 0
    underline = "underline"
    flag = False
    amount_image = None
    previous = None
    # utils.display_image1(img_bin_inv_final)
    for contour in contours:
        # get rectangle bounding contour
        [x, y, w, h] = cv2.boundingRect(contour)
        # Don't plot small false positives that aren't text
        if w < width / (2):
            continue

        if ((y - (height // 8)) > 0):
            utils.display_image(
                'captcha_result',
                img_bin_inv_final[y - (height // 10):y + h + (height // 100),
                                  width // 10:width - width // 5])
            # utils.display_image('captcha_result', crop_img)
            # utils.store_img(dir_path, underline + "_" + str(idx) + "_" + img_for_extraction_path, crop_img, "handwritten_payee")
        else:
            # crop_img = img_bin_inv_final[0 : y + h + (height // 100), x : x + w]
            utils.display_image(
                'captcha_result',
                img_bin_inv_final[0:y + h + (height // 100),
                                  width // 10:width - width // 5])

        utils.display_image(
            'captcha_result',
            img_bin_inv_final[y - (height // 10):y + h + (height // 100),
                              width // 10:width - width // 5])
        # y_act = y - (height // 12)
        # h_act = y_act + (height // 12) + (h + (height // 100))
        if flag:
            if previous is None:
                # print ("Previous is None")
                previous = [0, y, width, h]
            else:
                # print (previous)
                # print ([0, y, width, h])
                overlap = utils.find_overlap(img_bin_inv_final, previous,
                                             [0, y, width, h])
                # previous = [0, y, width, h]
                if overlap > 0.1:
                    continue
                else:
                    previous = [0, y, width, h]
        if not flag:
            # draw rectangle around contour on original image
            # cv2.rectangle(og_image_contours, (x, y , (x + w, y + h + (height // 100), (0, 0, 0), 2)
            flag = True
            # delta = (height // 100)
            if ((y - (height // 8)) > 0):
                crop_img = img_bin_inv_final[y - (height // 10):y + h +
                                             (height // 100),
                                             width // 10:width - width // 5]
                # utils.display_image('captcha_result', crop_img)
                # utils.store_img(dir_path, underline + "_" + str(idx) + "_" + img_for_extraction_path, crop_img, "handwritten_payee")
            else:
                # crop_img = img_bin_inv_final[0 : y + h + (height // 100), x : x + w]
                crop_img = img_bin_inv_final[0:y + h + (height // 100),
                                             width // 10:width - width // 5]
                # utils.display_image('captcha_result', crop_img)
                # utils.store_img(dir_path, underline + "_" + str(idx) + "_" + img_for_extraction_path, crop_img, "handwritten_payee")
        else:
            if ((y - (height // 8)) > 0):
                crop_img = img_bin_inv_final[y - (height // 12):y + h +
                                             (height // 100), :]
            else:
                # crop_img = img_bin_inv_final[0 : y + h + (height // 100), x : x + w]
                crop_img = img_bin_inv_final[0:y + h + (height // 100), :]
                # utils.display_image('captcha_result', crop_img)
                # print("Underline")
                # utils.store_img(dir_path, underline + "_" + str(idx) + "_" + img_for_extraction_path, crop_img, "handwritten")
            if amount_image is None:
                amount_image = crop_img
            else:
                h1, w1 = amount_image.shape[:2]
                h2, w2 = crop_img.shape[:2]
                vis = np.zeros((max(h1, h2), w1 + w2), np.uint8)
                vis[:h1, :w1] = amount_image
                vis[:h2, w1:w1 + w2] = crop_img
                amount_image = vis
            # utils.display_image('captcha_result', amount_image)
            # print("Underline")
            # utils.store_img(dir_path, underline + "_" + str(idx) + "_" + img_for_extraction_path, crop_img, "handwritten")
        idx = idx + 1
    height, width = amount_image.shape[:2]
    # utils.display_image('captcha_result', amount_image)
    amount_image[:, width - ((width) // 5):] = 0
    # utils.display_image('captcha_result', amount_image)

    # width//2 - (width//2)//20
    amount_image[:, width // 2 - (width // 2) // 15:width // 2 +
                 (width // 2) // 15] = 0
    # utils.display_image('captcha_result', amount_image)
    # utils.store_img(dir_path, underline + "_" + str(idx) + "_" + img_for_extraction_path, amount_image, "handwritten_concatenated")
    if idx == 4:
        print(file_name)

    amount_image = amount_image[:, :width // 2]
Example #11
0
def remove_underline_name(img_for_extraction_path, file_name, dir_path, img):

    height, width = img.shape[:2]
    img = img[height // 20:, width // 20:width - width // 5]
    final_img = img
    temp_image = img
    kernel = cv2.getStructuringElement(
        cv2.MORPH_CROSS, (5, 1)
    )  # to manipulate the orientation of dilution , large x means horizonatally dilating  more, large y means vertically dilating more
    img_dilated = cv2.dilate(
        img, kernel,
        iterations=2)  # dilate , more the iteration more the dilation
    # utils.display_image('display_image', img_dilated)

    kernel_length = np.array(img_dilated).shape[1] // 5
    hori_kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (kernel_length, 1))

    img_temp_horizontal = cv2.erode(img_dilated, hori_kernel, iterations=1)
    # utils.display_image('display_image', img_temp_horizontal)

    horizontal_lines_img = cv2.dilate(img_temp_horizontal,
                                      hori_kernel,
                                      iterations=3)
    # utils.display_image('display_image', horizontal_lines_img)

    new_img = img - horizontal_lines_img
    # utils.display_image('display_image', new_img)
    final_img = new_img

    kernel = cv2.getStructuringElement(
        cv2.MORPH_RECT, (5, 5)
    )  # to manipulate the orientation of dilution , large x means horizonatally dilating  more, large y means vertically dilating more
    dilated_img = cv2.dilate(new_img, kernel, iterations=2)
    # utils.display_image('display_image', dilated_img)
    new_img = dilated_img

    im2, contours, hierarchy = cv2.findContours(new_img, cv2.RETR_EXTERNAL,
                                                cv2.CHAIN_APPROX_SIMPLE)
    #utils.display_image('display_image', im2)

    (contours, boundingBoxes) = utils.sort_contours(contours,
                                                    method="left_to_right")

    # contours = utils.sort_contours_area(contours)

    length = len(contours)
    trim_size = length // 5
    print("Length : " + str(length) + " -- trim_size : " + str(trim_size))
    for i in range(0, length):
        # and i < length - 2*trim_size
        if (i >= trim_size):
            continue

        contour = contours[i]
        # get rectangle bounding contour
        [x, y, w, h] = cv2.boundingRect(contour)

        if w > width // 50 and h > height // 2:
            continue
        # Don't plot small false positives that aren't text
        # if  w < width//50 or h < height//3:
        # 	continue

        # draw rectangle around contour on original image
        cv2.rectangle(temp_image, (x, y), (x + w, y + h), (255, 255, 255), 2)
        crop_img = new_img[y:y + h, x:x + w]
        # utils.display_image('captcha_result', crop_img)
        # new_img[y : y + h, x : x + w] = 0
        final_img[y:y + h, x:x + w] = 0
        # utils.display_image('captcha_result', new_img)
        print("contour")
    # utils.display_image('captcha_result', final_img)
    utils.store_img(dir_path, img_for_extraction_path, final_img, "name")
Example #12
0
threshold, binary = cv2.threshold(gray, 0, 255,
                                  cv2.THRESH_BINARY_INV | cv2.THRESH_OTSU)
print(threshold)
cv2.imshow('binary', binary)

# 获取模板图像的外轮廓, 保留终点坐标
ref, refCnts, hierarchy = cv2.findContours(binary.copy(), cv2.RETR_EXTERNAL,
                                           cv2.CHAIN_APPROX_SIMPLE)
cv2.imshow('ref', ref)
# 画出边框
cv2.drawContours(tpl, refCnts, -1, (0, 0, 255), 3)
cv2.imshow('tpl_Contours', tpl)
# print(np.array(refCnts))            # 10.

# 对模板图像进行排序, 方便从0-9对应存储
refCnts = utils.sort_contours(refCnts, method="left-to-right")[0]
digits = {}

# 遍历模板图形的每一个轮廓
for (k, v) in enumerate(refCnts):
    x, y, w, h = cv2.boundingRect(v)
    roi = ref[y:y + h, x:x + w]
    roi = cv2.resize(roi, (57, 88))
    # 按 method 方法进行存储, 每个数字代表一个模板
    digits[k] = roi

# step2: 预处理测试集图像
# 根据卡上字体大小, 初始化卷积核
rectKernel = cv2.getStructuringElement(cv2.MORPH_RECT, (9, 3))
sqKerbel = cv2.getStructuringElement(cv2.MORPH_RECT, (5, 5))
Example #13
0
if __name__ == '__main__':
    # load color image
    base_address = Path('Inputs')
    image_paths = base_address.glob('*.png')
    results_save_dir = Path('results')
    results_save_dir.mkdir(parents=True, exist_ok=True)

    dim = (820, 600)

    for image_path in image_paths:
        print(image_path)
        original_image = cv2.imread(str(image_path))

        original_image = cv2.resize(original_image, dim, interpolation=cv2.INTER_AREA)

        image_color = original_image.copy()

        processed_image = preprocess_image(image=original_image)

        img_final_bin = find_boxes(processed_image)

        # Find contours for image, which will detect all the boxes
        contours, hierarchy = cv2.findContours(img_final_bin, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)

        # Sort all the contours by top to bottom.
        (contours, boundingBoxes) = sort_contours(contours, method="top-to-bottom")

        save_results(save_dir=results_save_dir, image=image_color, all_contours=contours, image_name=image_path.name)

def processaAlunos(img):
    todosAlunos = []
    alunosPresentes = []
    imgFinal = img.copy()
    imgCerto = ff.carregaImagemCerto()

    linhasHorizontais, linhas = folhaPresenca.filtroDeLinhas(img)
    roiAlunos, roiAlunosLinhas = folhaPresenca.encontraTabelasAlunos(
        img, linhas)

    folhaInvalida = 0
    contador = 1
    #percorre as tabelas dos alunos encontradas
    for r in range(len(roiAlunos)):
        linhasAlunos = extraiLinhasAlunosIndividual(linhasHorizontais,
                                                    roiAlunosLinhas[r])
        larg = roiAlunos[r].shape[1]

        #percorre as linhas que definem cada espaço do aluno
        for i in range(len(linhasAlunos) - 1):
            (x1, Yi, x2, y2) = linhasAlunos[i]
            (x1, y1, x2, Yf) = linhasAlunos[i + 1]
            altura = Yf - Yi
            if altura < int(IMGY * 0.005):
                continue
            #extrai um aluno consuante as linhas
            Aluno = roiAlunos[r][Yi:Yf, 5:larg - 10]
            #extrai número de aluno consuante coordenadas fixas.
            nrAluno = Aluno[int(round(altura * 0.1)):int(round(altura * 0.93)),
                            int(round(larg * 0.1)):int(round(larg * 0.29))]
            #aproximação exata ao local do número de aluno
            nrAluno = encontraNumeroAluno(nrAluno)
            nrAlunoGray = cv2.cvtColor(nrAluno, cv2.COLOR_BGR2GRAY)
            ret, thresh = cv2.threshold(nrAlunoGray, 130, 255,
                                        cv2.THRESH_BINARY_INV)
            contours = cv2.findContours(thresh, cv2.RETR_EXTERNAL,
                                        cv2.CHAIN_APPROX_SIMPLE)
            contours = imutils.grab_contours(contours)
            if len(contours) > 0:
                contours = utils.sort_contours(contours,
                                               method="left-to-right")[0]
            larguraNumero = nrAluno.shape[1] / 10
            listaNr = []
            #percorre os números encontrados
            for c in contours:
                (x, y, w, h) = cv2.boundingRect(c)
                roi = nrAlunoGray[y:y + h, x:x + w]
                roi = cv2.addWeighted(roi, 1, roi, 0, -35)
                if cv2.arcLength(c, True) > 25:
                    if (w > larguraNumero + (larguraNumero * 0.5)):
                        primeiroNumero = nrAlunoGray[y:y + h,
                                                     x:int(x + (w / 2))]
                        primeiroNumero = cv2.addWeighted(
                            primeiroNumero, 1, primeiroNumero, 0, -35)
                        segundoNumero = nrAlunoGray[y:y + h,
                                                    int(x + (w / 2)):x + w]
                        segundoNumero = cv2.addWeighted(
                            segundoNumero, 1, segundoNumero, 0, -35)
                        listaNr.append(identificaNumeros(primeiroNumero))
                        listaNr.append(identificaNumeros(segundoNumero))
                    else:
                        listaNr.append(identificaNumeros(roi))
            n = ""
            for j in listaNr:
                n = n + str(j)
            if len(n) == 10:
                try:
                    numero_Aluno = int(n)
                except ValueError:
                    print(
                        "Não foi possível ler o número do aluno corretamente")
                    numero_Aluno = 0

                assinatura = Aluno[int(round(altura *
                                             0.25)):int(round(altura * 0.94)),
                                   int(round(larg *
                                             0.74)):int(round(larg * 0.97))]
                assinado, incerto = verificaAssinatura(assinatura)
                todosAlunos.append(numero_Aluno)
                if assinado:
                    ff.folhaFinal(imgFinal, roiAlunosLinhas[r], Yi, imgCerto)
                    alunosPresentes.append(numero_Aluno)

                print(
                    str(contador) + " - " + str(numero_Aluno) +
                    " = Assinatura incerta, verificar") if incerto else print(
                        str(contador) + " - " + str(numero_Aluno) +
                        " = PRESENTE") if assinado else print(
                            str(contador) + " - " + str(numero_Aluno))
                contador += 1

            else:
                numero_Aluno = int(n)
                print(
                    str(contador) +
                    " - Não foi possível ler o número do aluno corretamente -> "
                    + str(numero_Aluno))
                folhaInvalida += 1
                contador += 1
    if folhaInvalida > len(todosAlunos):
        quit("folha com problemas")

    imgFinal = cv2.resize(imgFinal, (1000, 1200))
    cv2.imshow("imagem Final", imgFinal)
    return todosAlunos, alunosPresentes