Search code examples
pythonimageopencvin-place

Opencv: How to use rectangle() function to draw a rectangle on a COPY of an image rather than the original image?


this is what I am trying to accomplish. I have some images with multiple bounding boxes associated with each image. I want to load an image, draw box1 on image, and save the new image as image_1. Then I want to draw box2 on image, and save it as image_2. The problem I am having currently is that image_2 ends up with both box1 and box2 on it, rather than just box2. I tried to circumvent the issue by saving a temporary copy of the image each time I draw a new bounding box, but it seems like the original image still gets modified somehow. How can I create a copy of the loaded img such that changes to the copy will not get propagated to the loaded img when I call opencv's rectangle() function? Below is what I have currently.

for fname in boxes:
    img = cv2.imread(fname, -1)
    for i in range(len(boxes[fname])):
        x1, y1, x2, y2 = boxes[fname][i]
        tmp = img
        cv2.rectangle(tmp, (x1, y1), (x2, y2), (255,0,0), 2)
        cv2.imwrite(fname+str(i+1), tmp)

Solution

  • This can be accomplished fairly easily using numpy.

    for i in range(len(boxes[fname])):
       temp = numpy.copy(img)
       .....
    

    This ensures you actually create a copy of the image as in python this

    tmp = img
    

    is just creating a new pointer to the same image that the tag 'img' points to. That's why if you edit tmp, you also edit img.