开发

固定注视点渲染 (FFR)(已停用)

更新时间: 2024年10月18日
Mobile SDK Deprecation
自 2022 年 8 月 31 日起,我们不再支持移动 SDK 和 VrApi 资源库。未来的更新将通过 OpenXR 扩展程序和我们的 OpenXR 移动 SDK,而非移动 Meta 或 PC API 的任何新更新提供。
停止支持移动 SDK 后,意味着:
  • 新应用将无法访问 Meta 原生移动 API,但现有应用可继续使用此类 API。
  • 对于使用 Meta 原生 API 创建新应用的,将不提供任何帮助。您可以在开发者指南中找到将现有应用迁移到 OpenXR 的建议。
  • 只有 Meta 原生 API 中的关键安全性、隐私或安全问题才会得到解决。
  • Meta 原生移动应用的任何测试都将仅限于自动化 QA 测试,以确保核心功能正常运作。
如需了解有关该停用的更多信息,请访问 Meta 全面投入 OpenXR:停用专用 API
本指南说明如何在原生 VRAPI 应用程序中实现固定注视点渲染 (FFR)。要了解 FFR 的运作方式和调试方法,请前往此处

如何实现动态注视点

动态注视点调整是使用 FFR 的推荐方法。可使用以下方法启用动态 FFR:
vrapi_SetPropertyInt( &Java, VRAPI_DYNAMIC_FOVEATION_ENABLED, true );
默认情况下,动态注视点是禁用的。启用动态注视点时,系统会自动调整注视点级别,将最高级别设置为 VRAPI_FOVEATION_LEVEL。要进行此设置,请调用以下方法:
vrapi_SetPropertyInt( &Java, VRAPI_FOVEATION_LEVEL, level );
调用时,level 可以是 0、1、2、3 或 4。在动态注视点下,注视点 3 级(高)和 4 级(最高)被视为同一级别。选择这两个级别中的哪一个级别与 VRAPI_FOVEATION_LEVEL 选择一致。例如,如果 VRAPI_FOVEATION_LEVEL 被设置为 4 级,动态注视点将仅在 0、1、2 与 4 之间变化。
因为动态注视点使用 GPU 利用率来增加或减少注视点级别,所以它是相当波动的,并且在创建过时帧之前,级别应该比固定 FFR 级别有所增加,但是,如果在特定级别上没有发现增加的过时帧,则可以在那些区域中启用和禁用动态 FFR。强烈建议使用动态 FFR。
如果拥有动态 FFR 应用的开发者想直观地显示他们的应用看起来是怎样的,看看他们的 FFR 级别是否太高,他们可以使用以下 setprop 命令:
setprop debug.oculus.foveation.dynamic 0
此命令将立即禁用动态 FFR,并且注视点级别将立即变成 VRAPI_FOVEATION_LEVEL,无需重新编译应用的非动态 FFR 版本。

如何实现非动态固定注视点渲染

首先,如果您想检查设备是否支持注视点渲染。请检查系统属性 VRAPI_SYS_PROP_FOVEATION_AVAILABLE,如果支持注视点渲染,它将返回 VRAPI_TRUE
然后,要使用 FFR,请调用以下方法来设置注视点级别:
vrapi_SetPropertyInt( &Java, VRAPI_FOVEATION_LEVEL, level );
调用时,level 可以是 0、1、2、3 或 4。

启用子采样布局

为了提高注视点渲染的视觉质量,我们建议应用启用子采样布局。这将能实现低分辨率区域中的双线性向上采样,从而获得更平滑的图像,并消除周边视觉中的任何像素化伪影(请参阅下面的图像示例)。请查看 GLVulkan 规格来获取关于子采样布局的更多信息。
Side-by-side comparison of foveated rendering with subsampled layout on versus off.
要启用子采样布局,只需在创建颜色纹理交换链时包含 VRAPI_SWAPCHAIN_CREATE_SUBSAMPLED_BIT 创建标记:
ovrSwapChainCreateInfo swapChainCreateInfo = {
    .Format = colorFormat,
    .Width = width,
    .Height = height,
    .Levels = 1,
    .FaceCount = 1,
    .ArraySize = 2,
    .BufferCount = 3,
    .CreateFlags = VRAPI_SWAPCHAIN_CREATE_SUBSAMPLED_BIT, // make sure the swapchain is created with subsampled bit!
    .UsageFlags = VRAPI_SWAPCHAIN_USAGE_COLOR_ATTACHMENT_BIT,
};
colorTextureSwapChain = vrapi_CreateTextureSwapChain4(&swapChainCreateInfo);