20. WebAR那些事: 一个40行的ARDemo

简介: #紧接上文 WebVR+Three.js可以快速高效的搭建VR场景,降低了初学者的准入门槛,节省多平台重复开发,开始了H5在VR的新时代。 #本次Demo所需二维码 用户可以本地启动HTTP服务,将URL填写到播放路径 本次demo已经集成到APK中,用户可以点击《AR地球》来体验 ![1480510893.png](http://ata2-img.cn-hangzhou.img-p

紧接上文

WebVR+Three.js可以快速高效的搭建VR场景,降低了初学者的准入门槛,节省多平台重复开发,开始了H5在VR的新时代。

本次Demo所需二维码

用户可以本地启动HTTP服务,将URL填写到播放路径
本次demo已经集成到APK中,用户可以点击《AR地球》来体验
1480510893.png

AR地球

环境准备

  1. Demo使用r82版本,向下兼容
  2. Three.js 到http://www.threejs.org下载最新源码,这里使用three.min.js作为渲染引擎。
  3. WebVR.js WebVR的工具库,用于切换VR状态(three.js的源码包中,自己拷贝)
  4. VREffect.js WebVR的展示库,用于分屏展示(three.js的源码包中,自己拷贝)
  5. VRControls.js WebVR的控制库,用于监控陀螺仪、Camera、重力等(three.js的源码包中,自己拷贝)

纹理准备

可以使用其他3D模型,为了方便起见,我们使用老的模型

  1. 地球纹理,在网上可以找到最新的地图纹理,最好使用4k,比较清晰
    earth_map_jpeg

兼容性准备

常见的浏览器对摄像头的支持,良莠不齐,这里只是简单的支持了一种API标准

捕获音视频接口: Navigator.getUserMedia

点击进入: Mozilla官方使用文档
使用方法:

var params = { video: true, video: { width: 1280, height: 720 } };
window.navigator.getUserMedia(params, function(stream) {
    var video = document.querySelector('video');
    video.src = window.URL.createObjectURL(stream);
    video.onloadedmetadata = function(e) {
        video.play();
    };
});

兼容性分析

Navigator.getUserMedia接口目前Safari是不支持的,常见的浏览器使用摄像头,往往通过Flash插件来完成。所以这些代码不一定能够成功运行在用户的浏览器上,但没有关系,我们的的WebVRSDK已经提供了支持,开发者可以放心的使用。
Navigator.getUserMedia已经废弃了,使用MediaDevices.getUserMedia来取代。因为我对Promise原理不是很清楚,所以暂时只支持Navigator.getUserMedia。
开发者需要提前申请App的Camera权限,Android6.0以后支持动态权限管理,开发者需要确保App拥有Camera的使用权限,最直接的的办法是在设置中手动的打开权限,否则背景会出现黑屏。

准备空白的html

我们会将所有JS代码写在单独的index.js中,因此index.html只是提供JS运行的环境,这一步为代码迁移到WebVRSDK做准备。代码如下:

<!doctype html>
<html>
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>WebGL Earth</title>
    <style>
        body { margin: 0; overflow: hidden; background-color: #000; }
    </style>
</head>
<body>
    <script src="three.js"></script>
    <script src="WebVR.js"></script>
    <script src="VREffect.js"></script>
    <script src="VRControls.js"></script>
    <script src="index.js"></script> 
</body>
</html>

index.js核心代码

  1. 代码行数控制在40行以内
  2. 渲染器,使用WebGL渲染three.js中的3D对象
  3. 加载器,使用XMLHttpRequest或者Image,异步加载图片纹理
  4. 摄像机,模拟观察者的位置和方向,从不同角度来观看3D世界
  5. 控制器,接受用户点击、触摸、鼠标等事件,控制摄像机的参数,实现人机交互
  6. 材料,任何3D对象,是由骨骼和图像组成,材料就像油漆,粉刷过的对象更加真实
  7. 几何,3D对象的结构描述,这里只用球状几何
  8. 场景,用来管理所有需要展示的3D对象,以及他们之间的层级和关系
  9. video标签,用于承载摄像头内容的呈现

代码如下

var w = window.innerWidth;
var h = window.innerHeight;
var renderer = new THREE.WebGLRenderer();        // 创建渲染器
renderer.setSize(w, h);                            // 设置渲染器为全屏
document.body.appendChild(renderer.domElement);    // 将渲染器添加到body上

var camera    = new THREE.PerspectiveCamera(45, w / h, 0.01, 100);
var effect    = new THREE.VREffect(renderer);        // 控制器,用来控制VR渲染
var loader    = new THREE.TextureLoader();        // 加载器,用于异步加载图片
var control    = new THREE.VRControls(camera);        // 控制器,用来控制摄像机

var mater = { map : new THREE.TextureLoader().load('earth_map.jpg') };
var earth = new THREE.Mesh(new THREE.SphereGeometry(20, 32, 32), new THREE.MeshBasicMaterial(mater));
earth.position.x = -100;

var scene  = new THREE.Scene();                    // 创建场景
scene.add(earth);                                // 添加地球
scene.add(new THREE.AmbientLight(0xFFFFFF));    // 创建环境光

window.navigator.getUserMedia({ audio : true, video: { width: w, height: h }}, function(stream) {
    var video = document.createElement('video');
    video.src = stream;
    video.play();

    var image = new THREE.VideoTexture(video);
    image.generateMipmaps = false;
    image.format    = THREE.RGBAFormat;
    image.maxFilter = THREE.NearestFilter;
    image.minFilter = THREE.NearestFilter;
    scene.background = image;                    // 背景视频纹理
}, null);

animate();
function animate() {
    effect.requestAnimationFrame(animate);
    control.update();
    earth.rotation.y += 0.002;
    effect.render(scene, camera);
}

用浏览器打开index.html

在Safari上是无法打开的,因为navigator没有成员函数:getUserMedia
开发者可以添加判断,因为WebVRSDK我添加了支持,所以就不判断了,代码如下:

navigator.getUserMedia = navigator.getUserMedia        ||
                         navigator.mozGetUserMedia    ||
                         navigator.webkitGetUserMedia;

if (navigator.getUserMedia) {
    ....
}

效果展示

悬浮的3D地球
a1f0a50aacd8308bcccbf7f5f99aa22e.jpg

畅想

AR距离我们很近

AR翻译过来是增强现实,简单一点说,就是在摄像头捕获的视频或者图片中,加入3D效果,并融入背景。就像二次元或者三次元一样,给用户带来更多的欢乐。

如果我们把3D地球换成一只可爱的猫咪,是不是就是淘宝双十一的抓猫猫游戏了?

下一回

我们把地球换成一个复杂的3D模型,并想办法让TA动起来,就像淘宝双十一的AR抓猫猫一样,会动会跳,还会发红包。

目录
相关文章
|
开发工具 对象存储 Python
使用Python的SDK从OSS中下载指定日期的所有文件
使用Python的SDK从OSS中下载指定日期的所有文件
340 1
|
5月前
|
前端开发 算法 API
Multi-Agent实践第4期:智能体的“想”与“做”-ReAct Agent
本期文章,我们将向大家展示如何使用AgentScope内置的ReAct智能体解决更为复杂的问题。
|
5月前
|
缓存
npm install 一直卡着不动如何解决
npm install 一直卡着不动如何解决
1761 0
ly~
|
1月前
|
开发框架 小程序 前端开发
抖音小程序的开发难度大吗?
抖音小程序的开发难度因人而异,主要取决于开发者经验、技能及功能需求。技术上需掌握前端技术及抖音开发框架,了解平台生态与规则;设计上需符合用户审美和习惯,具备创新性和实用性。此外,严格的审核标准和激烈的市场竞争增加了开发难度,开发者需制定有效推广策略并持续优化小程序以保持竞争力。
ly~
79 4
|
前端开发
Threejs - 加载视频纹理渲染 实现一个3D视频播放器
Threejs - 加载视频纹理渲染 实现一个3D视频播放器
2095 0
Threejs - 加载视频纹理渲染 实现一个3D视频播放器
|
分布式计算 数据处理 MaxCompute
MaxCompute单字段拆分多行多列
数据导入MaxCompute后,需要把某个字段String类型(多键值(key-value )对 ) 拆分成多行,每行有都有key, value两列。比如“{k1:v1,k2:v2,k3:k4}” 拆成多行,每行两个值key,value 分别为k1,v1;k2,v2;k3;k4。
3884 0
|
11月前
|
Linux iOS开发 Docker
|
5月前
|
开发框架 前端开发 JavaScript
【Uniapp 专栏】Uniapp 中的动画效果实现与特性
【5月更文挑战第13天】Uniapp是一款跨平台开发框架,提供丰富的动画效果以提升用户体验和应用吸引力。基于CSS和JavaScript动画,支持转场、元素等多种动画类型,确保跨平台一致性并优化性能。通过CSS属性或JavaScript库实现动画,结合页面布局和手势操作,创造沉浸式交互。通过调试和优化,开发者可打造惊艳效果,适应未来技术发展,提升应用竞争力。
602 1
【Uniapp 专栏】Uniapp 中的动画效果实现与特性
|
传感器 前端开发 安全
前端前沿技术之webAR
随着用户体验的升级和技术的进步,浏览器中涌现了越来越多的技术。前端也从十年前网页中的纯HTML和CSS技术开始涵盖到服务端、移动端的领域。
2639 0
前端前沿技术之webAR
|
定位技术 API C#
【EasyAR学习】平面追踪、表面跟踪和运动跟踪、稀疏空间地图
Easy平面追踪、表面跟踪和运动跟踪、稀疏空间地图解析与实战
771 0