Am trying to perform image warping but i can’t seem to apply the transformation matrix given a set of points. Am trying to accomplish is a face morphing given the feature points wich in total is 68 feature points i already calculated the triangulation between the points but i cant seem to warp the image.
Face.py
import numpy as np
import cv2 as cv
import dlib
from warp import triangulate, warp
def crop_faces(image1_path, image2_path):
cropped_faces_list = []
for img in [image1_path, image2_path]:
image = cv.imread(img)
# convert to grayscale of each frames
gray = cv.cvtColor(image, cv.COLOR_BGR2GRAY)
# read the haarcascade to detect the faces in an image
face_cascade = cv.CascadeClassifier(cv.data.haarcascades + 'haarcascade_frontalface_default.xml')
# detects faces in the input image
faces = face_cascade.detectMultiScale(gray, 1.3, 4)
print('Number of detected faces:', len(faces))
# Crop and save each detected face
cropped_faces = []
if len(faces) > 0:
for (x, y, w, h) in faces:
cropped_faces.append(image[y: y + h, x:x + w])
cropped_faces_list.append(cropped_faces)
return cropped_faces_list
def generate_face_correspondeces(theImage1, theImage2):
# Detect the points of face.
detector = dlib.get_frontal_face_detector()
predictor = dlib.shape_predictor('shape_predictor_68_face_landmarks.dat')
imgList = crop_faces(theImage1, theImage2)
list1 = []
list2 = []
feature_points = []
cropped_images = []
j = 1
for m, img_list in enumerate(imgList):
for img in img_list:
if (j == 1):
currList = list1
else:
currList = list2
# Ask the detector to find the bounding boxes of each face. The 1 in the
# second argument indicates that we should upsample the image 1 time. This
# will make everything bigger and allow us to detect more faces.
dets = detector(img, 1)
try:
if len(dets) == 0:
raise NoFaceFound # type: ignore
except NoFaceFound: # type: ignore
print("Sorry, but I couldn't find a face in the image.")
j = j + 1
for k, rect in enumerate(dets):
# Get landmarks/part for the face in rect
shape = predictor(img, rect)
for i in range(0, 68):
x = shape.part(i).x
y = shape.part(i).y
currList.append((x, y))
cv.circle(img, (x, y), 1, (0, 255, 0), 2)
feature_points.append(currList)
cropped_images.append(img)
cv.imwrite(f"test_{m}.png", img)
return feature_points, cropped_images
img1 = './Images/mulher1.jpg'
img2 = './Images/homem.jpg'
feature_points, cropped_images = generate_face_correspondeces(img1, img2)
for i, image in enumerate(cropped_images):
triangulate(image, feature_points[i])
warp(img2, feature_points[0], feature_points[1])
Warp.py
import numpy as np
import cv2 as cv
def triangulate(image, points):
# Create Subdiv2D object
rect = (0, 0, image.shape[0], image.shape[1]) # Rectangle covering the entire image
triangulation = cv.Subdiv2D(rect)
# Insert points into triangulation object
valid_points = [] # List to store valid points within the image bounds
for point in points:
x, y = point
if 0 <= x < image.shape[1] and 0 <= y < image.shape[0]: # Check if point is within image bounds
triangulation.insert((x, y))
valid_points.append((x, y))
# Get triangles
triangleList1 = triangulation.getTriangleList()
# Draw triangles on the image (optional)
for t in triangleList1:
pt1 = (int(t[0]), int(t[1]))
pt2 = (int(t[2]), int(t[3]))
pt3 = (int(t[4]), int(t[5]))
cv.line(image, pt1, pt2, (0, 255, 0), 1, cv.LINE_AA)
cv.line(image, pt2, pt3, (0, 255, 0), 1, cv.LINE_AA)
cv.line(image, pt3, pt1, (0, 255, 0), 1, cv.LINE_AA)
# Show or return the triangulated image (optional)
cv.imshow('Triangulated Image', image)
cv.waitKey(0)
cv.destroyAllWindows()
return valid_points
def warp(image, points1, points2):
# Compute affine transformation matrix
M = cv.getAffineTransform(np.float32(points1), np.float32(points2))
# Warp image1 onto image2
rows, cols, _ = image.shape
warped_image = cv.warpAffine(image, M, (cols, rows))
# Display or save the warped image
cv.imshow('Warped Image', warped_image)
cv.waitKey(0)
cv.destroyAllWindows()
Am getting this error
M = cv.getAffineTransform(np.float32(points1), np.float32(points2))
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
cv2.error: OpenCV(4.9.0) D:aopencv-pythonopencv-pythonopencvmodulesimgprocsrcimgwarp.cpp:3554: error: (-215:Assertion failed) src.checkVector(2, CV_32F) == 3 && dst.checkVector(2, CV_32F) == 3 in function 'cv::getAffineTransform'