import numpy as np
import cv2


def draw_borderline(img, corners):
    copy_image = img.copy()
    for pt in corners:
        cv2.circle(copy_image, tuple(pt), 20, (0, 255, 255), -1, 1)
    cv2.line(copy_image, tuple(corners[0]), tuple(corners[1]), (0, 255, 255), 4, 5)
    cv2.line(copy_image, tuple(corners[1]), tuple(corners[2]), (0, 255, 255), 4, 5)
    cv2.line(copy_image, tuple(corners[2]), tuple(corners[3]), (0, 255, 255), 4, 5)
    cv2.line(copy_image, tuple(corners[3]), tuple(corners[0]), (0, 255, 255), 4, 5)
    return copy_image


def onMouse(event, x, y, flags, param):
    global points
    if event == cv2.EVENT_LBUTTONDOWN:
        for i in range(4):
            if cv2.norm(start_points[i] - (x, y)) < 20:
                drag_points[i] = True
                points = (x, y)
                break

    if event == cv2.EVENT_LBUTTONUP:
        for i in range(4):
            drag_points[i] = False

    if event == cv2.EVENT_MOUSEMOVE:
        for i in range(4):
            if drag_points[i]:
                dx = x - points[0]
                dy = y - points[1]
                start_points[i] += (dx, dy)
                cpy = draw_borderline(image, start_points)
                cv2.imshow('image', cpy)
                points = (x, y)
                break


# 불러올 이미지 지정

image = cv2.imread('text_book.jpg')
print(image.shape)
# 이미지 세로와 너비 추출
h, w = image.shape[:2]

# 결과 영상 화면 세팅 (210 * 297) a4 용지 규격으로 설정함.
result_w = 210 * 3
result_h = 297 * 3

# 모서리 점들의 좌표, 드래그 상태 여부
start_points = np.array([[50, 50], [50, h-50], [w-50, h-50], [w-50, 50]], np.float32)
end_points = np.array([[0, 0], [0, result_h-1], [result_w-1, result_h-1], [result_w-1, 0]], np.float32)

# 현재 드래그 하는 포인트를 기억하는 함수, 눌러지게 되면 True로 변경됨, 놓으면 다시 False
drag_points = [False, False, False, False]

# 모서리점, 사각형 그리기
borderline = draw_borderline(image, start_points)
cv2.namedWindow('image',cv2.WINDOW_NORMAL)
# cv2.resizeWindow('image', int(h/4), int(w/4))
cv2.imshow('image', borderline)
cv2.setMouseCallback('image', onMouse)

while True:
    key = cv2.waitKey()
    if key == 13:
        break
    elif key == 27:
        cv2.destroyWindow('image')

# 투시 변환
perspective_transform = cv2.getPerspectiveTransform(start_points, end_points)
final_result = cv2.warpPerspective(image, perspective_transform, (result_w, result_h), flags=cv2.INTER_CUBIC)

# 결과 영상 출력
cv2.imshow('dst', final_result)
cv2.waitKey()
cv2.destroyAllWindows()
반응형

+ Recent posts