前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >使用 OpenCV 的基于标记的增强现实

使用 OpenCV 的基于标记的增强现实

作者头像
小白学视觉
发布于 2022-12-27 10:11:42
发布于 2022-12-27 10:11:42
1.5K00
代码可运行
举报
运行总次数:0
代码可运行

先决条件

了解什么是增强现实 (AR)、虚拟现实 (VR) 和混合现实 (MR),Marker-based AR 和 Marker-less AR 之间的区别:https://arshren.medium.com/all-you-want-to-know-about-augmented-reality-1d5a8cd08977

基于标记的增强现实

基于标记的 AR,也称为图像识别 AR,使用对象或基准标记作为参考来确定相机的位置或方向。

基于位置的 AR 通过扫描像 ArUco 标记这样的标记来工作。ArUco 标记检测触发增强体验以定位对象、文本、视频或动画以显示在设备上。

在这个例子中,我们将编写一个简单的代码,借助 ArUco 标记来增强视频流上的图像。

ArUco 标记

ArUco(Augmented Reality University of Cordoba) 由 S.Garrido-Jurado 等人于 2014 年在他们的工作“自动生成和检测遮挡下高度可靠的基准标记”(https://www.researchgate.net/publication/260251570_Automatic_generation_and_detection_of_highly_reliable_fiducial_markers_under_occlusion)中开发。

ArUco 标记是用于相机姿态估计的基准方形标记。当在视频中检测到 ArUco 标记时,你可以在检测到的标记上增加数字内容,例如图像。

尺寸为 6X6 的 ArUco 标记

ArUco 标记是一种合成方形标记,内部的二进制矩阵包含在带有唯一标识符的宽黑色边框内。在 ArUco 标记中, 黑色表示1,白色表示0。

标记大小决定了内部二进制矩阵的大小。ArUco 标记中的奇数块代表奇偶校验位,标记中的偶数方块代表数据位。

黑色边框便于在图像内快速检测,二进制矩阵允许对其进行识别。

ArUco 标记帮助相机了解角度、高度和深度,并在计算机视觉、机器人和增强现实中得到应用。

ArUco 标记由预定义的字典组成,涵盖一系列不同的字典大小和标记大小。要生成 ArUco 标记,你需要指定:

  • 字典大小:是字典中标记的数量
  • 指示位数的标记大小

上面的 ArUco 标记来自 100 个标记的字典,标记大小为 6X6 二进制矩阵。

此示例将使用计算机的默认摄像头捕捉视频,然后从 6x6x100 字典中引入 4 个 ArUco 标记。一旦检测到 ArUco 标记,就在检测到的 ArUco 标记上增加图像。

在此处阅读如何使用 OpenCV 读取、写入和显示视频:https://arshren.medium.com/read-and-write-videos-using-opencv-7f92548afcba

导入所需的库

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
import numpy as np
import cv2
import imutils

检测图像中的 ArUco 标记

要检测图像中的 ArUco 标记,

  1. 分析图像以找到作为标记候选的正方形形状。
  2. 检测到候选后,验证其内部编码以确保它们是 ArUco 标记。

在 OpenCV 中,ArUco 标记字典遵循命名约定cv2.aruco.DICT_NxN_M,其中 N 是二进制矩阵的大小,代表标记的大小,M 是字典中 ArUco 标记的数量。

要检测 ArUco 标记,请将 BGR 图像转换为灰度图像,以便于检测。getattr()用于访问 ArUco 标记中键属性的值以加载 ArUco 字典。

检测在detectMarkers()函数中执行,其中输入参数是包含 ArUco 标记的图像,ArUco 字典对象,在我们的例子中是 6x6x100 和 DetectorParameters(). detectMarkers()函数返回四个角的向量、它们的 id 以及检测到但不符合 ArUco 编码的任何矩形。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
def findArucoMarkers(img, markerSize = 6, totalMarkers=250, draw=True):
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    key = getattr(cv2.aruco, f'DICT_{markerSize}X{markerSize}_{totalMarkers}')
    
    #Load the dictionary that was used to generate the markers.
    arucoDict = cv2.aruco.Dictionary_get(key)
    
    # Initialize the detector parameters using default values
    arucoParam = cv2.aruco.DetectorParameters_create()
    
    # Detect the markers
    bboxs, ids, rejected = cv2.aruco.detectMarkers(gray, arucoDict, parameters = arucoParam)
    return bboxs, ids

通过将源图像叠加在视频顶部来应用增强现实。

开始使用计算机的默认摄像头捕捉视频,并读取要叠加在 ArUco 标记上的图像。

检测视频帧中的 ArUco 标记并找到每个 ArUco 标记的所有四个角的位置。计算视频帧和将要叠加的图像之间的单应性。

单应性是一个图像中的点到另一图像中的对应点的变换映射。

OpenCV 的findHomography()计算图像和视频帧点之间的单应性函数 h 以扭曲图像以适应视频帧。然后对扭曲的图像进行屏蔽并复制到视频帧上。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
import numpy as np
import cv2
import imutils

# function to detect ArUco Markers
def findArucoMarkers(img, markerSize = 6, totalMarkers=250, draw=True):
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    key = getattr(cv2.aruco, f'DICT_{markerSize}X{markerSize}_{totalMarkers}')
    
    
    #Load the dictionary that was used to generate the markers.
    arucoDict = cv2.aruco.Dictionary_get(key)
    
    # Initialize the detector parameters using default values
    arucoParam = cv2.aruco.DetectorParameters_create()
    
    # Detect the markers
    bboxs, ids, rejected = cv2.aruco.detectMarkers(gray, arucoDict, parameters = arucoParam)
    return bboxs, ids
    
# Superimposing the image on the aruco markers detected in the video 
imgH=480
imgW=640

video = cv2. VideoCapture(0)

ret, video_frame=video.read()
image = cv2.imread(r'nature.png')
image = cv2.resize(image, (imgH, imgW))

while(video.isOpened()):
    if ret==True:
        refPts=[]  
        #Detect the Aruco markers on the video frame
        arucofound =findArucoMarkers(video_frame, totalMarkers=100)
        h, w = video_frame.shape[:2]
        
        # if the aruco markers are detected
        if  len(arucofound[0])!=0:
                
                for Corner, id in zip(arucofound[0], arucofound[1]):
                    
                    corners = Corner.reshape((4, 2))
                    (topLeft, topRight, bottomRight, bottomLeft) = corners
                    topRight = (int(topRight[0]), int(topRight[1]))
                    bottomRight = (int(bottomRight[0]), int(bottomRight[1]))
                    bottomLeft = (int(bottomLeft[0]), int(bottomLeft[1]))
                    topLeft = (int(topLeft[0]), int(topLeft[1]))
                    # draw lines around the marker and display the marker id
                    cv2.line(video_frame, topLeft, topRight, (0, 255, 0), 2)
                    cv2.line(video_frame, topRight, bottomRight, (0, 255, 0), 2)
                    cv2.line(video_frame, bottomRight, bottomLeft, (0, 255, 0), 2)
                    cv2.line(video_frame, bottomLeft, topLeft, (0, 255, 0), 2)                    
                    cv2.putText(video_frame, str(id),(topLeft[0], topLeft[1] - 15), cv2.FONT_HERSHEY_SIMPLEX,0.5, (0, 255, 0), 2)
                    corner = np.squeeze(Corner)
                    refPts.append(corner)
                    
                    # only when all the 4 markes are detected in the image
                    if len(refPts)==4:
                        ( refPtBR, refPtTR,refPtBL, refPtTL) = refPts
                        video_pt = np.array([  refPtTL[3], refPtBL[3],refPtBR[2], refPtTR[3]])
                       
                        # grab the spatial dimensions of the  image and define the
                        # transform matrix for the image in 
                        #top-left, top-right,bottom-right, and bottom-left order
                        image_pt = np.float32([[0,0], [h,0], [h,w], [0,w]])
                        
                        # compute the homography matrix between the image and the video frame
                        matrix, _ = cv2.findHomography( image_pt, video_pt)
                        
                        #warp the  image to video frame based on the homography
                        warped  = cv2.warpPerspective(image, matrix, (video_frame.shape[1], video_frame.shape[0]))
                        
                        #Create a mask representing region to 
                        #copy from the warped image into the video frame.
                        mask = np.zeros((imgH, imgW), dtype="uint8")
                        cv2.fillConvexPoly(mask, video_pt.astype("int32"), (255, 255, 255),cv2.LINE_AA)
                                                                    
                        # give the source image a black border
                        # surrounding it when applied to the source image,
                        #you can apply a dilation operation
                        rect = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))
                        mask = cv2.dilate(mask, rect, iterations=2)
                        
                        # Copy the mask with the three channel version by stacking it depth-wise,
                        # This will allow copying the warped source image into the input image
                        maskScaled = mask.copy() / 255.0
                        maskScaled = np.dstack([maskScaled] * 3)
                        
                        # Copy the masked warped image into the video frame by
                        # (1) multiplying the warped image and masked together, 
                        # (2) multiplying the Video frame with the mask 
                        # (3) adding the resulting images
                        warpedMultiplied = cv2.multiply(warped.astype("float"), maskScaled)
                        imageMultiplied = cv2.multiply(video_frame.astype(float), 1.0 - maskScaled)
                        #imgout = video frame multipled with mask 
                        #        + warped image multipled with mask
                        output = cv2.add(warpedMultiplied, imageMultiplied)
                        output = output.astype("uint8")
                        cv2.imshow("output", output)
    
    ret, video_frame=video.read()
    key = cv2.waitKey(20)
    # if key q is pressed then break 
    if key == 113:
        break 
    
#finally destroy/close all open windows
video.release()
cv2.destroyAllWindows()

最终输出会将图像映射到视频中检测到的 ArUco 标记的顶部。

使用 ArUco 标记的增强现实

此处提供代码:https://github.com/arshren/AR_Aruco

参考:

https://docs.opencv.org/4.x/d5/dae/tutorial_aruco_detection.html

https://machinelearningknowledge.ai/augmented-reality-using-aruco-marker-detection-with-python-opencv/

https://learnopencv.com/augmented-reality-using-aruco-markers-in-opencv-c-python/

☆ END ☆

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2022-12-25,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 小白学视觉 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
【实战】使用ArUco标记实现增强现实
在本文中,我们将介绍ArUco标记以及如何使用OpenCV将其用于简单的增强现实任务,具体形式如下图的视频所示。
小白学视觉
2020/04/21
2.1K0
【实战】使用ArUco标记实现增强现实
ArUco与OpenCV
        ArUco标记可以用于增强现实、相机姿势估计和相机校准等应用场景,具体如无人机的自主降落地标、机器人定位。标记中白色部分为唯一标识的二进制编码。
小锋学长生活大爆炸
2022/05/09
1.2K0
ArUco与OpenCV
Python OpenCV3 计算机视觉秘籍:1~5
计算机视觉算法消耗并产生数据-它们通常将图像作为输入并生成输入的特征,例如轮廓,感兴趣的点或区域,对象的边界框或其他图像。 因此,处理图形信息的输入和输出是任何计算机视觉算法的重要组成部分。 这不仅意味着要读取和保存图像,还要显示有关其功能的其他信息。
ApacheCN_飞龙
2023/04/27
2K0
七轴开源协作机械臂myArm视觉跟踪技术!
ArUco标记是一种基于二维码的标记,可以被用于高效的场景识别和位置跟踪。这些标记的简单性和高效性使其成为机器视觉领域的理想选择,特别是在需要实时和高精度跟踪的场景中。结合机器学习和先进的图像处理技术,使用ArUco标记的机械臂系统可以实现更高级的自动化功能,如精确定位、导航和复杂动作的执行。
大象机器人
2023/12/18
4830
七轴开源协作机械臂myArm视觉跟踪技术!
OpenCV中检测ChArUco的角点(2)
ArUCo标记板是非常有用的,因为他们的快速检测和多功能性。然而,ArUco标记的一个问题是,即使在应用亚像素细化后,其角点位置的精度也不太高。相反,棋盘图案的角点可以更精确地细化,因为每个角点被两个黑色正方形包围。然而,寻找棋盘图案并不像寻找aruco棋盘那样通用:它必须是完全可见的,并且不允许遮挡。
点云PCL博主
2022/02/10
3K0
OpenCV中检测ChArUco的角点(2)
增强现实,让课堂从“纸上谈兵”变成“亲身体验”
在传统教育模式中,学生主要通过书本、PPT、老师讲解来学习知识。然而,这种方式有个明显的局限:很多概念太抽象,尤其是科学实验、医学解剖、历史场景等,学生只能靠想象。而增强现实(AR)的出现,就像给教育装上了一双“透视眼”,让学习从单纯的理论灌输,变成沉浸式体验,让知识真正“看得见,摸得着”。
Echo_Wish
2025/05/13
650
增强现实,让课堂从“纸上谈兵”变成“亲身体验”
精通 Python OpenCV4:第二部分
在本书的第二部分中,您将更深入地了解 OpenCV 库。 更具体地说,您将看到计算机视觉项目中所需的大多数常见图像处理技术。 此外,您还将看到如何创建和理解直方图,直方图是用于更好地理解图像内容的强大工具。 此外,您将在计算机视觉应用中看到所需的主要阈值处理技术,这是图像分割的关键部分。 此外,您还将看到如何处理轮廓,轮廓用于形状分析以及对象检测和识别。 最后,您将学习如何构建第一个增强现实应用。
ApacheCN_飞龙
2023/04/27
2.3K0
OpenCV-简易答题卡识别
参考自:https://www.pyimagesearch.com/2016/10/03/bubble-sheet-multiple-choice-scanner-and-test-grader-using-omr-python-and-opencv/
xxpcb
2020/08/04
1.4K0
ArUco的生成与检测
ArUco是一个开源的小型的AR虚拟现实增强库,已经集成在OpenCV3.0以上的版本,它除了用于现实增强,还很用于实现一些机器视觉方面的应用。
点云PCL博主
2022/02/10
3.3K0
ArUco的生成与检测
【Java版本OpenCV】无敌OpenCV越学越爽Java版代码持续更新(环境搭建|核心代码)
以上章节采免安装方式,所以安装章节可以直接跳过,节约点时间用springboot整合OpenCV(也可以用maven项目或者简单的java项目),主要是引入一个jar包和库文件,jar跨平台,库文件不跨平台,所以要区分windows和linux,至于工具idea就ok. 环境安装可以参考:springboot免安装整合Opencv兼容windows和linux
九转成圣
2024/04/10
2.2K0
【Java版本OpenCV】无敌OpenCV越学越爽Java版代码持续更新(环境搭建|核心代码)
【OpenCV】Chapter9.边缘检测与图像分割
边缘检测的原理和matlab实现在我之前这两篇博文中提到过,这里不再赘述。 【计算机视觉】基础图像知识点整理【计算机视觉】数字图像处理基础知识题 此次来看OpenCV的实现方式。
zstar
2022/09/28
1.5K0
【OpenCV】Chapter9.边缘检测与图像分割
OpenCV 图像处理学习手册:1~5
本章旨在与 OpenCV,其安装和第一个基本程序进行首次接触。 我们将涵盖以下主题:
ApacheCN_飞龙
2023/04/27
3K0
OpenCV 图像处理学习手册:1~5
基于OpenCV的实时车道检测
自动驾驶汽车是人工智能领域最具颠覆性的创新之一。它们借助深度学习算法不断推动社会发展,并在移动领域创造新的机遇。自动驾驶汽车可以去任何传统汽车可以去的地方,也能像经验丰富的人类驾驶员一样完成各种操作。但是,正确的训练是非常重要的。在自动驾驶汽车的训练过程中,车道检测是其中的一个重要步骤,也是最初要完成的步骤。今天,我们将学习如何使用视频进行车道检测。
一点人工一点智能
2023/08/21
9980
基于OpenCV的实时车道检测
24K纯干货:OpenCV入门教程
OpenCV是计算机视觉中最受欢迎的库,最初由intel使用C和C ++进行开发的,现在也可以在python中使用。该库是一个跨平台的开源库,是免费使用的。OpenCV库是一个高度优化的库,主要关注实时应用程序。
AI算法与图像处理
2021/04/21
3.3K0
24K纯干货:OpenCV入门教程
实战 | 基于YOLOv8和OpenCV实现目标检测、跟踪与计数(步骤+源码)
目标检测:识别并定位图像或视频中的物体,用边界框指定它们的位置。YOLO(You Only Look Once)是一种流行的单阶段物体检测算法,以其速度和准确性而闻名。与两阶段检测器不同,YOLO 一次性处理整个图像,使实时检测成为可能。这种方法通过提供高效可靠的物体检测功能,彻底改变了自动驾驶、监控和机器人等应用。
Color Space
2024/07/25
5.1K0
实战 | 基于YOLOv8和OpenCV实现目标检测、跟踪与计数(步骤+源码)
独家 | 无人驾驶项目实战: 使用OpenCV进行实时车道检测
大约十年前,我瞥见了第一辆自动驾驶汽车,当时Google仍在对初代无人车进行测试,而我立刻被这个想法吸引了。诚然,在将这些概念开源给社区之前,我必须等待一段时间,但是这些等待是值得的。
数据派THU
2020/07/09
1.8K0
独家 | 无人驾驶项目实战: 使用OpenCV进行实时车道检测
使用Pytorch和OpenCV实现视频人脸替换
“DeepFaceLab”项目已经发布了很长时间了,作为研究的目的,本文将介绍他的原理,并使用Pytorch和OpenCV创建一个简化版本。
deephub
2023/08/30
6180
使用Pytorch和OpenCV实现视频人脸替换
OpenCV 系列教程5 | OpenCV 图像处理(中)
霍夫变换是一种特征提取技术,主要应用于检测图像中的直线或者圆。 OpenCV 中分为霍夫线变换和霍夫圆变换。
机器视觉CV
2019/11/12
1.7K0
OpenCV 系列教程5 | OpenCV 图像处理(中)
Python 数据科学入门教程:OpenCV
欢迎阅读系列教程,内容涵盖 OpenCV,它是一个图像和视频处理库,包含 C ++,C,Python 和 Java 的绑定。 OpenCV 用于各种图像和视频分析,如面部识别和检测,车牌阅读,照片编辑,高级机器人视觉,光学字符识别等等。
ApacheCN_飞龙
2022/12/01
1.4K0
Python 数据科学入门教程:OpenCV
opencv︱图片与视频的读入、显示、写出、放缩与基本绘图函数介绍
opencv中读入、显示、写出图片:cv2.imread(), cv2.imshow(), cv2.imwrite()
悟乙己
2019/05/26
5.8K0
相关推荐
【实战】使用ArUco标记实现增强现实
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档