Utilisation basique de matchTemplate cv2
Paya200 Messages postés 2 Date d'inscription Statut Membre Dernière intervention -
Bonjour,
Je suis débutant en programmation et j'aimerais utiliser très simplement, du moins le plus simplement possible, utiliser "matchTemplate" de cv2 dans python :
https://docs.opencv.org/4.x/d4/dc6/tutorial_py_template_matching.html
J'arrive à utiliser cette fonction comme dans l'exemple, c'est-à-dire en comparant mes deux images et en affichant le résultat. Mais je souhaite faire encore plus simple.
Comment puis-je juste comparer mes deux images et sortir uniquement un booléen,"true" si ma première image est détectée dans ma deuxième, "false" si ma première image n'est pas détectée dans ma deuxième.
Pouvez-vous, s'il vous plaît, m'aider à écrire ce script qui semble extrêmement simple ?
Merci d'avance pour vos réponses et bonne journée à vous :-)
2 réponses
Bonjour,
Si tu lis la documentation de matchTemplate, tu verras que la fonction permet de retrouver la région avec MinMaxLoc, qui elle même est utilisée dans l'exemple que tu as partagé. C'est le résultat de cette fonction qui permet de déterminer la position et la taille du rectangle dessiné sur l'image de droite (detected point).
Selon la méthode de reconnaissance d'image utilisée, le rectangle optimal est le min, soit le max.
# If the method is TM_SQDIFF or TM_SQDIFF_NORMED, take minimum if method in [cv.TM_SQDIFF, cv.TM_SQDIFF_NORMED]: top_left = min_loc else: top_left = max_loc
Cependant, j'ai l'impression que peu importe la méthode de reconnaissance d'image utilisée, matchTemplate retourne toujours un rectangle, même s'il est très mauvais. Je suppose donc qu'il faut regarder si la valeur retournée (min_val pour cv.TM_SQDIFF et cv.TM_SQNORMED) ne dépasse pas une valeur seuil (que tu devras choisir) pour déterminer si le résultat est acceptable ou non.
Je n'ai pas regardé les valeurs retournées par ces méthodes, mais d'après leur noms, je suspecte que les méthodes cv2.*NORMED retournent une valeur entre 0 et 1. Tu peux alors définir pour ces méthodes un seuil, par exemple, min_val < 0.1 pour cv.TM_SQDIFF_NORMED et max_loc > 0.9 pour les autres.
Je n'ai pas testé, mais voici à quoi ça pourrait peut-être ressembler :
import cv2 as cv import numpy as np from matplotlib import pyplot as plt img = cv.imread('messi5.jpg',0) img2 = img.copy() template = cv.imread('template.jpg',0) (w, h) = template.shape[::-1] methods = ['cv.TM_CCOEFF_NORMED', 'cv.TM_CCORR_NORMED', 'cv.TM_SQDIFF_NORMED'] for meth in methods: img = img2.copy() method = eval(meth) # Apply template Matching res = cv.matchTemplate(img, template, method) (min_val, max_val, min_loc, max_loc) = cv.minMaxLoc(res) # If the method is TM_SQDIFF or TM_SQDIFF_NORMED, take minimum print(min_val, max_val, min_loc, max_loc) if method in [cv.TM_SQDIFF, cv.TM_SQDIFF_NORMED]: top_left = min_loc found = min_val < 0.1 else: top_left = max_loc found = max_val > 0.9 bottom_right = (top_left[0] + w, top_left[1] + h) cv.rectangle(img,top_left, bottom_right, 255, 2) plt.subplot(121),plt.imshow(res,cmap = 'gray') plt.title('Matching Result'), plt.xticks([]), plt.yticks([]) plt.subplot(122),plt.imshow(img,cmap = 'gray') plt.title('Detected Point'), plt.xticks([]), plt.yticks([]) plt.suptitle(meth) plt.show() if found: print("FOUND") else: print("NOT FOUND")
Bonne chance