Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

cropping an image with respect to co ordinates selected

I am having an input image like this

enter image description here

Cropping the redpoints is easy since its a rectangle. How can i crop if the red point on 2,3,6 and 7 are moved to green points dynamically. These points may change how can i crop dynamically in program.

The result may look like this

enter image description here

I tried Warppperspective but i was unable to get expected result. The program was like this

import matplotlib.pyplot as plt
import numpy as np
import cv2

img = cv2.imread('sudoku_result.png')

pts1 = np.float32([[100,60],[260,60],[100,180],[260,180],[100,300],[260,300]])
pts2 = np.float32([[20,60],[340,60],[60,180],[300,180][100,300],[260,300]])

M = cv2.getPerspectiveTransform(pts1,pts2)
dst = cv2.warpPerspective(img,M,(360,360))


plt.subplot(121),plt.imshow(img),plt.title('Input')
plt.subplot(122),plt.imshow(dst),plt.title('Output')
plt.show()

I am new to image processing an would like to know which is the best method.

like image 336
ganeshredcobra Avatar asked Mar 11 '23 03:03

ganeshredcobra


1 Answers

Crop the enclosing rectangle the one created by (minX,minY,maxX,maxY) and then for each pixel in the cropped image you can check if the point inside the polygon created by the original points or not and for the points outside the original shape you put zero.

The code:

import cv2
import numpy as np

# Read a image
I = cv2.imread('i.png')

# Define the polygon coordinates to use or the crop
polygon = [[[20,110],[450,108],[340,420],[125,420]]]

# First find the minX minY maxX and maxY of the polygon
minX = I.shape[1]
maxX = -1
minY = I.shape[0]
maxY = -1
for point in polygon[0]:

    x = point[0]
    y = point[1]

    if x < minX:
        minX = x
    if x > maxX:
        maxX = x
    if y < minY:
        minY = y
    if y > maxY:
        maxY = y

# Go over the points in the image if thay are out side of the emclosing rectangle put zero
# if not check if thay are inside the polygon or not
cropedImage = np.zeros_like(I)
for y in range(0,I.shape[0]):
    for x in range(0, I.shape[1]):

        if x < minX or x > maxX or y < minY or y > maxY:
            continue

        if cv2.pointPolygonTest(np.asarray(polygon),(x,y),False) >= 0:
            cropedImage[y, x, 0] = I[y, x, 0]
            cropedImage[y, x, 1] = I[y, x, 1]
            cropedImage[y, x, 2] = I[y, x, 2]

# Now we can crop again just the envloping rectangle
finalImage = cropedImage[minY:maxY,minX:maxX]

cv2.imwrite('finalImage.png',finalImage)

The final image:

enter image description here

If you want to stretch the croped image

# Now strectch the polygon to a rectangle. We take the points that
polygonStrecth = np.float32([[0,0],[finalImage.shape[1],0],[finalImage.shape[1],finalImage.shape[0]],[0,finalImage.shape[0]]])

# Convert the polygon corrdanite to the new rectnagle
polygonForTransform = np.zeros_like(polygonStrecth)
i = 0
for point in polygon[0]:

    x = point[0]
    y = point[1]

    newX = x - minX
    newY = y - minY

    polygonForTransform[i] = [newX,newY]
    i += 1


# Find affine transform
M = cv2.getPerspectiveTransform(np.asarray(polygonForTransform).astype(np.float32), np.asarray(polygonStrecth).astype(np.float32))

# Warp one image to the other
warpedImage = cv2.warpPerspective(finalImage, M, (finalImage.shape[1], finalImage.shape[0]))
cv2.imshow('a',warpedImage)

enter image description here

like image 88
Amitay Nachmani Avatar answered Mar 31 '23 17:03

Amitay Nachmani