Résoudre la correspondance entre les pixels de l'image entre différentes caméras (solution matricielle d'homographie)

1. Scène

        Les positions relatives de la caméra 1 et de la caméra 2 restent inchangées et les images prises par les caméras se chevauchent. Trouvez la correspondance biunivoque entre leurs parties qui se chevauchent. La description du langage mathématique est que le pixel (u1, v1) du point P dans l'image de la caméra 1 est connu, et la valeur du pixel du point P dans la caméra 1 dans l'image de la caméra 2 est (u2, v2). une sorte de transformation entre eux, alors trouvez la matrice de transformation.

        Étant donné que la scène impliquée est relativement simple et n'implique actuellement pas de profondeur, et que la cible collectée en même temps est approximativement plane, la scène peut être simplifiée et résolue à l'aide d'une matrice d'homographie. Par conséquent, la matrice de transformation impliquée ci-dessus est supposée être la matrice d'homographie H (matrice 3*3), et elle satisfait la relation suivante.

         Dans ce cas, c'est beaucoup plus simple (si la scène est complexe, implique de la profondeur ou si l'objet d'acquisition n'est pas un plan, on peut utiliser la méthode matrice essentielle/matrice de base pour obtenir la matrice de transformation), et il suffit d'utiliser la plaque d'étalonnage standard pour calculer H.

2. Matrice d'homographie

        Définition : Il existe une homographie entre des images de [le même objet plan] prises depuis différentes positions avec une caméra [d'imagerie idéale] , qui peut être exprimée par [une transformation de perspective] . Il existe la formule suivante :

         L'étape suivante consiste à résoudre la matrice H. La formule ci-dessus est développée comme suit :

         Sur la base de la relation correspondante entre les coordonnées planes et les coordonnées homogènes, la formule ci-dessus peut être exprimée comme suit :

         plus loin,

        Écrivez-le sous la forme AX=0, comme suit. Il existe de nombreuses façons de résoudre ce formulaire, qui sont également abordées dans le blog précédent . Cependant, il faut souligner que bien que la matrice H comporte 9 inconnues, elle ne possède que 8 degrés de liberté (relation plane), parmi lesquels h33=1. Par conséquent, seuls 4 points non colinéaires sont nécessaires pour résoudre l’équation.

 

3. Effet réel

3.1 Tout le code

#!/usr/bin/env python
# -*- coding: utf-8 -*-
import cv2
import numpy as np


def OnMouseAction(event, x, y, flags, param):
    """
    鼠标的回调函数,处理鼠标事件
    :param event:
    :param x:
    :param y:
    :param flags:
    :param param:
    :return:
    """
    if event == cv2.EVENT_LBUTTONDOWN:
        global gimg_x, gimg_y, gis_ok
        gimg_x = x
        gimg_y = y
        gis_ok = True
    elif event == cv2.EVENT_RBUTTONDOWN:
        print("右键点击")
    elif flags == cv2.EVENT_FLAG_LBUTTON:
        print("左鍵拖曳")
    elif event == cv2.EVENT_MBUTTONDOWN:
        print("中键点击")


def verification(img1, img2, H):
    def nothing(x):
        pass

    cv2.namedWindow('image1')
    cv2.setMouseCallback('image1', OnMouseAction)
    # create trackbars for color change
    cv2.createTrackbar('thr', 'image1', 121, 255, nothing)
    cv2.createTrackbar('Shading', 'image1', 255, 255, nothing)
    count = 0
    while True:
        cv2.imshow("image1", img1)
        cv2.imshow("image2", img2)

        k = cv2.waitKey(1) & 0xFF
        # 通过关闭窗口的右上角关闭
        if cv2.getWindowProperty('image1', cv2.WND_PROP_AUTOSIZE) < 1:
            break
        # 通过按键盘的ESC退出
        if k == 27:
            break
        global gimg_x, gimg_y, gis_ok
        if gis_ok:
            count += 1
            cv2.circle(img1, (gimg_x, gimg_y), 3, (0, 0, 255), -1)
            cv2.putText(img1, str(count), (gimg_x, gimg_y), 2, 1, (0, 0, 255))
            gis_ok = False

            (x, y, z) = np.matmul(H, np.array([gimg_x, gimg_y, 1]).T)

            cv2.circle(img2, (int(x / z), int(y / z)), 2, (0, 0, 255), -1)
            cv2.putText(img2, str(count), (int(x / z), int(y / z)), 2, 1, (0, 0, 255))


def getHomography(img1, img2):
    gray1 = cv2.cvtColor(img1, cv2.COLOR_BGR2GRAY)
    gray2 = cv2.cvtColor(img2, cv2.COLOR_BGR2GRAY)
    criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 30, 0.001)

    ret, corners1_1 = cv2.findChessboardCorners(gray1, (gcols, grows), None)
    if not ret:
        return ret, None
    # sub-pixel corner detection
    corners1_2 = cv2.cornerSubPix(gray1, corners1_1, (11, 11), (-1, -1), criteria)

    ret, corners2_1 = cv2.findChessboardCorners(gray2, (gcols, grows), None)
    if not ret:
        return ret, None
    # sub-pixel corner detection
    corners2_2 = cv2.cornerSubPix(gray2, corners2_1, (11, 11), (-1, -1), criteria)

    H, mask = cv2.findHomography(corners1_2, corners2_2, cv2.RANSAC)

    return True, H


gimg1Root = "./image_homography/1080p_1.png"
gimg2Root = "./image_homography/1080p_2.png"
gimg3Root = "./image_homography/720p_3.png"
(grows, gcols) = (8, 11)
def main():
    img1 = cv2.imread(gimg1Root)
    img2 = cv2.imread(gimg3Root)
    is_ok, H = getHomography(img1, img2)
    print(H)

    verification(img1, img2, H)


global gimg_x, gimg_y, gis_ok
gimg_x = 0
gimg_y = 0
gis_ok = False
if __name__ == "__main__":
    main()

3.2 Effet réel

 

Je suppose que tu aimes

Origine blog.csdn.net/qq_31112205/article/details/129047100
conseillé
Classement