OpenCV 光流Optical Flow示例

下面是对于“OpenCV 光流Optical Flow示例”的完整攻略以及两个示例说明。

简介

Optical Flow是指在视频中的相邻两帧之间,在像素级别上计算出像素点在两帧之间的位移的技术。OpenCV是一个广泛使用的计算机视觉库,也支持光流技术。本攻略将介绍如何使用OpenCV进行光流分析。

步骤

  1. 安装OpenCV。

如果你还没有安装OpenCV,请先前往官方网站下载安装。

  1. 加载视频。

将视频加载到OpenCV中。

import cv2

cap = cv2.VideoCapture('path/to/video')
  1. 设置参数。

设置角点检测器的最大角点数,角点检测器的质量水平等等。

feature_params = dict(maxCorners=100, qualityLevel=0.3, minDistance=7, blockSize=7)
lk_params = dict(winSize=(15, 15), maxLevel=2, criteria=(cv2.TERM_CRITERIA_EPS | cv2.TERM_CRITERIA_COUNT, 10, 0.03))
color = (0, 255, 0)
  1. 计算光流。

计算相邻两帧之间的光流,并将其绘制到新图像中。

# 读取一帧
ret, old_frame = cap.read()
old_gray = cv2.cvtColor(old_frame, cv2.COLOR_BGR2GRAY)

# 寻找角点
p0 = cv2.goodFeaturesToTrack(old_gray, mask=None, **feature_params)

# 创建一个mask用来绘制轨迹
mask = np.zeros_like(old_frame)

# 循环读取视频并计算光流
while True:
    ret, frame = cap.read()
    if not ret:
        break
    frame_gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)

    p1, st, err = cv2.calcOpticalFlowPyrLK(old_gray, frame_gray, p0, None, **lk_params)

    good_new = p1[st == 1]
    good_old = p0[st == 1]

    # 绘制轨迹
    for i, (new, old) in enumerate(zip(good_new, good_old)):
        a, b = new.ravel()
        c, d = old.ravel()
        mask = cv2.line(mask, (a, b), (c, d), color, 2)
        frame = cv2.circle(frame, (a, b), 5, color, -1)
    img = cv2.add(frame, mask)
    cv2.imshow('frame', img)

    # 更新帧和角点点
    old_gray = frame_gray.copy()
    p0 = good_new.reshape(-1, 1, 2)

    k = cv2.waitKey(30) & 0xff
    if k == 27:
        break

cv2.destroyAllWindows()
cap.release()

示例1

在这个示例中,我们模拟一个二维的均匀平移,它会随着时间的推移而减小。

import cv2
import numpy as np

# 创建画布
canvas = np.zeros((400, 400), dtype="uint8")

# 初始化变量
shift = 0
delta = 4

# 绘制旋转方格
for x in range(10, 390, 25):
    shift += delta
    pts = np.array([[10 + shift, x], [390, x], [390 - shift, x + 25], [10, x + 25]], dtype=np.int32)
    cv2.fillConvexPoly(canvas, pts, (255))

# 循环将画布变换
for i in range(120):
    M = np.float32([[1, 0, i * 3], [0, 1, 0]])
    rotated = cv2.warpAffine(canvas, M, (400, 400))

    # 计算光流
    flow = cv2.calcOpticalFlowFarneback(canvas, rotated, None, 0.5, 3, 25, 3, 5, 1.2, 0)
    magnitude, angle = cv2.cartToPolar(flow[..., 0], flow[..., 1])

    # 构造HSV图像
    hsv = np.zeros((400, 400, 3), dtype="uint8")
    hsv[..., 0] = angle * (180 / np.pi / 2)
    hsv[..., 1] = 255
    hsv[..., 2] = cv2.normalize(magnitude, None, 0, 255, cv2.NORM_MINMAX)

    # 转换为BGR图像并输出
    bgr = cv2.cvtColor(hsv, cv2.COLOR_HSV2BGR)
    cv2.imshow("Optical Flow", bgr)
    if cv2.waitKey(1) & 0xFF == ord("q"):
        break

cv2.destroyAllWindows()

该示例演示了如何在画布上进行均匀平移,然后使用OpenCV的calcOpticalFlowFarneback函数计算出运动的光流。最终使用cvtColor函数将光流图像转换为BGR空间,以便将其显示出来。

示例2

在这个示例中,我们将通过直接对NGC 2237进行光流处理来演示OpenCV的光流功能。NGC 2237是Rosette星云中的一个部分,是一个美丽的星云。

import cv2
import numpy as np
from urllib import request

# 加载图像
url = "https://www.winhelponline.com/blog/wp-content/uploads/2017/12/Windows-10-default-background-3.jpg"
resp = request.urlopen(url)
image = np.asarray(bytearray(resp.read()), dtype="uint8")
image = cv2.imdecode(image, cv2.IMREAD_GRAYSCALE)

# 初始化前一帧和光流
previous_frame = None
optical_flow = None

# 不断循环,直到用户终止程序
while True:
    # 如果前一帧为空,则将当前帧设置为前一帧
    if previous_frame is None:
        previous_frame = image.copy()
    else:
        previous_frame = current_frame.copy()

    # 如果当前帧为空,则退出循环
    current_frame = image.copy()
    if current_frame is None:
        break

    # 如果光流为空,则使用Farneback计算光流
    if optical_flow is None:
        optical_flow = cv2.calcOpticalFlowFarneback(previous_frame, current_frame, None, 0.5, 3, 15, 3, 5, 1.2, 0)

    # 在当前帧上绘制运动向量
    for y in range(0, current_frame.shape[0], 5):
        for x in range(0, current_frame.shape[1], 5):
            dx, dy = optical_flow[y, x].astype(np.int0)
            cv2.arrowedLine(current_frame, (x, y), (x + dx, y + dy), (255, 255, 255))

    # 显示帧
    cv2.imshow("Rosette Nebula (NGC 2237)", current_frame)

    # 侦听键盘事件,确定是否退出
    key = cv2.waitKey(1) & 0xFF
    if key == ord("q"):
        break

cv2.destroyAllWindows()

该示例加载一个图像,然后使用calcOpticalFlowFarneback函数计算出前一帧和当前帧之间的运动光流。最终,使用光流图像在当前帧上绘制运动向量,并显示结果。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:OpenCV 光流Optical Flow示例 - Python技术站

(0)
上一篇 2023年5月25日
下一篇 2023年5月25日

相关文章

  • Linux运维常用维护命令记录

    关于“Linux运维常用维护命令记录”的完整攻略,我可以给您提供以下信息: 什么是“Linux运维常用维护命令记录”? “Linux运维常用维护命令记录”是一份维护Linux服务器常用的命令清单,它可以帮助管理员在运维过程中轻松地解决一些常见的问题,提高工作效率。这份清单包括了一些常用的维护命令,比如监控系统资源、查看进程信息、修改权限、备份数据等等。 常用…

    人工智能概览 2023年5月25日
    00
  • 浅析mmdetection在windows10系统环境中搭建过程

    下面是详细的”浅析mmdetection在windows10系统环境中搭建过程”攻略: 1. 安装Anaconda和CUDA 在Windows10系统环境中,我们首先需要安装Anaconda和CUDA。可以按照以下步骤进行: 下载并安装Anaconda,下载地址:https://www.anaconda.com/products/individual#win…

    人工智能概览 2023年5月25日
    00
  • express+mongoose实现对mongodb增删改查操作详解

    下面是“express+mongoose实现对mongodb增删改查操作详解”的完整攻略。 1. 概述 Mongodb是一个高性能、开源、面向文档的NoSQL数据库。Express.js是一个基于Node.js平台的Web应用开发框架,可用于快速创建Web应用程序。Mongoose是一个使用Node.js与MongoDB交互的对象模型工具,它提供了一系列的强…

    人工智能概论 2023年5月25日
    00
  • spring boot项目中MongoDB的使用方法

    下面就为大家详细讲解Spring Boot项目中MongoDB的使用方法的完整攻略。 1. MongoDB的介绍 MongoDB是一款基于文档模型的NoSQL数据库,它既支持动态模式(BSON),也支持静态模式(JSON),还支持原子操作。MongoDB是一个开源、分布式、高性能的、面向文档的数据库。它旨在提供高性能、高可用性和易扩展性,并通过数据的自动分片…

    人工智能概论 2023年5月25日
    00
  • python3 使用OpenCV计算滑块拼图验证码缺口位置(场景示例)

    简要介绍OpenCV OpenCV是一款功能强大的开源计算机视觉库,它可以处理图像和视频数据,支持多种编程语言,在数字图像处理、计算机视觉和机器学习等领域都有广泛应用。 准备工作 使用Python3,需要先安装OpenCV和Requests库。 pip install opencv-python pip install requests 获取验证码图片和缺口…

    人工智能概览 2023年5月25日
    00
  • 在Windows服务器下用Apache和mod_wsgi配置Python应用的教程

    下面是在Windows服务器下用Apache和mod_wsgi配置Python应用的完整攻略。 前提条件 在开始配置之前,需要确保满足以下几个前提条件: 已经安装了 Python 和 Apache,并且能够在本地运行 Python 和 Apache。 已经安装了 mod_wsgi。如果没有安装,可以从 mod_wsgi官网 下载安装。 配置过程 步骤一:创建…

    人工智能概论 2023年5月25日
    00
  • django使用graphql的实例

    下面我将对“django使用graphql的实例”的完整攻略进行详细讲解。 什么是GraphQL GraphQL是一种用于API的查询语言,与REST等传统的API相比,它有以下优点: 可以精确地请求所需的数据,避免了传统API请求大量不需要的数据 支持多个查询和变更操作的批量请求 可以通过类型系统和查询架构自动文档化查询 Django中使用GraphQL的…

    人工智能概论 2023年5月25日
    00
  • Python办公自动化SFTP详解

    Python办公自动化SFTP详解 在实际的工作场景中,经常需要将本地计算机的文件上传或下载到远程的服务器,这时sftp协议就变得非常实用了。Python语言提供了一种ubd-ftp库来操作sftp协议,Python办公自动化中的sftp常用于上传、下载、删除远程服务器上的文件。 连接SFTP服务器 首先,需要使用以下语句导入相关的库: import par…

    人工智能概论 2023年5月25日
    00
合作推广
合作推广
分享本页
返回顶部