mirror of
https://github.com/DrBeef/ioq3quest.git
synced 2025-04-17 22:00:58 +00:00
OpenXR integration fixes
This commit is contained in:
parent
c321b97894
commit
65e2031e95
6 changed files with 128 additions and 51 deletions
|
@ -18,7 +18,9 @@ const char* const requiredExtensionNames[] = {
|
||||||
XR_KHR_COMPOSITION_LAYER_CYLINDER_EXTENSION_NAME,
|
XR_KHR_COMPOSITION_LAYER_CYLINDER_EXTENSION_NAME,
|
||||||
XR_FB_DISPLAY_REFRESH_RATE_EXTENSION_NAME,
|
XR_FB_DISPLAY_REFRESH_RATE_EXTENSION_NAME,
|
||||||
XR_FB_SWAPCHAIN_UPDATE_STATE_EXTENSION_NAME,
|
XR_FB_SWAPCHAIN_UPDATE_STATE_EXTENSION_NAME,
|
||||||
XR_FB_SWAPCHAIN_UPDATE_STATE_OPENGL_ES_EXTENSION_NAME};
|
XR_FB_SWAPCHAIN_UPDATE_STATE_OPENGL_ES_EXTENSION_NAME,
|
||||||
|
XR_FB_FOVEATION_EXTENSION_NAME,
|
||||||
|
XR_FB_FOVEATION_CONFIGURATION_EXTENSION_NAME};
|
||||||
const uint32_t numRequiredExtensions =
|
const uint32_t numRequiredExtensions =
|
||||||
sizeof(requiredExtensionNames) / sizeof(requiredExtensionNames[0]);
|
sizeof(requiredExtensionNames) / sizeof(requiredExtensionNames[0]);
|
||||||
|
|
||||||
|
|
|
@ -1103,8 +1103,8 @@ static void IN_VRJoystick( qboolean isRightController, float joystickX, float jo
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
//Positional movement speed correction for when we are not hitting target framerate
|
//Positional movement speed correction for when we are not hitting target framerate
|
||||||
//TODO:int refresh = vrapi_GetSystemPropertyInt(&(VR_GetEngine()->java), VRAPI_SYS_PROP_DISPLAY_REFRESH_RATE);
|
float refresh;
|
||||||
int refresh = 72;
|
VR_GetEngine()->appState.pfnGetDisplayRefreshRate(VR_GetEngine()->appState.Session, &refresh);
|
||||||
float multiplier = (float)((1000.0 / refresh) / (in_vrEventTime - lastframetime));
|
float multiplier = (float)((1000.0 / refresh) / (in_vrEventTime - lastframetime));
|
||||||
|
|
||||||
float factor = (refresh / 72.0F) * 10.0f; // adjust positional factor based on refresh rate
|
float factor = (refresh / 72.0F) * 10.0f; // adjust positional factor based on refresh rate
|
||||||
|
|
|
@ -270,6 +270,14 @@ void VR_InitRenderer( engine_t* engine ) {
|
||||||
&engine->appState.Renderer,
|
&engine->appState.Renderer,
|
||||||
engine->appState.ViewConfigurationView[0].recommendedImageRectWidth,
|
engine->appState.ViewConfigurationView[0].recommendedImageRectWidth,
|
||||||
engine->appState.ViewConfigurationView[0].recommendedImageRectHeight);
|
engine->appState.ViewConfigurationView[0].recommendedImageRectHeight);
|
||||||
|
|
||||||
|
ovrRenderer_SetFoveation(
|
||||||
|
&engine->appState.Instance,
|
||||||
|
&engine->appState.Session,
|
||||||
|
&engine->appState.Renderer,
|
||||||
|
XR_FOVEATION_LEVEL_HIGH_FB,
|
||||||
|
0,
|
||||||
|
XR_FOVEATION_DYNAMIC_DISABLED_FB);
|
||||||
}
|
}
|
||||||
|
|
||||||
void VR_DestroyRenderer( engine_t* engine )
|
void VR_DestroyRenderer( engine_t* engine )
|
||||||
|
@ -284,6 +292,29 @@ void VR_ReInitRenderer()
|
||||||
VR_InitRenderer( VR_GetEngine() );
|
VR_InitRenderer( VR_GetEngine() );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void VR_ClearFrameBuffer( int width, int height)
|
||||||
|
{
|
||||||
|
glEnable( GL_SCISSOR_TEST );
|
||||||
|
glViewport( 0, 0, width, height );
|
||||||
|
|
||||||
|
if (Cvar_VariableIntegerValue("vr_thirdPersonSpectator"))
|
||||||
|
{
|
||||||
|
//Blood red.. ish
|
||||||
|
glClearColor( 0.12f, 0.0f, 0.05f, 1.0f );
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
//Black
|
||||||
|
glClearColor( 0.0f, 0.0f, 0.0f, 1.0f );
|
||||||
|
}
|
||||||
|
|
||||||
|
glScissor( 0, 0, width, height );
|
||||||
|
glClear( GL_COLOR_BUFFER_BIT );
|
||||||
|
|
||||||
|
glScissor( 0, 0, 0, 0 );
|
||||||
|
glDisable( GL_SCISSOR_TEST );
|
||||||
|
}
|
||||||
|
|
||||||
void VR_DrawFrame( engine_t* engine ) {
|
void VR_DrawFrame( engine_t* engine ) {
|
||||||
if (vr.weapon_zoomed) {
|
if (vr.weapon_zoomed) {
|
||||||
vr.weapon_zoomLevel += 0.05;
|
vr.weapon_zoomLevel += 0.05;
|
||||||
|
@ -375,39 +406,39 @@ void VR_DrawFrame( engine_t* engine ) {
|
||||||
vr.fov_y = (fabs(fov.angleUp) + fabs(fov.angleDown)) * 180.0f / M_PI;
|
vr.fov_y = (fabs(fov.angleUp) + fabs(fov.angleDown)) * 180.0f / M_PI;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set-up the compositor layers for this frame.
|
|
||||||
// NOTE: Multiple independent layers are allowed, but they need to be added
|
|
||||||
// in a depth consistent order.
|
|
||||||
|
|
||||||
XrCompositionLayerProjectionView projection_layer_elements[2] = {};
|
|
||||||
|
|
||||||
engine->appState.LayerCount = 0;
|
engine->appState.LayerCount = 0;
|
||||||
memset(engine->appState.Layers, 0, sizeof(ovrCompositorLayer_Union) * ovrMaxLayerCount);
|
memset(engine->appState.Layers, 0, sizeof(ovrCompositorLayer_Union) * ovrMaxLayerCount);
|
||||||
|
|
||||||
if (Cvar_VariableIntegerValue("vr_thirdPersonSpectator"))
|
|
||||||
{
|
|
||||||
//Blood red.. ish
|
|
||||||
glClearColor( 0.12f, 0.0f, 0.05f, 1.0f );
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
//Black
|
|
||||||
glClearColor( 0.0f, 0.0f, 0.0f, 1.0f );
|
|
||||||
}
|
|
||||||
glClear( GL_COLOR_BUFFER_BIT );
|
|
||||||
|
|
||||||
ovrFramebuffer* frameBuffer = &engine->appState.Renderer.FrameBuffer;
|
ovrFramebuffer* frameBuffer = &engine->appState.Renderer.FrameBuffer;
|
||||||
|
int swapchainIndex = engine->appState.Renderer.FrameBuffer.TextureSwapChainIndex;
|
||||||
|
int glFramebuffer = engine->appState.Renderer.FrameBuffer.FrameBuffers[swapchainIndex];
|
||||||
|
re.SetVRHeadsetParms(projectionMatrix.M, monoVRMatrix.M, glFramebuffer);
|
||||||
|
|
||||||
ovrFramebuffer_Acquire(frameBuffer);
|
ovrFramebuffer_Acquire(frameBuffer);
|
||||||
ovrFramebuffer_SetCurrent(frameBuffer);
|
ovrFramebuffer_SetCurrent(frameBuffer);
|
||||||
re.SetVRHeadsetParms(projectionMatrix.M, monoVRMatrix.M,
|
VR_ClearFrameBuffer(frameBuffer->ColorSwapChain.Width, frameBuffer->ColorSwapChain.Height);
|
||||||
engine->appState.Renderer.FrameBuffer.FrameBuffers[engine->appState.Renderer.FrameBuffer.TextureSwapChainIndex]);
|
|
||||||
Com_Frame();
|
Com_Frame();
|
||||||
ovrFramebuffer_Resolve(frameBuffer);
|
|
||||||
ovrFramebuffer_Release(frameBuffer);
|
|
||||||
ovrFramebuffer_SetNone();
|
|
||||||
|
|
||||||
if (!VR_useScreenLayer() && !(cl.snap.ps.pm_flags & PMF_FOLLOW && vr.follow_mode == VRFM_FIRSTPERSON)) {
|
if (!VR_useScreenLayer() && !(cl.snap.ps.pm_flags & PMF_FOLLOW && vr.follow_mode == VRFM_FIRSTPERSON)) {
|
||||||
|
|
||||||
|
XrCompositionLayerProjectionView projection_layer_elements[2] = {};
|
||||||
|
for (int eye = 0; eye < ovrMaxNumEyes; eye++) {
|
||||||
|
ovrFramebuffer* frameBuffer = &engine->appState.Renderer.FrameBuffer;
|
||||||
|
|
||||||
|
memset(&projection_layer_elements[eye], 0, sizeof(XrCompositionLayerProjectionView));
|
||||||
|
projection_layer_elements[eye].type = XR_TYPE_COMPOSITION_LAYER_PROJECTION_VIEW;
|
||||||
|
projection_layer_elements[eye].pose = XrPosef_Inverse(viewTransform[eye]);
|
||||||
|
projection_layer_elements[eye].fov = projections[eye].fov;
|
||||||
|
|
||||||
|
memset(&projection_layer_elements[eye].subImage, 0, sizeof(XrSwapchainSubImage));
|
||||||
|
projection_layer_elements[eye].subImage.swapchain = frameBuffer->ColorSwapChain.Handle;
|
||||||
|
projection_layer_elements[eye].subImage.imageRect.offset.x = 0;
|
||||||
|
projection_layer_elements[eye].subImage.imageRect.offset.y = 0;
|
||||||
|
projection_layer_elements[eye].subImage.imageRect.extent.width = frameBuffer->ColorSwapChain.Width;
|
||||||
|
projection_layer_elements[eye].subImage.imageRect.extent.height = frameBuffer->ColorSwapChain.Height;
|
||||||
|
projection_layer_elements[eye].subImage.imageArrayIndex = eye;
|
||||||
|
}
|
||||||
|
|
||||||
XrCompositionLayerProjection projection_layer = {};
|
XrCompositionLayerProjection projection_layer = {};
|
||||||
projection_layer.type = XR_TYPE_COMPOSITION_LAYER_PROJECTION;
|
projection_layer.type = XR_TYPE_COMPOSITION_LAYER_PROJECTION;
|
||||||
projection_layer.layerFlags = XR_COMPOSITION_LAYER_BLEND_TEXTURE_SOURCE_ALPHA_BIT;
|
projection_layer.layerFlags = XR_COMPOSITION_LAYER_BLEND_TEXTURE_SOURCE_ALPHA_BIT;
|
||||||
|
@ -416,28 +447,6 @@ void VR_DrawFrame( engine_t* engine ) {
|
||||||
projection_layer.viewCount = ovrMaxNumEyes;
|
projection_layer.viewCount = ovrMaxNumEyes;
|
||||||
projection_layer.views = projection_layer_elements;
|
projection_layer.views = projection_layer_elements;
|
||||||
|
|
||||||
for (int eye = 0; eye < ovrMaxNumEyes; eye++) {
|
|
||||||
ovrFramebuffer* frameBuffer = &engine->appState.Renderer.FrameBuffer;
|
|
||||||
|
|
||||||
memset(
|
|
||||||
&projection_layer_elements[eye], 0, sizeof(XrCompositionLayerProjectionView));
|
|
||||||
projection_layer_elements[eye].type = XR_TYPE_COMPOSITION_LAYER_PROJECTION_VIEW;
|
|
||||||
|
|
||||||
projection_layer_elements[eye].pose = XrPosef_Inverse(viewTransform[eye]);
|
|
||||||
projection_layer_elements[eye].fov = projections[eye].fov;
|
|
||||||
|
|
||||||
memset(&projection_layer_elements[eye].subImage, 0, sizeof(XrSwapchainSubImage));
|
|
||||||
projection_layer_elements[eye].subImage.swapchain =
|
|
||||||
frameBuffer->ColorSwapChain.Handle;
|
|
||||||
projection_layer_elements[eye].subImage.imageRect.offset.x = 0;
|
|
||||||
projection_layer_elements[eye].subImage.imageRect.offset.y = 0;
|
|
||||||
projection_layer_elements[eye].subImage.imageRect.extent.width =
|
|
||||||
frameBuffer->ColorSwapChain.Width;
|
|
||||||
projection_layer_elements[eye].subImage.imageRect.extent.height =
|
|
||||||
frameBuffer->ColorSwapChain.Height;
|
|
||||||
projection_layer_elements[eye].subImage.imageArrayIndex = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
engine->appState.Layers[engine->appState.LayerCount++].Projection = projection_layer;
|
engine->appState.Layers[engine->appState.LayerCount++].Projection = projection_layer;
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
|
@ -481,4 +490,7 @@ void VR_DrawFrame( engine_t* engine ) {
|
||||||
endFrameInfo.layers = layers;
|
endFrameInfo.layers = layers;
|
||||||
|
|
||||||
OXR(xrEndFrame(engine->appState.Session, &endFrameInfo));
|
OXR(xrEndFrame(engine->appState.Session, &endFrameInfo));
|
||||||
|
ovrFramebuffer_Resolve(frameBuffer);
|
||||||
|
ovrFramebuffer_Release(frameBuffer);
|
||||||
|
ovrFramebuffer_SetNone();
|
||||||
}
|
}
|
||||||
|
|
|
@ -73,6 +73,12 @@ bool ovrFramebuffer_Create(
|
||||||
swapChainCreateInfo.arraySize = 2;
|
swapChainCreateInfo.arraySize = 2;
|
||||||
swapChainCreateInfo.mipCount = 1;
|
swapChainCreateInfo.mipCount = 1;
|
||||||
|
|
||||||
|
// Enable Foveation on this swapchain
|
||||||
|
XrSwapchainCreateInfoFoveationFB swapChainFoveationCreateInfo;
|
||||||
|
memset(&swapChainFoveationCreateInfo, 0, sizeof(swapChainFoveationCreateInfo));
|
||||||
|
swapChainFoveationCreateInfo.type = XR_TYPE_SWAPCHAIN_CREATE_INFO_FOVEATION_FB;
|
||||||
|
swapChainCreateInfo.next = &swapChainFoveationCreateInfo;
|
||||||
|
|
||||||
frameBuffer->ColorSwapChain.Width = swapChainCreateInfo.width;
|
frameBuffer->ColorSwapChain.Width = swapChainCreateInfo.width;
|
||||||
frameBuffer->ColorSwapChain.Height = swapChainCreateInfo.height;
|
frameBuffer->ColorSwapChain.Height = swapChainCreateInfo.height;
|
||||||
|
|
||||||
|
@ -220,6 +226,57 @@ void ovrRenderer_Destroy(ovrRenderer* renderer) {
|
||||||
ovrFramebuffer_Destroy(&renderer->FrameBuffer);
|
ovrFramebuffer_Destroy(&renderer->FrameBuffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ovrRenderer_SetFoveation(
|
||||||
|
XrInstance* instance,
|
||||||
|
XrSession* session,
|
||||||
|
ovrRenderer* renderer,
|
||||||
|
XrFoveationLevelFB level,
|
||||||
|
float verticalOffset,
|
||||||
|
XrFoveationDynamicFB dynamic) {
|
||||||
|
PFN_xrCreateFoveationProfileFB pfnCreateFoveationProfileFB;
|
||||||
|
OXR(xrGetInstanceProcAddr(
|
||||||
|
*instance,
|
||||||
|
"xrCreateFoveationProfileFB",
|
||||||
|
(PFN_xrVoidFunction*)(&pfnCreateFoveationProfileFB)));
|
||||||
|
|
||||||
|
PFN_xrDestroyFoveationProfileFB pfnDestroyFoveationProfileFB;
|
||||||
|
OXR(xrGetInstanceProcAddr(
|
||||||
|
*instance,
|
||||||
|
"xrDestroyFoveationProfileFB",
|
||||||
|
(PFN_xrVoidFunction*)(&pfnDestroyFoveationProfileFB)));
|
||||||
|
|
||||||
|
PFN_xrUpdateSwapchainFB pfnUpdateSwapchainFB;
|
||||||
|
OXR(xrGetInstanceProcAddr(
|
||||||
|
*instance, "xrUpdateSwapchainFB", (PFN_xrVoidFunction*)(&pfnUpdateSwapchainFB)));
|
||||||
|
|
||||||
|
XrFoveationLevelProfileCreateInfoFB levelProfileCreateInfo;
|
||||||
|
memset(&levelProfileCreateInfo, 0, sizeof(levelProfileCreateInfo));
|
||||||
|
levelProfileCreateInfo.type = XR_TYPE_FOVEATION_LEVEL_PROFILE_CREATE_INFO_FB;
|
||||||
|
levelProfileCreateInfo.level = level;
|
||||||
|
levelProfileCreateInfo.verticalOffset = verticalOffset;
|
||||||
|
levelProfileCreateInfo.dynamic = dynamic;
|
||||||
|
|
||||||
|
XrFoveationProfileCreateInfoFB profileCreateInfo;
|
||||||
|
memset(&profileCreateInfo, 0, sizeof(profileCreateInfo));
|
||||||
|
profileCreateInfo.type = XR_TYPE_FOVEATION_PROFILE_CREATE_INFO_FB;
|
||||||
|
profileCreateInfo.next = &levelProfileCreateInfo;
|
||||||
|
|
||||||
|
XrFoveationProfileFB foveationProfile;
|
||||||
|
|
||||||
|
pfnCreateFoveationProfileFB(*session, &profileCreateInfo, &foveationProfile);
|
||||||
|
|
||||||
|
XrSwapchainStateFoveationFB foveationUpdateState;
|
||||||
|
memset(&foveationUpdateState, 0, sizeof(foveationUpdateState));
|
||||||
|
foveationUpdateState.type = XR_TYPE_SWAPCHAIN_STATE_FOVEATION_FB;
|
||||||
|
foveationUpdateState.profile = foveationProfile;
|
||||||
|
|
||||||
|
pfnUpdateSwapchainFB(
|
||||||
|
renderer->FrameBuffer.ColorSwapChain.Handle,
|
||||||
|
(XrSwapchainStateBaseHeaderFB*)(&foveationUpdateState));
|
||||||
|
|
||||||
|
pfnDestroyFoveationProfileFB(foveationProfile);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
================================================================================
|
================================================================================
|
||||||
|
|
||||||
|
|
|
@ -10,7 +10,6 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
//OpenXR
|
//OpenXR
|
||||||
#define XR_EYES_COUNT 2
|
|
||||||
#define XR_USE_GRAPHICS_API_OPENGL_ES 1
|
#define XR_USE_GRAPHICS_API_OPENGL_ES 1
|
||||||
#define XR_USE_PLATFORM_ANDROID 1
|
#define XR_USE_PLATFORM_ANDROID 1
|
||||||
#include <EGL/egl.h>
|
#include <EGL/egl.h>
|
||||||
|
@ -33,7 +32,7 @@ typedef union {
|
||||||
XrCompositionLayerCylinderKHR Cylinder;
|
XrCompositionLayerCylinderKHR Cylinder;
|
||||||
} ovrCompositorLayer_Union;
|
} ovrCompositorLayer_Union;
|
||||||
|
|
||||||
enum { ovrMaxLayerCount = 16 };
|
enum { ovrMaxLayerCount = 1 };
|
||||||
enum { ovrMaxNumEyes = 2 };
|
enum { ovrMaxNumEyes = 2 };
|
||||||
|
|
||||||
#define GL(func) func;
|
#define GL(func) func;
|
||||||
|
@ -174,6 +173,13 @@ void ovrRenderer_Create(
|
||||||
int suggestedEyeTextureWidth,
|
int suggestedEyeTextureWidth,
|
||||||
int suggestedEyeTextureHeight);
|
int suggestedEyeTextureHeight);
|
||||||
void ovrRenderer_Destroy(ovrRenderer* renderer);
|
void ovrRenderer_Destroy(ovrRenderer* renderer);
|
||||||
|
void ovrRenderer_SetFoveation(
|
||||||
|
XrInstance* instance,
|
||||||
|
XrSession* session,
|
||||||
|
ovrRenderer* renderer,
|
||||||
|
XrFoveationLevelFB level,
|
||||||
|
float verticalOffset,
|
||||||
|
XrFoveationDynamicFB dynamic);
|
||||||
|
|
||||||
void ovrTrackedController_Clear(ovrTrackedController* controller);
|
void ovrTrackedController_Clear(ovrTrackedController* controller);
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue