opencv图像透视处理

引言

在图像处理与计算机视觉领域,透视变换(Perspective Transformation)是一种重要的图像校正技术,它允许我们根据图像中已知的四个点(通常是矩形的四个角)和目标位置的四个点,将图像从一个视角映射到另一个视角。这种技术广泛应用于文档扫描、增强现实、图像拼接以及许多其他领域。本文将通过OpenCV这一强大的图像处理库,介绍如何执行图像的透视变换。

目录

引言

OpenCV简介

透视变换的基础

公式

OpenCV中的透视变换

步骤

结论


OpenCV简介

OpenCV(Open Source Computer Vision Library)是一个开源的计算机视觉和机器学习软件库。它包含了大量的图像处理函数和算法,可以运行在多种操作系统上,具有高效的性能和广泛的应用。

透视变换的基础

透视变换可以通过一个3x3的变换矩阵(也称为透视变换矩阵)来实现。这个矩阵定义了源图像和目标图像之间的映射关系。为了计算这个矩阵,我们需要知道源图像和目标图像中对应点的坐标。

公式

透视变换的数学表达式通常表示为:

begin{bmatrix} x' \\ y' \\ w' end{bmatrix} = begin{bmatrix} a_{11} & a_{12} & a_{13} \\ a_{21} & a_{22} & a_{23} \\ a_{31} & a_{32} & 1 end{bmatrix} begin{bmatrix} x \\ y \\ 1 end{bmatrix}

其中,(x,y) 是源图像中的点,(x′,y′) 是变换后图像中的对应点。w′ 是一个用于归一化的因子(通常不需要直接使用,但在计算时很有用)。

OpenCV中的透视变换

在OpenCV中,cv2.getPerspectiveTransform() 函数用于计算透视变换矩阵,而 cv2.warpPerspective() 函数则用于应用这个矩阵到图像上。

步骤

  1. 确定源点和目标点:首先,你需要从源图像中选取四个点(通常是矩形的四个角),并确定这四个点在目标图像中的位置。

  2. 计算透视变换矩阵 :使用 cv2.getPerspectiveTransform(src, dst) 来计算透视变换矩阵,其中 src 是源点坐标(形式为 (x, y) 的列表的列表),dst 是目标点坐标。

  3. 应用透视变换 :使用 cv2.warpPerspective(src_img, M, (width, height)) 将变换矩阵 M 应用到源图像 src_img 上,widthheight 是目标图像的宽度和高度。

代码示例

python 复制代码
import cv2  
import numpy as np  
  
# 读取图像  
img = cv2.imread('source_image.jpg')  
  
# 定义源点和目标点  
pts_src = np.float32([[56, 65], [368, 52], [28, 387], [389, 390]])  
pts_dst = np.float32([[0, 0], [300, 0], [0, 300], [300, 300]])  
  
# 计算透视变换矩阵  
M = cv2.getPerspectiveTransform(pts_src, pts_dst)  
  
# 应用透视变换  
height, width = img.shape[:2]  
warped_img = cv2.warpPerspective(img, M, (width, height))  
  
# 显示结果  
cv2.imshow('Warped Image', warped_img)  
cv2.waitKey(0)  
cv2.destroyAllWindows()

代码实例

python 复制代码
import cv2
import numpy as np


def order_points(pts):
    """
    根据点的位置对它们进行排序,以便左上角、右上角、右下角、左下角的顺序。
    这里使用简单的排序逻辑,可能需要根据实际情况调整。
    """
    rect = np.zeros((4, 2), dtype="float32")

    # 按x坐标排序,然后按y坐标排序(如果需要)
    s = pts.sum(axis=1)
    rect[0] = pts[np.argmin(s)]
    rect[2] = pts[np.argmax(s)]

    # 计算x坐标的差值
    diff = np.diff(pts, axis=1)
    rect[1] = pts[np.argmin(diff)]
    rect[3] = pts[np.argmax(diff)]

    return rect


def four_point_transform(image, pts):
    """
    对图像进行透视变换。
    :param image: 输入图像
    :param pts: 源图像中的四个点(矩形的四个角),格式为[(x1, y1), (x2, y2), (x3, y3), (x4, y4)]
    :return: 变换后的图像
    """
    rect = order_points(pts)
    (tl, tr, br, bl) = rect

    # 计算目标矩形的宽度
    widthA = np.linalg.norm(br - bl)
    widthB = np.linalg.norm(tr - tl)
    maxWidth = max(int(widthA), int(widthB))

    # 计算目标矩形的高度
    heightA = np.linalg.norm(tr - br)
    heightB = np.linalg.norm(tl - bl)
    maxHeight = max(int(heightA), int(heightB))

    # 目标点
    dst = np.array([
        [0, 0],
        [maxWidth - 1, 0],
        [maxWidth - 1, maxHeight - 1],
        [0, maxHeight - 1]], dtype="float32")

    # 计算透视变换矩阵并应用它
    M = cv2.getPerspectiveTransform(rect, dst)
    warped = cv2.warpPerspective(image, M, (maxWidth, maxHeight))

    # 返回变换后的图像
    return warped


# 读取图像
image = cv2.imread('bea.jpg')
if image is None:
    print("Error: Unable to load image.")
else:
    # 假设我们手动选取了文档的四个角点(这里用示例坐标代替)
    pts = np.array([[56, 65], [368, 52], [28, 387], [389, 390]], dtype="float32")

    # 进行透视变换
    warped_image = four_point_transform(image, pts)

    # 显示结果
    cv2.imshow('Original Image', image)
    cv2.imshow('Warped Image', warped_image)
    cv2.waitKey(0)
    cv2.destroyAllWindows()

结果:

结论

通过本文,我们学习了如何使用OpenCV进行图像的透视变换。从理论基础到实践代码,我们逐步了解了透视变换的整个过程。这项技术不仅可以用于图像校正,还可以为许多其他应用提供强大的支持。希望本文能为你处理图像透视变换提供有力的帮助。

相关推荐
AI_NEW_COME31 分钟前
知识库管理系统可扩展性深度测评
人工智能
海棠AI实验室1 小时前
AI的进阶之路:从机器学习到深度学习的演变(一)
人工智能·深度学习·机器学习
hunteritself1 小时前
AI Weekly『12月16-22日』:OpenAI公布o3,谷歌发布首个推理模型,GitHub Copilot免费版上线!
人工智能·gpt·chatgpt·github·openai·copilot
IT古董2 小时前
【机器学习】机器学习的基本分类-强化学习-策略梯度(Policy Gradient,PG)
人工智能·机器学习·分类
centurysee2 小时前
【最佳实践】Anthropic:Agentic系统实践案例
人工智能
mahuifa2 小时前
混合开发环境---使用编程AI辅助开发Qt
人工智能·vscode·qt·qtcreator·编程ai
四口鲸鱼爱吃盐2 小时前
Pytorch | 从零构建GoogleNet对CIFAR10进行分类
人工智能·pytorch·分类
蓝天星空2 小时前
Python调用open ai接口
人工智能·python
睡觉狂魔er2 小时前
自动驾驶控制与规划——Project 3: LQR车辆横向控制
人工智能·机器学习·自动驾驶
scan7242 小时前
LILAC采样算法
人工智能·算法·机器学习