单个场景最多支持 15 层 VR 合成层(超过 15 层将不予显示)。同时,每个场景中最多只能存在一个 Equirect 层和一个 Cylinder 层。考虑到对性能的影响,建议你将单个场景的 VR 合成层数量控制在 4 层左右。
VR 合成层(VR Compositor Layers)可以用来展示场景中的焦点对象,例如信息、文本、视频以及纹理,也可以用来展示简单的场景环境和背景。
通常来说,渲染 VR 内容时,左右眼摄像机首先将场景内容渲染到 Eye Buffer 上;绘制完成后,异步时间扭曲线程(Asynchronous Timewarp,ATW)对 Eye Buffer 进行畸变、采样、合成等处理;处理完毕后,场景内容最终被渲染到屏幕上。
若通过 VR 合成层技术进行场景渲染,则无需将场景内容绘制到 Eye Buffer 上,而是直接透传给 ATW 线程进行畸变、采样、合成等处理。因此,减少了一次额外的纹理采样,简化了整个渲染流程,同时可提升渲染质量。
注意事项
- 目前,单个场景最多支持添加 7 个 VR 合成层,建议不超过 4 个。
- 应该遵循近处物体遮挡远处物体的规则来使用合成层,否则可能会出现轻微晃动。
- 若你在项目中使用了 Vulkan 和通用渲染管线(URP),同时需使用 Underlay 层时,则需要禁用 HDR,否则 Underlay 层无法生效。
PXR_Over Lay 脚本参数说明
PXR_Over Lay 脚本用于配置合成层相关参数。
Type (合成层类型)
SDK 提供两种类型的合成层:Overlay 和 Underlay。
|----------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 类型 | 说明 |
| Overlay | Overlay 类型的合成层将纹理呈现在 Eye Buffer 前面,默认为该选项。使用该类型的合成层时,需注意以下事项: * 勾选 Texture Rects 选框后,若选择自定义 Source Rects 和 Destination Rects(即选择 Custom 选项),则需确保 X、Y、W、H 的值位于以下指定区间内: * X:[0,1) * Y:[0,1) * W:(0,1] * H:(0,1] * 使用 Overlay 类型的合成层,并且将 Shape 设置为 Equirect(球体纹理)时,需注意以下事项: * Radius 参数用于指定圆柱的半径,当设置为 0 或者正无限大(1.0f/0.0f)时,表示无限大的半径。球面半径无限大时,其展示效果如同空场景中的天空盒。 * Destination Rects 下的 X 参数无用;W 参数映射到中心角,关于中心点坐标 (0, 0) 对称。 |
| Underlay | Underlay 类型的合成层将纹理呈现在 Eye Buffer 后面。 由于 Underlay 层依赖于渲染目标上的 alpha 通道。场景中的所有对象绘制到 Eye Buffer 后,你需要在 Eye Buffer 上构建一个 "洞",使 Underlay 纹理透过这个 "洞" 显示出来。你可以在 Packages/PICO Integration/Assets/Resources/Shader 目录下获取 PXR_UnderlayHole 脚本,然后使用该脚本来构建"洞",或根据应用需求编写 shader 来构建 "洞"。 提示:URP 不支持使用 Underlay 类型的合成层。 |
Shape (合成层形状)
SDK 提供五种形状的合成层:Quad、Cylinder、Equirect、Cubemap 和 Equi-Angular Cubemap (EAC)。具体说明如下:
|----------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 形状 | 说明 |
| Quad | 具有四个顶点的平面纹理,通常用来显示场景中的文本或信息。默认为该选项。 |
| Cylinder | 具有柱面弧度的圆柱形纹理,通常用于显示曲面 UI 界面。 若使用 Cylinder,则: * Transform 中心将作为 Cylinder 的中心,Transform 的尺寸将作为 Cylinder 的尺寸,且 Cylinder 中 Transform 的尺寸均为全局尺寸(Global Scale)。其中,Z 作为 Cylinder 的半径,Y 作为 Cylinder 的高,X/Z 作为 Cylinder 的弧长。 * 必须将摄像机放置在圆柱内切球内。如果摄像机接近内切球表面,合成层将无法显示。 |
| Equirect | 球体纹理,通常用于显示 360/180 全景纹理。 |
| Cubemap | 立方体贴图。一个立方形贴图为六个正方形纹理的集合,用来表示环境反射。这六个立方体构成了围绕某物体的假想立方体的面,每个面都代表了对应世界轴方向(上、下、左、右、前、后)的视图。立方体贴图常用来捕捉物体的反射或周围环境。 |
| Equi-Angular Cubemap (EAC) | 等角立方体贴图是一种用于展示 360 度全景图片和视频的投影技术,是等距投影和立方体投影的结合体,支持 180 度投影。 在 EAC 投影中,360 度全景图首先被分成六个立方体面,然后将来自每个立方体面的像素映射到一个球体上,从而创建一个可以从任何角度浏览的无缝全景图像。 |
| Blurred Quad | 模糊平面纹理,用于渲染空间图片或空间视频。 |
Depth (合成层深度)
合成层深度(Depth)用于定义合成层在场景中的顺序。数值越小,越靠近 Eye Buffer。假设一个场景中添加了三层 Overlay 和三层 Underlay,深度值设定可以为[Camera](Overlay)2/1/0[EyeBuffer]0/1/2(Underlay)。
Texture Type (纹理类型)
SDK 提供三种纹理类型:外部纹理(External Surface)、动态纹理(Dynamic Texture)和静态纹理(Static Texture)。每个纹理都有最佳使用场景。
|--------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 类型 | 说明 |
| 外部纹理 | 相应的合成层将从外部 Android Surface 直接获取纹理(例如:Android 播放器视频纹理)。该选项将创建一个 Android Surface 并将 Android Surface Texture 直接渲染到 VR 合成层上。创建的对象为 public IntPtr externalAndroidSurfaceObject = IntPtr.Zero;,可在 PXR_OverLay.cs 文件中查看。 若想提升 VR 视频的清晰度,建议使用 External Surface。 |
| 动态纹理 | 若要将动态内容渲染至该合成层,即为合成层每帧更新纹理,则需要使用动态纹理。例如:若想使用普通摄像机生成的 RenderTexture 图片,则需使用动态纹理。 |
| 静态纹理 | 若需要渲染静态内容,例如:在画廊中显示一幅画,则需使用静态纹理。 |
Texture (纹理)
Texture 参数用于指定左右眼透传的纹理。
Radius (半径)
将 Shape (合成层形状) 设置为 Equirect(球体纹理)时,需要配置 Radius 参数,指定圆柱的半径。
Texture Rects (纹理矩形)
勾选 Texture Rects 选框后,可配置 Source Rects 和 Destination Rects 相关参数。
Source Rects (源矩形)
Source Rects 参数用于设置被渲染到物体表面的纹理区域。选项说明如下:
|---------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 选项 | 说明 |
| Mono Scopic | 为左右眼摄像机选择不同的纹理,分别显示。 |
| Stereo Scopic | 纹理左右中分,左眼摄像机显示左半部分,右眼摄像机显示右半部分。 提示:建议左右眼指定同一张纹理且纹理宽高需保持一致,否则可能会因为左右眼纹理差别过大而导致异样感。 |
| Custom | 自定义渲染到物体表面的纹理区域,其中: * X 和 Y 用于设置纹理上的起始点 * W 用于设置纹理区域的宽度 * H 用于设置纹理区域的高度 举个例子,如果你将 X 和 Y 都设置为 0.5 ,然后将 W 和 H 都设置为 0.5,那么起始点为纹理的中心,纹理右上角 1/4 的区域将渲染至物体表面。 |
Destination Rects (目标矩形)
Destination Rects 参数用于设置合成层所覆盖的目标区域。选项说明如下:
|---------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 选项 | 说明 |
| Default | 保持目标区域的原始尺寸。 |
| Custom | 自定义合成层所覆盖的目标区域,其中: * X 和 Y 用于设置目标区域的起始点 * W 用于设置目标区域的宽度 * H 用于设置目标区域的高度 举个例子,如果在 Source Rects 参数处,你将 X 和 Y 都设置为 0.5 ,并且将 W 和 H 都设置为 0.5 ,在此处,你将 X 和 Y 都设置成 0.5 ,并且将 W 和 H 都设置成 1,那么物体表面右上方 1/4 区域将被纹理右上方 1/4 区域所覆盖。 |
Layer Blend (图层混合)
Layer Blend 用于设置 Source 层和 Destination 层的颜色值和透明度值。
图层混合可将源图层颜色和目标图层颜色进行混合,常用来绘制透明或半透明的物体。合成层默认从后往前进行混合,若当前场景有合成层 1、2、3、4,则图层混合顺序为:
- 合成层 4 和 3 优先被混合,作为 Destination 层 1。此时,合成层 2 将作为 Source 层。
- Destination 层 1 与合成层 2 进行混合,作为 Destination 层 2。此时,合成层 1 将作为 Source 层。
- Destination 层 2 与合成层 1 进行混合。
相关参数说明如下:
|-----------|--------------|
| 参数 | 说明 |
| Src Color | 设置的颜色值。 |
| Dst Color | 设置背景图层的颜色值。 |
| Src Alpha | 设置合成层的透明度值。 |
| Dst Alpha | 设置背景图层的透明度值。 |
Override Color Scale (覆盖全局颜色设置)
若想覆盖该层的全局颜色设置,可勾选 Override Color Scale,然后配置以下参数:
|--------|-------------|
| 参数 | 说明 |
| Scale | 设置颜色值的缩放倍数。 |
| Offset | 设置颜色值的偏移量。 |
通用使用步骤
此部分以 Overlay 类型的 Quad 层为例,介绍如何配置基本的合成层参数,并实现 World-Locked 和 Head-Locked 两种模式。
- World-Locked 模式
通常情况下,合成层为 World-Locked 模式。无论头戴位置如何移动,合成层都不会随着头戴移动,而是保持其在世界中的固定位置。
- Head-Locked 模式
在 Head-Locked 模式中,合成层会随着头戴的移动而移动。若想达到此效果,需将合成层作为摄像机的的子节点。
配置 World-Locked 模式
第一步,为场景添加 XR Origin 并为其挂载 PXR_Manager 脚本,然后将 XR Origin 下的摄像机设置为主摄像机。步骤如下:
- 在 Unity 编辑器中打开项目。
- 在 Hierarchy 窗口中,点击 + > XR > XR Origin (VR) 。
XR Origin 将被添加至场景中。XR Origin 下的 Main Camera 将默认成为场景内容捕捉摄像机。若未升级 XR Interaction Toolkit 至最新版本,则 XR Origin 的名称为 XR Rig。XR Interaction Toolkit 升级步骤可参考《快速开始》指南*。*
3.选中 XR Origin 节点下的 Main Camera。
4.在 Inspector 窗口中,将 Main Camera 的 Tag 设置为 MainCamera。一般已默认为该设置。
5.删除场景自带的 Main Camera。
6.选中 XR Origin。
Inspector 窗口展示 XR Origin 挂载的组件和脚本。
7.点击 Inspector 窗口底部的 Add Component 按钮。
8.搜索 PXR_Manager 脚本,然后双击添加。
第二步,为场景添加一个 3D 对象并为其挂载 PXR_Over Lay 脚本,该脚本用来配置合成层参数。步骤如下:
- 在上方菜单栏处,选择 GameObject > 3D Object。
- 创建一个 3D 对象,例如:Cube。
- 调整 3D 对象的位置,使其处于摄像机可见位置。
- 在 Hierarchy 窗口中,选中该 3D 对象。
Inspector 窗口中将展示该 3D 对象挂载的配置脚本和组件。
5.点击 Inspector 窗口底部的 Add Component 按钮。
6.搜索 PXR_Over Lay 脚本,然后双击添加。脚本界面如下:
第三步,配置合成层基础参数。步骤如下:
- 将 Type 设置为 Overlay。
- 将 Shape 设置为 Quad。
- 将 Depth 设置为 0。
最后,选择纹理类型并按需配置参数。步骤:
- 将 Texture Type 设置为 Dynamic Texture 或 Static Texture。
PXR_Over Lay 脚本界面转换如下:
2.在 Texture 参数处,选择左右眼透传的纹理。
至此,合成层基础配置完成。你可以在设备上运行该场景,将体验到"效果展示"中的效果。此外,可根据实际需求,进行以下配置:
3.(可选) 勾选 Texture Rects,然后配置 Source Rects 和 Destination Rects 相关参数。
4.(可选) 勾选 Layer Blend,然后设置 Source 层和 Destination 层的颜色值和透明度值。
5.(可选) 若想覆盖该层的全局颜色设置,可勾选 Override Color Scale,然后配置相关参数。
配置 Head-Locked 模式
- 添加 XR Origin 并为其挂载 PXR_Manager 脚本,然后将 XR Origin 下的摄像机设置为主摄像机。
- 在 Hierarchy 窗口中,展开 XR Origin (或 XR Rig)> Camera Offset。
- 右击 Main Camera ,然后选择 3D Object,为摄像机节点创建一个子 3D 对象(例如:Cube)。
4.将 Cube 移动至摄像机可见位置。
5.选中 Cube。
6.在 Inspector 窗口中,点击底部的 Add Component 按钮,为 Cube 添加 PXR_Over Lay 脚本。
7.参考 World-Locked 模式,配置相关参数。
Equirect 层使用说明
Equirect 层为球体纹理,通常用于显示 180/360 全景图像和视频。配置步骤如下:
- 参考 使用 Quad 层,为场景添加 XR Origin 和 3D 对象,并分别为它们添加 PXR_Manager 和 PXR_Over Lay 脚本。
- 在 PXR_Over Lay 面板处,进行以下参数配置:
- 选择 Type。
- 将 Shape 设置为 Equirect。
- 按需设置 Depth。
- 按需选择 Texture Type。
- 将 Texture 指定为 360 全景纹理。
- 按需配置 Texture Rects ,Layer Blend ,和 Override Color Scale 参数。参数说明参考 使用 Quad 层。
- 将场景打包安装至设备上运行。效果如下:
EAC 层使用说明
等角立方体贴图(Equi-Angular Cubemap,EAC)是一种用于展示 180 度或 360 度全景图片和视频的投影技术,是等距投影和立方体投影的结合体。
SDK 提供四种 EAC 模式,将 Overlay Settings 部分的 Shape 参数设置为 Eac 后,可以在 Model Type 参数处进一步选择 EAC 模式。
EAC 各模式的说明如下:
|-------------------|---------------------------|----------------------------------------------------------------------------------------------------------------------------------------------|
| 模式 | 说明 | 6 个面的排列方式 |
| EAC 360 | 水平 360°×垂直 360° 全景视频。 | 360° EAC 层的 6 个面的排列方式如下图所示。 |
| EAC 360 View Port | 在 EAC 360 的基础上,支持视口偏移的功能。 | 360° EAC 层的 6 个面的排列方式如下图所示。 |
| EAC 180 | 水平 180°×垂直 180° 视频。 | 180° EAC 层的 5 个面的排列方式如下图所示:其中 Left、Right、Bottom、Top 四个面只展示靠近前方的一半。 |
| EAC 180 View Port | 在 EAC 180 的基础上,支持视口偏移的功能。 | 180° EAC 层的 5 个面的排列方式如下图所示:其中 Left、Right、Bottom、Top 四个面只展示靠近前方的一半。 |
EAC 层相关参数说明如下:
|------------------|-----------------------------------------------------------------------|------------------------------------------------|
| 参数 | 说明 | 备注 |
| Offset Pos Left | 表示左眼的纹理映射时的视口平移。 | 仅适用于 Eac 180 View Port 和 Eac 360 View Port 模式。 |
| Offset Pos Right | 表示右眼的纹理映射时的视口平移。 | 仅适用于 Eac 180 View Port 和 Eac 360 View Port 模式。 |
| Offset Rot Left | 表示左眼的纹理映射时的视口旋转。 | 仅适用于 Eac 180 View Port 和 Eac 360 View Port 模式。 |
| Offset Rot Right | 表示右眼的纹理映射时的视口旋转。 | 仅适用于 Eac 180 View Port 和 Eac 360 View Port 模式。 |
| Overlap Factor | 重叠系数,表示每一个面扩展的比例。在合成器的采样公式为:Texcoord = arctan(position/overlapFactor) | - |
Blurred Quad 层使用说明
Blurred Quad 层用于渲染空间图片或空间视频。
若想使用 Blurred Quad 层,需要在 PXR_Over Lay (Script) 组件中将 Shape 参数设置为 Blurred Quad,将 Texture Type 设置为 External Surface(目前仅支持此类型),然后配置相关参数。
Blurred Quad 层相关参数说明如下。
|----------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 参数名称 | 说明 |
| Mode | 用于设置空间图片或空间视频在场景内的展示模式: * Small Window:小窗模式,在场景内打开一个窗口,展示图片或视频。纹理位于窗口后面 0.5 米处。 * * Immersion:沉浸模式,与 "小窗模式" 相比,窗口更大,不再遮挡纹理,并增加毛玻璃向外羽化透出的效果。纹理位于窗口后面 0.5 米处。 |
| Scale | 用于降低视差,判断主体是否过近、视差是否过大。如果视差过大,则在播放时降低图像的全图 Scale,并且对左右眼图像做水平方向的全图偏移(Shift),降低视差以改善合像困难。取值范围为 [0.0, +∞],需根据窗口大小调整。Small Window 模式建议设置为 0.5,Immersion 模式建议设置为 1.0。 |
| Shift | 用于对左右眼图像做水平方向的全图偏移,降低视差以改善合像困难。左右眼的偏移方向相反,设置的 Shift 值默认用于左眼,右眼会使用相反的 Shift 值(即 -Shift)。取值范围为 [-1, 1],默认值为 0.01。 |
| FOV | 用户拍摄的图片或视频的纵向视场角,取值范围为 [0, 180],默认值为 70。如果图片或视频本身携带 FOV 值或者已知实际的 FOV 值,则使用该 FOV 值,否则推荐设置为 61.05。 提示:此参数设置的为纵向角度,而非弧度。运行时会根据纹理此处的设置以及纹理的宽高来计算纵向 FOV。 |
| IPD | 拍摄图像或视频时所用的相机的瞳孔间距。取值范围为 [0.05, 0.07],默认值为 0.064。 |
除了在 Unity 编辑器内的 PXR_Over Lay (Script) 组件中设置参数外,你也可以直接修改 PXR_OverLay.cs 文件中的值(如下所示),设置后会每帧生效。
cs
#region Blurred Quad
public BlurredQuadMode blurredQuadMode = BlurredQuadMode.SmallWindow;
public float blurredQuadScale = 0.5f;
public float blurredQuadShift = 0.01f;
public float blurredQuadFOV = 70.0f;
public float blurredQuadIPD = 0.064f;
#endregion
播放 HDR 视频
External Surface 类型的纹理支持播放 HDR 视频。播放视频时,根据视频类型动态设置 HDR 类型(HDRFlags)。HDRFlags 枚举值如下:
cs
public HDRFlags hdr = HDRFlags.None;
public enum HDRFlags
{
None, // 关闭 HDR 视频透传
HdrPQ, // PQ 兼容显示模式,支持将符合 ST.2084 标准的 HDR 源重映射成 SDR,以得到正确的显示效果
HdrHLG, // HLG 兼容显示模式,支持将符合 HLG 标准的 HDR 源重映射成 SDR,以得到正确的显示效果
}
外部纹理补充说明
若使用外部纹理,可按需配置以下参数:
参数说明如下:
|-----------------|------------------------------------------------------------------------------------------------------------------------------------------|
| 参数 | 说明 |
| DRM | 若需要对外部纹理进行版权保护,可勾选 DRM 。勾选后,用户截屏/录屏时,External Surface 部分将显示为黑色。 |
| 3D Surface Type | 纹理显示类型: * Single:完整图像同时在左右眼摄像机上显示。 * Left Right:图像左右中分,左眼摄像机显示左半部分,右眼摄像机显示右半部分。 * Top Bottom:图像上下中分,左眼摄像机显示上半部分,右眼摄像机显示下半部分。 |
已知问题
Unity 2023 中,若在多视图渲染(Multiview Rendering)模式下使用 Overlay 合成层,会导致 Overlay 合成层不显示或显示异常。待后续引擎更新解决。