Transformación de imágenes en OpenCV.

Esta pregunta está relacionada con esta pregunta: How to remove convexity defects in sudoku square

Estaba intentando implementar nikie's answer en Mathematica to OpenCV-Python . Pero estoy atascado en el paso final del procedimiento.

es decir, tengo todos los puntos de intersección en el cuadrado como a continuación:

introduzca la descripción de la imagen aquí

Ahora, quiero transformar esto en un cuadrado perfecto de tamaño (450,450) como se indica a continuación:

introduzca la descripción de la imagen aquí

(No importa la diferencia de brillo de dos imágenes).

Pregunta: ¿Cómo puedo hacer esto en OpenCV-Python? Estoy usando la versión cv2 .

Además de la sugerencia de etarion, también puede utilizar la función de reasignación . Escribí un guión rápido para mostrar cómo puedes hacer esto. Como ves, la encoding es muy fácil en Python. Esta es la imagen de prueba:

imagen distorsionada

y este es el resultado después de la deformación:

imagen deformada

Y aquí está el código:

 import cv2 from scipy.interpolate import griddata import numpy as np grid_x, grid_y = np.mgrid[0:149:150j, 0:149:150j] destination = np.array([[0,0], [0,49], [0,99], [0,149], [49,0],[49,49],[49,99],[49,149], [99,0],[99,49],[99,99],[99,149], [149,0],[149,49],[149,99],[149,149]]) source = np.array([[22,22], [24,68], [26,116], [25,162], [64,19],[65,64],[65,114],[64,159], [107,16],[108,62],[108,111],[107,157], [151,11],[151,58],[151,107],[151,156]]) grid_z = griddata(destination, source, (grid_x, grid_y), method='cubic') map_x = np.append([], [ar[:,1] for ar in grid_z]).reshape(150,150) map_y = np.append([], [ar[:,0] for ar in grid_z]).reshape(150,150) map_x_32 = map_x.astype('float32') map_y_32 = map_y.astype('float32') orig = cv2.imread("tmp.png") warped = cv2.remap(orig, map_x_32, map_y_32, cv2.INTER_CUBIC) cv2.imwrite("warped.png", warped) 

Supongo que puedes buscar en google y encontrar lo que hace griddata. En resumen, hace interpolación y aquí la usamos para convertir asignaciones dispersas en asignaciones densas, ya que cv2.remap requiere asignaciones densas. Solo tenemos que convertir los valores a float32 ya que OpenCV se queja del tipo float64. Hágame saber como va por favor.

Actualización : si no desea confiar en Scipy, una forma es implementar la función de interpolación 2d en su código, por ejemplo, ver el código fuente de griddata en Scipy o uno más simple como este http: //inasafe.readthedocs .org / es / latest / _modules / engine / interpolation2d.html que depende solo de numpy. Sin embargo, sugeriría usar Scipy u otra biblioteca para esto, aunque veo por qué requerir solo CV2 y numpy puede ser mejor para un caso como este. Me gustaría saber cómo resuelve Sudokus tu código final.

Si tiene puntos de origen y puntos finales (solo necesita 4), puede conectarlos en cv2.getPerspectiveTransform, y usar ese resultado en cv2.warpPerspective. Te da un buen resultado plano.