The image of the code is in the link given with this question. (https://i.stack.imgur.com/zq8V8.png) Even when I pass the wrong image as the 'main' image , the template still matches. And even when I give the main image and the template(that is actually a part of main image ) then also the 'for' loop fails to run because the rectangle never gets drawn on the main image. As for the code , it is available in almost all the links when you google 'template matching in openCV python'

# Python program to illustrate
# template matching
import cv2
import numpy as np

# Read the main image
img_rgb = cv2.imread('test.jpg')

# Convert it to grayscale
img_gray = cv2.cvtColor(img_rgb, cv2.COLOR_BGR2GRAY)

# Read the template
template = cv2.imread('cropped1.jpg',0)

# Store width and heigth of template in w and h
w, h = template.shape[::-1]

# Perform match operations.
res = cv2.matchTemplate(img_gray,template,cv2.TM_CCOEFF_NORMED)

# Specify a threshold
threshold = 0.8

# Store the coordinates of matched area in a numpy array
loc = np.where( res >= threshold)

# Draw a rectangle around the matched region.
for pt in zip(*loc[::-1]):
    cv2.rectangle(img_rgb, pt, (pt[0] + w, pt[1] + h), (0,255,255), 2)



# Show the final image with the matched area.
cv2.imshow('Detected',img_rgb)
cv2.waitKey(0)
1

There are 1 best solutions below

0
On

(actually, I think this will not solve your problem, as you say your template matching isn't working, but i'll leave the answer for future use, as this should also be checked, to be sure that the for loop won't make your program crash by writing out of the image)

When drawing a rect (or anything else) you should be very sure (escape all cases) that your rect won't go out of the image size. I think that your rect ending point is going out of the image bounds, when you add w and h here:

cv2.rectangle(img_rgb, pt, (pt[0] + w, pt[1] + h), (0,255,255), 2)

try something like this (there may be errors, i usually code in c++ and haven't checked this snippet, but the idea behind should be clear:

for pt in zip(*loc[::-1]):
    if pt[0] > 0 and pt[1]>0 and pt[0] < img_rgb.width and pt[1] < img_rgb.height
        endPt[0] = max(pt[0] + w, img_rgb.width)
        endPt[1] = max(pt[1] + h, img_rgb.height)
        cv2.rectangle(img_rgb, pt, endPt, (0,255,255), 2)