Web全景图的原理及实现

全景图的基本原理

全景图是一种广角图。通过全景播放器可以让观看者身临其境地进入到全景图所记录的场景中去。比如像是这个。这种看起来很高大上的效果其实背后的原理并不复杂。

通常标准的全景图是一张2:1的图像,其背后的实质就是等距圆柱投影。等距圆柱投影是一种将球体上的各个点投影到圆柱体的侧面上的一种投影方式,投影完之后再将它展开就是一张2:1的长方形的图像。比较常见的就是应用在地图上的投影。

Web全景图的原理及实现

而在对全景图进行展示之前就需要得到一张这样的图像,这种图像可以自己用普通相机拍摄再自己合成,也可以直接使用专门的全景相机进行拍摄。全景照片的拍摄在网上有比较多的教程,由于这不是摄影分享就不详细的去说了:P。

在得到了全景图之后,就是要怎么去展示的问题了。接下来就要说说全景展示的原理。全景展示其实是等距圆柱投影的逆过程,我们要做的就是将我们得到的全景图,贴图到一个球体上,熟悉webgl的,可以用它画一个球体,然后将全景图作为材质贴到这个球体上进行渲染。由于使用webgl来进行编程的话,需要自己进行比较多的3d运算,所以也可以选择使用api更加友好的3D库,如THREE.JS来编程。比如下面的这张全景图,在球面上进行贴图。

Web全景图的原理及实现
Web全景图的原理及实现

这时我们看到的还跟预想的全景不一样,那是因为我们在球的外面,当我们在球的里面时,看到的就是跟一开始的示例一样的效果了。像是下面的这个示意图这样。

Web全景图的原理及实现

用threejs进行编程的话,关键的代码如下:

//新建一个球体var geometry = new THREE.SphereGeometry( 500, 60, 40 );//沿x轴进行-1的scale,让球体的面朝内(因为我们将从球内进行观看)。geometry.scale( - 1, 1, 1 );//载入一张全景图生成threejs中可以使用的材质var material = new THREE.MeshBasicMaterial( {    map: new THREE.TextureLoader().load( 'panoPic.jpg' )} );//将几何体和材质进行结合。mesh = new THREE.Mesh( geometry, material );

兼容性

虽然使用webgl可以很容易的就生成一个全景的场景,但是在web里,兼容性似乎是个挥之不去的话题。主要是由于webgl不支持Android5.0以下的机器,所以,用webgl来实现将会将很多用户排除在外。所以只能寻求更好的解决方案。首先想到的就是css 3D transform 和 2D canvas画布。在threejs里支持在2D的canvas里进行绘制,本是一个比较好的方案,但是经过测试之后,发现2d画布来绘制3d的场景,性能上太吃力。所以,也被排除。剩下的就是css变换了。但是,要怎么用css来画一个一个球体呢?答案显然是不行的。虽然css不能绘制一个球体,但是css通过3D变换来绘制立方体还是简单一些的。那么用立方体可不可以实现一样的效果呢?

球体到立方体

根据全景图的原理,我们是把视角放在球的中心,通过从球心观看球面上正式场景在球面上的映像从而产生一种空间中全方位的视觉体验,同理,对于立方体,应该也可以使用相同的方式来实现。而我们要做,就是把球面上的像素点映射到立方体上。

Web全景图的原理及实现

说了基本的原理,接下来就是进行数学建模了。首先我们建立一个球坐标系,坐标系描述的变量分别为半径r,竖直方向上的夹角θ,水平方向上的夹角ø,对于球体,我们可以假定

r=10 < θ < π -π/4 < ø < 7π/4

这样我们就可以得到球面上的各个点在直角坐标系中的x,y,z

x= r sin θ cos øy= r sin θ sin øz= r cos θ

对于球面到立方体上的投影,我们需要的是角度θ和ø相同时,延长球的半径r直到和立方体的面相交,假设这个长度是R,由于我们设了半径r是1所以球面上的点为 (sin θ cos ø, sin θ sin ø, cos θ) 对应的立方体上的点是(Rsin θ cos ø, Rsin θ sin ø, Rcos θ)

如果我们要求x=1这个平面上的点,则

1=Rsin θ cos ø

则可以求出来

R= 1/(sin θ cos ø)

所以在x平面上映射的点就是

(1, tan ø, cot θ / cos ø)

在立方体另外的五个平面上的投影也可以类似地得出。通过上述方法转换一张全景图,可以得到以下结果。

Web全景图的原理及实现

离我们想要的效果还有一些差距,图中似乎多了一些黑色的线。导致这种现象的原因是,由于我们的处理是以像素为单位来进行处理的,通过遍历球面图上的每个像素然后投影到立方体上的面来实现。经过这种方式进行投射之后,立方体的面上就会有一些像素被重复设置,而一些地方的像素就会缺失,比如图中的黑色部分(由于底色的黑色的)。为了解决这个问题,我们可以通过逆向的方法来解决,也就是遍历立方体上面上的每个点,求得映射到球面上的位置,然后获取球面上最接近的位置的像素。
Web全景图的原理及实现
得到了立方体上需要的图之后,就可以用css 3D变换来实现全景图了。

展示更多信息

单单地进行全景观看可能还不能满足我们的需求,也许我们还需要展示更多的信息,而这些信息可能是跟全景中的内容相关的,比如给全景中的物品打标,给全景中的内容添加评论,像是下图这样
Web全景图的原理及实现
对于这个实现的关键在于,屏幕2D坐标和空间3D坐标之间的相互转换。第一步需要实现的是记录,当用户点击屏幕,要根据点击的位置来计算出和空间中的立方体相交的点并记下这个点的位置信息。一些3d库当中会有一些api来帮助完成这项工作。而在THREEJS中使用的是Raycaster,Raycaster可以生成一条直线,然后可以很方便地得到三维空间中,和这条直线相交的物体和点。由于THREEJS中是以绘制的中心作为原点,而鼠标的点击位置是以左上角为原点,所以需要进行一下转换。

//将鼠标点击事件中的位置信息,转换到位置中心  var mouse = new THREE.Vector2(    ( ev.clientX / _this.wrapper.width() ) * 2 - 1,    -( ev.clientY / _this.wrapper.height() ) * 2 + 1  )

然后就可以初始化一个Raycaster获得需要的内容了

//创建一个Raycaster实例  var raycaster = new THREE.Raycaster()//根据点击的位置,从镜头开始初始化一和镜头的屏幕垂直的直线  raycaster.setFromCamera(mouse, _this.camera)//获得和直线相交的物体  var intersects = raycaster.intersectObjects(_this.scene.children)

这样就在空间中记录下了一个目标位置。

有了三维中的位置之后,如果我们想要展示这个位置相关信息,比如打一个标签,就是需要将空间中的位置还原到屏幕的二维坐标上,然后用传统的css方法来进行展示就可以了。

//根据上一步中记录的位置生成一个向量var vector  = new THREE.Vector3(pos.x, pos.y, pos.z)//将这个向量映射到镜头的平面上vector.project(camera)//将位置信息还原成以左上角为原点的位置信息var screenPos = {  left: Math.round((   vector.x + 1 ) * wrapper.width() / 2),  top: Math.round(( -vector.y + 1 ) * wrapper.height() / 2)

本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,请添加站长微信举报,一经查实,本站将立刻删除。

如若转载,请注明出处:https://www.ibjoo.com/298.html

(0)
上一篇 2020年5月5日 下午3:44
下一篇 2020年5月5日 下午3:46

相关推荐

  • 全景拍摄教程:为什么要使用全景云台?

      在我们日常拍摄全景图片的时候,一定都会用到一个设备:全景云台。那么有小伙伴就问了:为什么要使用全景云台?全景云台在全景拍摄中到底起到了什么作用?今天就给大家说一下!  首先,全景云台具备一个具有360度刻度的水平转轴,可以安装在三脚架上,并对安装相机的支架部分可以进行水平360度的旋转;其次,全景云台的支架部分可以对相机进行前面的移动,从而达到适应不同相…

    VR全景教程 2020年5月5日
    9500
  • 如何制作珠宝360度全景效果图?3D环物拍摄流程详解

    珠宝钻石首饰对女生拥有天然吸引力,除了璀璨好看,珠宝钻石等往往是对美好爱情的寓意象征。随着移动互联网及电子商务的普及,越来越多的高端珠宝钻石等奢侈品品牌也纷纷开拓互联网营销市场。如何把珠宝钻石完美的设计加工在线上呈现出来?360度VR全景效果图无疑是各大品牌店家首选。那么,如何制作珠宝360度全景效果图?下面为大家详解3D环物展示拍摄制作原理及流程。 什么是…

    2020年4月23日
    12600
  • 浏览器中实现3D全景浏览

    如果你用过网页版的百度地图,你大概3D全景图浏览是一种怎样的酷炫体验:在一个点可以360度环顾周围的建筑、景色,当然也可以四周移动,就像身临其境。 科普 全景图共分为三种: ①球面全景图    利用一张全景图围成一个球,自身位置位于球体内。由于图片是矩形,所以最上和最下的缝合处很明显就能够看得出来。    球面全景图是…

    VR全景教程 2020年5月5日
    10900
  • H5全景图-朋友圈全景图-720°全景-VR —- 项目简单分析

    这里我们主要看一下生成的项目中都有什么。源码中都有什么,如何去自定义 我们先只导入一张全景图,不做任何设置 然后导出项目。(为了方便,我将其项目地址和 生成的html地址都设置在一起) 我们看看都有什么 文件夹images:软件切好的图片存放目录pano2vr_player.js :Pano2VR自动生成的JavaScript脚本,是整个项目的核心test1…

    VR全景教程 2020年5月5日
    14700
  • 全景视频拼接关键技术

    全景视频拼接关键技术 一、原理介绍         图像拼接(Image Stitching)是一种利用实景图像组成全景空间的技术,它将多幅图像拼接成一幅大尺度图像或360度全景图,图像拼接技术涉及到计算机视觉、计算机图形学、数字图像处理以及一些数学工具等技术。图像拼接其基本步骤主要包括以下几个方面:摄相机的标定、传感…

    VR全景教程 2020年5月5日
    8600

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注

工具推荐
公众号
公众号
分享本页
返回顶部
特别提示:欢迎收藏&使用市场工具导航,如您有任何建议或好用工具推荐,请留言告知我们。谢谢~