利用python实现AR教程


Posted in Python onNovember 20, 2019

先了解如何利用python语言实现以平面和标记物进行姿态估计

本实验只是先实现一个简单的小例子。简单来说就是先识别出图像中的参考面,再拍摄一张目标图像,将参考面顶部的3D模型投影到目标图像上。

大致步骤如下:

识别参考平面

在这一步中,我们所需要做的事就是提取参考图像和目标图像的sift特征,然后使用RANSAC算法稳健地估计单应性矩阵。

代码如下:

#计算特征
sift.process_image('D:输入图片/book_frontal.JPG', 'im0.sift')
l0, d0 = sift.read_features_from_file('im0.sift')

sift.process_image('D:输入图片/book_per.JPG', 'im1.sift')
l1, d1 = sift.read_features_from_file('im1.sift')

#匹配特征,并计算单应性矩阵
matches = sift.match_twosided(d0, d1)
ndx = matches.nonzero()[0]
fp = homography.make_homog(l0[ndx, :2].T)
ndx2 = [int(matches[i]) for i in ndx]
tp = homography.make_homog(l1[ndx2, :2].T)

model = homography.RansacModel()
H, inliers = homography.H_from_ransac(fp, tp, model)

由上面代码可得到单应性矩阵,它能够将一幅图像中标记物的点映射到另一幅图像中的对应点。还需要建立X-Y(Z=0)三维坐标系,标记物在Z=0平面上,原点在标记物的某个位置上。

从单应性推导出从参考面坐标系到目标图像坐标系的转换

在进行坐标转换之前,为了检验单应性矩阵结果的正确性,需要将一些三维物体放置在目标图像上,本实验使用了一个立方体。产生立方体的代码如下:

def cube_points(c, wid):

  p = []
  p.append([c[0]-wid, c[1]-wid, c[2]-wid])
  p.append([c[0]-wid, c[1]+wid, c[2]-wid])
  p.append([c[0]+wid, c[1]+wid, c[2]-wid])
  p.append([c[0]+wid, c[1]-wid, c[2]-wid])
  p.append([c[0]-wid, c[1]-wid, c[2]-wid])

  p.append([c[0]-wid, c[1]-wid, c[2]+wid])
  p.append([c[0]-wid, c[1]+wid, c[2]+wid])
  p.append([c[0]+wid, c[1]+wid, c[2]+wid])
  p.append([c[0]+wid, c[1]-wid, c[2]+wid])
  p.append([c[0]-wid, c[1]-wid, c[2]+wid])

  p.append([c[0]-wid, c[1]-wid, c[2]+wid])
  p.append([c[0]-wid, c[1]+wid, c[2]+wid])
  p.append([c[0]-wid, c[1]+wid, c[2]-wid])
  p.append([c[0]+wid, c[1]+wid, c[2]-wid])
  p.append([c[0]+wid, c[1]+wid, c[2]+wid])
  p.append([c[0]+wid, c[1]-wid, c[2]+wid])
  p.append([c[0]+wid, c[1]-wid, c[2]-wid]

 return array(p).T

先计算出照相机的标定矩阵,就可以得出两个视图间的相对变换

代码如下:

#计算照相机标定矩阵,使用图像的分辨率为747*1000
K = my_calibration((747, 1000))

#位于边长为0.2,Z=0平面上的三维点
box = cube_points([0, 0, 0.1], 0.1)

#投影第一幅图像上底部的正方形
cam1 = camera.Camera(hstack((K, dot(K, array([[0], [0], [-1]])))))
#底部正方形上的点
box_cam1 = cam1.project(homography.make_homog(box[:, :5]))

#使用H将点变换到第二幅图像上
box_trans = homography.normalize(dot(H,box_cam1))

#从cam1和H中计算第二个照相机矩阵
cam2 = camera.Camera(dot(H, cam1.P))
A = dot(linalg.inv(K), cam2.P[:, :3])
A = array([A[:, 0], A[:, 1], cross(A[:, 0], A[:, 1])]).T
cam2.P[:, :3] = dot(K, A)

#使用第二个照相机矩阵投影
box_cam2 = cam2.project(homography.make_homog(box))

在图像(像素空间)中投影我们的3D模型并绘制它。

#底部正方形的二维投影
figure()
imshow(im0)
plot(box_cam1[0, :], box_cam1[1, :], linewidth=3)
title('2D projection of bottom square')
axis('off')

#使用H对二维投影进行变换
figure()
imshow(im1)
plot(box_trans[0, :], box_trans[1, :], linewidth=3)
title('2D projection transfered with H')
axis('off')

#三维立方体
figure()
imshow(im1)
plot(box_cam2[0, :], box_cam2[1, :], linewidth=3)
title('3D points projected in second image')
axis('off')

实验结果如下

利用python实现AR教程

什么是AR

AR全称Augmented Reality,意为增强现实技术。

它是一种将真实世界信息和虚拟世界信息“无缝”集成的新技术,是把原本在现实世界的一定时间空间范围内很难体验到的实体信息(视觉信息,声音,味道,触觉等),通过电脑等科学技术,模拟仿真后再叠加,将虚拟的信息应用到真实世界,被人类感官所感知,从而达到超越现实的感官体验。真实的环境和虚拟的物体实时地叠加到了同一个画面或空间同时存在。

增强现实技术,不仅展现了真实世界的信息,而且将虚拟的信息同时显示出来,两种信息相互补充、叠加。在视觉化的增强现实中,用户利用头盔显示器,把真实世界与电脑图形多重合成在一起,便可以看到真实的世界围绕着它。

增强现实技术包含了多媒体、三维建模、实时视频显示及控制、多传感器融合、实时跟踪及注册、场景融合等新技术与新手段。增强现实提供了在一般情况下,不同于人类可以感知的信息。

如何利用python实现AR

步骤和实现姿态估计无太大差别。由上述内容计算出照相机的位置和姿态,使用这些信息来放置计算机图像学模型。这里我们放置了一个红色的小茶壶。

在运行代码之前,我们需要先安装PyGame和PyOpenGL,下载链接(https://www.lfd.uci.edu/~gohlke/pythonlibs/)。

核心代码如下:

def set_projection_from_camera(K): 
#从照相机标定矩阵中获得视图

 glMatrixMode(GL_PROJECTION) 
 glLoadIdentity()
 fx = K[0,0] 
 fy = K[1,1] 
 fovy = 2*math.atan(0.5*height/fy)*180/math.pi 
 aspect = (width*fy)/(height*fx)
 near = 0.1 
 far = 100.0
 gluPerspective(fovy,aspect,near,far) 
 glViewport(0,0,width,height)

def set_modelview_from_camera(Rt): 
#从照相机姿态中获取模拟视图矩阵

 glMatrixMode(GL_MODELVIEW) 
 glLoadIdentity()
 Rx = np.array([[1,0,0],[0,0,-1],[0,1,0]])
 R = Rt[:,:3] 
 U,S,V = np.linalg.svd(R) 
 R = np.dot(U,V) 
 R[0,:] = -R[0,:]
 t = Rt[:,3]
 M = np.eye(4) 
 M[:3,:3] = np.dot(R,Rx) 
 M[:3,3] = t
 M = M.T
 m = M.flatten()
 glLoadMatrixf(m)

def draw_background(imname):
#使用四边形绘制背景图像

 bg_image = pygame.image.load(imname).convert() 
 bg_data = pygame.image.tostring(bg_image,"RGBX",1)
 glMatrixMode(GL_MODELVIEW) 
 glLoadIdentity()

 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)
 glEnable(GL_TEXTURE_2D) 
 glBindTexture(GL_TEXTURE_2D,glGenTextures(1)) 
 glTexImage2D(GL_TEXTURE_2D,0,GL_RGBA,width,height,0,GL_RGBA,GL_UNSIGNED_BYTE,bg_data) 
 glTexParameterf(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_NEAREST) 
 glTexParameterf(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_NEAREST)
 glBegin(GL_QUADS) 
 glTexCoord2f(0.0,0.0); glVertex3f(-1.0,-1.0,-1.0) 
 glTexCoord2f(1.0,0.0); glVertex3f( 1.0,-1.0,-1.0) 
 glTexCoord2f(1.0,1.0); glVertex3f( 1.0, 1.0,-1.0) 
 glTexCoord2f(0.0,1.0); glVertex3f(-1.0, 1.0,-1.0) 
 glEnd()
 glDeleteTextures(1)

def draw_teapot(size):
#在原点处绘制红色茶壶

 glEnable(GL_LIGHTING) 
 glEnable(GL_LIGHT0) 
 glEnable(GL_DEPTH_TEST) 
 glClear(GL_DEPTH_BUFFER_BIT)
 glMaterialfv(GL_FRONT,GL_AMBIENT,[0,0,0,0]) 
 glMaterialfv(GL_FRONT,GL_DIFFUSE,[0.5,0.0,0.0,0.0]) 
 glMaterialfv(GL_FRONT,GL_SPECULAR,[0.7,0.6,0.6,0.0]) 
 glMaterialf(GL_FRONT,GL_SHININESS,0.25*128.0) 
 glutSolidTeapot(size)

width,height = 1000,747
def setup():
 pygame.init() 
 pygame.display.set_mode((width,height),OPENGL | DOUBLEBUF) 
 pygame.display.set_caption("OpenGL AR demo")

实验结果如图:

利用python实现AR教程

运行代码遇到的错误及解决方案

错误如下:An error ocurred while starting the kernelfreeglut ERROR: Function called without first calling ‘glutInit'.

原因:经大神指点得知这个错误是freeglut和glut共存的缘故,它们俩定义了相同的方法,这个是动态链接库的重叠问题,我的在ana\Lib\site-packages\OpenGL\DLLS文件夹里面。

利用python实现AR教程

你需要删除freeglut.vc15.dll这个文件。我这是已经删除完的样子。

以上这篇利用python实现AR教程就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python中的yield使用方法
Feb 11 Python
在Django框架中设置语言偏好的教程
Jul 27 Python
python 打印对象的所有属性值的方法
Sep 11 Python
Python入门_条件控制(详解)
May 16 Python
python对html过滤处理的方法
Oct 21 Python
python3.x提取中文的正则表达式示例代码
Jul 23 Python
python numpy 反转 reverse示例
Dec 04 Python
pycharm激活码有效到2020年11月底
Sep 18 Python
将数据集制作成VOC数据集格式的实例
Feb 17 Python
完美解决keras 读取多个hdf5文件进行训练的问题
Jul 01 Python
Python中常用的os操作汇总
Nov 05 Python
Python 列表反转显示的四种方法
Nov 16 Python
使用python实现画AR模型时序图
Nov 20 #Python
Python笔记之工厂模式
Nov 20 #Python
Python常用模块logging——日志输出功能(示例代码)
Nov 20 #Python
将python2.7添加进64位系统的注册表方式
Nov 20 #Python
10个Python面试常问的问题(小结)
Nov 20 #Python
python使用pip安装SciPy、SymPy、matplotlib教程
Nov 20 #Python
Python笔记之facade模式
Nov 20 #Python
You might like
用PHP编写PDF文档生成器
2006/10/09 PHP
小文件php+SQLite存储方案
2010/09/04 PHP
tp5递归 无限级分类详解
2019/10/18 PHP
Javascript & DHTML 实例编程(教程)(三)初级实例篇1—上传文件控件实例
2007/06/02 Javascript
DOM 基本方法
2009/07/18 Javascript
javascript下string.format函数补充
2010/08/24 Javascript
jQuery对html元素取值与赋值的方法
2013/11/20 Javascript
利用javascript实现全部删或清空所选的操作
2014/05/27 Javascript
jQuery中nextUntil()方法用法实例
2015/01/07 Javascript
用JavaScript显示浏览器客户端信息的超相近教程
2015/06/18 Javascript
详解js中构造流程图的核心技术JsPlumb(2)
2015/12/08 Javascript
简述JavaScript提交表单的方式 (Using JavaScript Submit Form)
2016/03/18 Javascript
jquery.validate使用详解
2016/06/02 Javascript
node.js操作mysql简单实例
2017/05/25 Javascript
jQuery选择器之属性筛选选择器用法详解
2017/09/19 jQuery
微信小程序如何实现全局重新加载
2019/06/05 Javascript
微信小程序与公众号卡券/会员打通的问题
2019/07/25 Javascript
NodeJS多种创建WebSocket监听的方式(三种)
2020/06/04 NodeJs
nodeJs项目在阿里云的简单部署
2020/11/27 NodeJs
python 查找文件名包含指定字符串的方法
2018/06/05 Python
Python3 io文本及原始流I/O工具用法详解
2020/03/23 Python
Django全局启用登陆验证login_required的方法
2020/06/02 Python
Windows下PyCharm配置Anaconda环境(超详细教程)
2020/07/31 Python
详解python对象之间的交互
2020/09/29 Python
纯CSS3实现自定义Tooltip边框涂鸦风格的教程
2014/11/05 HTML / CSS
利用简洁的图片预加载组件提升html5移动页面的用户体验
2016/03/11 HTML / CSS
Champion官网:美国冠军运动服装
2017/01/25 全球购物
测试时代收集的软件测试面试题
2013/09/25 面试题
应届生如何写自荐信
2014/01/05 职场文书
上学迟到的检讨书
2014/01/11 职场文书
《王二小》教学反思
2014/02/27 职场文书
2014两会优秀的心得体会范文
2014/03/17 职场文书
物价局领导班子四风问题整改措施
2014/10/26 职场文书
2014年世界艾滋病日演讲稿
2014/11/28 职场文书
2015年招商引资工作总结
2015/04/25 职场文书
2019年手机市场的调研报告2篇
2019/10/10 职场文书