This image is the first processed image from a map created with a LiDAR sensor.
If you look closely at the image, there are many bumpy parts that are not exactly straight lines.
I want to make the result like this image.
This is the first map image scanned with LiDAR.
I tried using the hough line, but it’s not perfect.
I would like to figure out a method that can be applied in different situations
Here is my code.
import numpy as np
import math
import cv2
def get_dist(pt1, pt2):
return math.hypot(pt1[0]-pt2[0], pt1[1]-pt2[1])
def reorderPts(pts):
idx = np.lexsort((pts[:, 1], pts[:, 0]))
pts = pts[idx]
if pts[0, 1] > pts[1, 1]:
pts[[0, 1]] = pts[[1, 0]]
if pts[2, 1] < pts[3, 1]:
pts[[2, 3]] = pts[[3, 2]]
return pts
def solve(src):
H, W = src.shape[:2]
dst = src.copy()
gray = cv2.cvtColor(src, cv2.COLOR_BGR2GRAY)
_, bin = cv2.threshold(gray, 127, 255, cv2.THRESH_BINARY)
bin = cv2.erode(bin, np.ones((5, 5)))
cv2.floodFill(bin, np.zeros((H+2, W+2), np.uint8), (0, 0), 0)
bin = cv2.medianBlur(bin, 7)
nonRectArea = bin.copy()
cv2.floodFill(nonRectArea, np.zeros((H+2, W+2), np.uint8), (W//2, H//2), 0)
bin[np.where(nonRectArea == 255)] = 0
contours, _ = cv2.findContours(bin, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
rect = cv2.minAreaRect(contours[0])
box = cv2.boxPoints(rect)
box = np.int0(box)
cv2.drawContours(dst, [box], 0, (0, 255, 0), 1)
srcQuad = reorderPts(box.reshape(4, 2).astype(np.float32))
dw = int(get_dist(srcQuad[0], srcQuad[3])*2)
dh = int(get_dist(srcQuad[0], srcQuad[1])*2)
dstQuad = np.array([[0, 0], [0, dh], [dw, dh], [dw, 0]], np.float32)
pers = cv2.getPerspectiveTransform(srcQuad, dstQuad)
dst = cv2.warpPerspective(src, pers, (dw, dh))
gray = cv2.cvtColor(dst, cv2.COLOR_BGR2GRAY)
_, thresh = cv2.threshold(gray, 127, 255, cv2.THRESH_BINARY_INV)
thresh = cv2.morphologyEx(thresh, cv2.MORPH_CLOSE, np.ones((25, 25)))
lines = cv2.HoughLinesP(thresh, 0.8, np.pi/180, 80, minLineLength=30, maxLineGap=100)
w, h = dst.shape[:2]
mask = np.zeros((w, h), dtype=np.uint8)
for line in lines:
x1, y1, x2, y2 = line[0]
cv2.line(dst, (x1,y1), (x2, y2), (0,255,0), 3)
cv2.line(mask, (x1,y1), (x2, y2), 255, 3)
mask = cv2.morphologyEx(mask, cv2.MORPH_OPEN, np.ones((7, 7), dtype=np.uint8))
thresh = cv2.bitwise_and(thresh,thresh,mask=~mask)
thresh = cv2.morphologyEx(thresh, cv2.MORPH_OPEN, np.ones((9, 9), dtype=np.uint8))
cv2.imshow("src", src)
cv2.imshow("dst", dst)
cv2.imshow("thresh", thresh)
cv2.waitKey()
src = cv2.imread('map.png')
solve(src)
This is code result.