How to remove horizontal and vertical lines

I need to remove horizontal and vertical lines in a binary image. Is there a way to filter these lines? bwareaopen()

is not a good method to remove these lines, and Dilation and Erosion are not suitable for these cases. Does anyone know a solution?

Image example:

example

EDIT: (more example images added:

http://s1.upload7.ir/downloads/pPqTDnmsmjHUGTEpbwnksf3uUkzncDwr/example%202.png

original image file:

https://www.dropbox.com/sh/tamcdqk244ktoyp/AAAuxkmYgBkB8erNS9SajkGVa?dl=0

www.directexe.com/9cg/pics.rar

+3


source to share


3 answers


Use regionprops

and remove areas with high eccentricity (that is, the area is long and thin) and an orientation of about 0 or about 90 degrees (areas are vertical or horizontal).

Code:

img = im2double(rgb2gray(imread('removelines.jpg')));

mask = ~im2bw(img);

rp = regionprops(mask, 'PixelIdxList', 'Eccentricity', 'Orientation');

% Get high eccentricity and orientations at 90 and 0 degrees
rp = rp([rp.Eccentricity] > 0.95 & (abs([rp.Orientation]) < 2 | abs([rp.Orientation]) > 88));

mask(vertcat(rp.PixelIdxList)) = false;

imshow(mask);

      



Output:

enter image description here

+6


source


If all of your images match when the horizontal and vertical lines touch the border, a simple call imclearborder

would be Show Focus. imclearborder

removes any pixels from objects that touch the borders of the image. You will need to invert the image so that the characters are white and the background is dark and then go back again, but I assume this is not a problem. However, to be sure that none of the actual characters get deleted, as they might touch the border as well, it might be prudent to artificially overlay the top border of the image with one pixel thickness, clear the border, and then restore.

im = imread('http://i.stack.imgur.com/L1hUa.jpg'); %// Read image directly from StackOverflow

im = ~im2bw(im); %// Convert to black and white and invert
im_pad = zeros(size(im,1)+1, size(im,2)) == 1; %// Pad the image too with a single pixel border
im_pad(2:end,:) = im;

out = ~imclearborder(im_pad); %// Clear border pixels then reinvert
out = out(2:end,:); %// Crop out padded pixels

imshow(out); %// Show image

      



We get the following:

enter image description here

+3


source


You can find horizontal and vertical lines first. Since the edge map will also be binary, so you can perform logical subtraction between images. To find vertical lines you can use (in MATLAB)

BW = edge(I,'sobel','vertical');

      

For horizontal lines, you can use

% Generate horizontal edge emphasis kernel
h = fspecial('sobel');

% invert kernel to detect vertical edges
h = h';

J = imfilter(I,h);

      

+1


source







All Articles