Как я могу преобразовать вид камеры в декартову плоскость вида сверху в opencv python? - PullRequest
0 голосов
/ 27 мая 2020

У меня видеопоток идет с камеры под углом, я хочу видеть кадр сверху, но только для движущейся точки. Изображение не обязательно должно быть завернуто или растянуто. Все, что я хочу, это сопоставить диапазон указателя от исходного изображения до декартовой плоскости (вид сверху). См. Изображения ниже.

код на данный момент

import cv2
import numpy as np
ix = 0
iy = 0


def draw_circle(event, x, y, flags, param):
    global ix, iy
    if event == cv2.EVENT_MOUSEMOVE:
        ix = x
        iy = y


img = cv2.imread("./maxresdefault.jpg")
h, w, c = img.shape
ones = np.zeros((h, w))
left, top = 50, 50
right, bottom = w - 50, h - 50
cv2.namedWindow('main_image')
while True:
    ones_copy = ones.copy()
    cv2.setMouseCallback('main_image', draw_circle)
    cv2.rectangle(ones, (left, top), (right, bottom), (255, 255, 255), 2)
    cv2.circle(ones_copy, (ix, iy), 2, (255, 255, 255), 2)
    cv2.imshow("main_image", img)
    cv2.imshow("ones", ones_copy)
    cv2.waitKey(32)
# coords = [[54, 199], [520, 336], [542, 177], [233, 121]]
# coords = [[233, 121]]
# y = ((x / 99.0) * 2) - 1

enter image description here

enter image description here

1 Ответ

1 голос
/ 27 мая 2020

Таким образом, изображение не нужно преобразовывать, но базовое пиксельное пространство необходимо. Я не эксперт, но, как мне кажется, математика довольно сложна. Поэтому, если вас интересует только результат, я предлагаю воспользоваться простым подходом:

Создать черное изображение с размером входного кадра
Нарисуйте белую точку в позиции курсора
Преобразуйте черное изображение в прямоугольник (описан здесь )

Обратите внимание, что точка также будет растянутой. Если вам нужна декартова позиция x, y, вы можете найти первый белый пиксель в массиве изображений или вычислить среднее положение. Или, например, используйте findcontours , а затем findEnclosingCircle , чтобы получить центр x, y.

Для справки я добавил пример, но поскольку это всего лишь процесс, связанный с выше (со смешанным интерфейсом мыши), я не буду его подробно объяснять. Обратите внимание, что порядок, в котором щелкают угловые точки, имеет значение, он должен быть по часовой стрелке.

Результат (курсор находился на пластине): enter image description here

import cv2
import numpy as np

img_ori = cv2.imread('img.jpg')
img = img_ori.copy()
base = np.zeros((img_ori.shape[:2]))

l = []
setup = True
m = 0

def getTransform(points):
    # from documentation linked above
    pts1 = np.float32(points)
    pts2 = np.float32([[0,0],[300,0],[300,300],[0,300]])

    return cv2.getPerspectiveTransform(pts1,pts2)

def processMouse(event,x,y,flags,params):
    global l,setup,m
    if setup:
        # create ROI + getTransform when 4 corners are clicked
        if event == cv2.EVENT_LBUTTONDOWN:
            l.append([x,y])
            cv2.circle(img, (x,y), 5,(255,0,0),3)
            cv2.imshow('IMG',img)
            if(len(l)) == 4:
                m = getTransform(l)
                setup = False
    else:
        # draw mouse position

        # with image
        img2 = img_ori.copy()
        cv2.circle(img2, (x,y), 5,(0,0,255),-1)
        dst =   cv2.warpPerspective(np.float32(img2), m, (300,300))
        dst = np.array(dst, dtype='uint8')
        cv2.imshow('IMG2',dst)

        # black 
        img3 = base.copy()
        cv2.circle(img3, (x,y), 5,(255),-1)
        dst =   cv2.warpPerspective(np.float32(img3), m, (300,300))
        dst = np.array(dst, dtype='uint8')
        cv2.imshow('IMG3',dst)


cv2.namedWindow('IMG')
cv2.setMouseCallback("IMG",processMouse)
cv2.imshow('IMG',img)

cv2.waitKey(0)
cv2.destroyAllWindows()
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...