| 10 min read

终于找到机会分享了自己最近几年一直想分享的话题,这次分享也是非常浅显,重点在于科普这个东西;

本篇文章感谢 《WebXR 入门必读》 提供的一些资料,也感谢 MDN 非常棒的文档,自己结合了去年开发 Oculus PWA 的一些探索;

English Version

在分享前,我觉得我需要回顾下计算机的发展历史;

从20世纪40年代,世界诞生了第一台计算机,那个时候计算机还是一个大个子选手,界面和按键都非常粗糙;而我们只能通过各种信号灯的组合来传达具体的信息;随着技术的发展,美国各大公司进入个人计算机市场,我们熟悉的计算机模样,诞生了;我们认识到了鼠标,键盘;随着时间的推移,人们开始追求越来越轻量化,我们拥有了笔记本,用书包就能够随时随地的带着它到处办公;来了新世纪,我们拥有了触摸屏的 iPad,这是人类历史上非常伟大的发明之一;冯诺依曼模型,输入与输出完美了结合在一张显示屏上;带给了我们非常多的创新交互;

而最近十年,人类还在寻找下一代计算机通用设备;比如 Apple Meta 都花了非常多资源在 VR 设备上,所以我们也可以期待它是否可以承担起这样的角色。因为 VR 头显设备本身,具备最先进显示技术,结合它超自由度的空间交互,会给人类进行创作,娱乐,工作等带来完全新的体验;所以我也觉得 VR 依旧是值得这些大厂区不断探索的;

什么是 XR

从网上的资料来看,有人愿意用 X 表示多种内容,供大家区想象;从我们当前接触的场景来看,主要是 VR, AR 以及 XR (一种结合虚拟现实与增强现实的)方向;

XR 给我们最大的不一样便是沉浸式体验(Immersive Experience);自己把它解释成两个方向;

  • 身临其境;通过视觉和听觉的刺激,设备给我们营造一种接近真实的体验;
  • 动静结合; 我们的交互不是单纯的按键,而是会动态的结合我们所在物理空间的位置和设备的位置,所以当会根据我们的行动做出反应;

WebXR

简单而言, WebXR 就是需要我们在 XR OS 的浏览器开发 Web 应用;

WebXR API 介绍

对于任何新的 API 我们的第一件事情都是去判断它的兼容性;我们可以通过

if ("xr" in window.navigator) {
  /* WebXR can be used! */
} else {
  /* WebXR isn't available */
}

判断完之后,我们就是要做启动的事情了;其中 XRSession 是 里面非常重要的一个概念;我们可以 requestSession 来进入我们的 VR 模式;

navigator.xr.requestSession('immersive-vr').then(onSessionStarted)

XRSession 里面会有两种模式;

  • inline 可以为普通模式,也就是会按照浏览器的执行方式去展示我们的页面,比如我们正常浏览的微博,知乎都可以正常展示
  • immersive-vr 也就是我们预期的 VR 模式,我们会进入一个立体的场景,这取决于我们怎么实现;

在 XRSession 里面,我们可以实现对 WebXR API 的一些操作,比如:

  • 画面合成模式(environmentBlendMode)
  • 渲染状态(renderState)
  • 输入源列表(inputSources)
  • 渲染画面(requestAnimationFrame())
  • 更新渲染状态(updateRenderState())
  • 监听交互输入事件(比如 selectend)

XRRenderState 可以进行影响画面渲染的一些配置;

  • XRRenderState.baseLayer` 浏览器的合成系统 XRWebGLLayer 从中获取 XR 会话的图像。
  • XRRenderState.depthFar 远裁剪平面与观察者的距离 。远裁剪平面是平行于显示器的平面,超出该平面不再进行场景渲染。这实质上指定了用户可以看到的最大距离。
  • XRRenderState.depthNear 近裁剪平面与观察者的距离。近裁剪平面是平行于显示器的平面,场景渲染从该平面开始。比这更靠近观察者,并且不会绘制场景的任何部分。
  • XRRenderState.inlineVerticalFieldOfView 默认垂直视野,以弧度定义,在会话处于inline模式时使用。
  • XRRenderState.layers XRLayerc包含XR 合成器显示的对象的有序数组。

接下来也是我们需要去重点关注的; WebXR API 本身并不包含 3D 图形 API,要跟 WebGL API(或更现代的 WebGPU API)结合使用;因此如果我们要深入应用开发, WebGL 的学习肯定避免不了;

XRSpace 在 WebXR 中,一个“空间(XRSpace)”代表了虚拟空间中的一套 3D 坐标系,其原点对应了一个物理现实世界中的位置,因此“空间”可以起到把数字虚拟空间和物理现实空间关联到一起的作用; 借助它,我们可以更好处理我们交互;无论是来自手柄的以及头显本身;

这里可以出一个问题?

我们实现网页国际象棋,可以根据鼠标 click, mouseover 等事件来进行棋子的控制;如果我们想要实现立体的棋盘,摆在我们前方,我们要实现走棋,交互信息应该是怎样的?

接下来也很重要;我们如何处理交互;VR 同样拥有众多的交互来源,比如我们常见两个手柄;初次之前,头显也是我们需要跟踪的交互设备之一;如果未来手势跟踪(Hand Tracking)技术越来越精确,我们的手也会变成我们交互处理的对象;

通过上图,我们可以简单对比下我们是如何实现事件的绑定;

除了上述介绍的 API 外,下面这些大家有兴趣也可以了解下

如何开发

前面介绍了基本的 API 我们怎么开发呢;自己有一些小 tips 可以分享

  • 1 Web 项目初始化(PWA 更好);因为是个 Web 项目,所以我们可以用我们喜欢的技术脚手架或者工程,什么 Webpack/TS/Eslnt 等可以自由搭配;如果你希望把应用发布到 Quest 商店,最好使用 PWA 的一些辅助工具;我之前写过一篇关于 Oculus 和 PWA 的文章,大家可以去瞅瞅;
  • 2 WebGL 是核心,所以我们最好选择合适的 WebGL 框架(Three.js,Babylon.js,claygl …),写原生的代码真的非常繁琐;
  • 3 初始化 WebXR 并处理好 XRFrame (也可以选择 WebXR 的框架);这个是我们都需要做的,借助文档,参考 WebXR Sample 可以帮助你理解他们;
  • 4 测试与真机调试;无论如何,一定要在真机上测试;

我们平时开发,可以借助 webxr-api-emulator 来进行一些交互的处理;如果我们在真机调试的话,

我们可以借助 adb reverse 命令来进行 localhost 代理;当然别的代理网络工具都可以;因为 WebXR 的 API 也是只能在 HTTPS 或者 localhost 下工作;

开发完成之后,你当然可以发布自己的应用,别忘了打包 PWA 以及 APK 包;

一些有用的工具:

这里我也简单对比了下传统 Web 和 WebXR 开发的异同;主要是

  • WebXR 更偏图形化相关开发
  • 我们使用很多模型文件 (bx,gLTE,obj)
  • 我们处理交互会更加复杂

尽管 WebXR 开发非常难,但是由于 Web 天生的跨平台兼容性,以及无需安装,即开即用的特点,相信未来一定有自己的一片天地;

最后安利:

北京时间6月6日凌晨1点,WWDC23特别活动准时直播;

https://developer.apple.com/wwdc23/

小道消息: 不出意外的话,苹果将在WWDC 2023 开发者大会上推出新款 Mac Studio、 13 英寸 MacBook Pro 和 15 英寸 MacBook Air 机型,可能还有 24 英寸 iMac 和新款 Mac Pro,还将展示旗下首款 AR / VR 头显

让我们期待 Apple 开始步入 XR 市场吧。

扩展阅读

You Can Speak "Hi" to Me in Those Ways