### Build and Install OpenXR Samples with Gradle Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Commands to build a single sample, all samples, or install a specific sample to a connected Quest device using Gradle. ```bash # Build a single sample (e.g. XrHandsFB) from command line cd Samples ./gradlew :XrHandsFB:assembleDebug # Build all samples ./gradlew assembleDebug # Install and run on connected Quest device ./gradlew :XrHandsFB:installDebug adb shell am start -n com.oculus.sdk.handsfb/.MainActivity ``` -------------------------------- ### Build and Install XrMicrogestures Sample App Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrMicrogestures/README.md Instructions for building and installing the XrMicrogestures sample app on Android using Gradle. Ensure you have the Oculus Mobile OpenXR SDK package (v74 or later) installed. ```bash adb uninstall com.oculus.sdk.xrmicrogestures cd XrSamples/XrMicrogestures/Projects/Android ../../../../gradlew installDebug ``` -------------------------------- ### Constructor for Vt Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the Vt class with start, end, and step values, performing validation. ```javascript function Vt(n,t,r){if(Ut(),0===r)throw fu("Step must be non-zero.");if(r===vr().MIN_VALUE)throw fu("Step must be greater than Int.MIN_VALUE to avoid overflow on negation.");this.z2_1=n,this.a3_1=function(n,t,r){var i;if(r>0)i=n>=t?t:t-Ft(t,n,r)|0;else{if(!(r<0))throw fu("Step is zero.");i=n<=t?t:t+Ft(n,t,0|-r)|0}return i}(n,t,r),this.b3_1=r} ``` -------------------------------- ### Get Singleton Empty List Instance Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Returns the singleton instance of the empty list (yt). Creates it if it doesn't exist. ```javascript function pt(){return null==e&&new yt,e} ``` -------------------------------- ### Initialize and Use Virtual Keyboard Helper Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Sets up and interacts with the `XrVirtualKeyboardHelper` for displaying and inputting text via a system-rendered virtual keyboard. ```cpp // Samples/XrSamples/XrVirtualKeyboard/Src/XrVirtualKeyboardHelper.h XrVirtualKeyboardHelper keyboardHelper(GetInstance()); keyboardHelper.SessionInit(GetSession()); // Create the keyboard XrVirtualKeyboardCreateInfoMETA createInfo{XR_TYPE_VIRTUAL_KEYBOARD_CREATE_INFO_META}; keyboardHelper.CreateVirtualKeyboard(&createInfo); // Position it in the world XrVirtualKeyboardSpaceCreateInfoMETA spaceInfo{XR_TYPE_VIRTUAL_KEYBOARD_SPACE_CREATE_INFO_META}; spaceInfo.locationType = XR_VIRTUAL_KEYBOARD_LOCATION_TYPE_CUSTOM_META; spaceInfo.poseInSpace = {{0,0,0,1}, {0.0f, 1.2f, -0.5f}}; // 1.2m up, 0.5m in front keyboardHelper.CreateVirtualKeyboardSpace(&spaceInfo); keyboardHelper.ShowModel(true); // Per-frame update, retrieve location, send pointer input keyboardHelper.Update(currentSpace, predictedDisplayTime); VirtualKeyboardLocation loc; keyboardHelper.GetVirtualKeyboardLocation(currentSpace, predictedDisplayTime, &loc); XrPosef interactorRootPose; keyboardHelper.SendVirtualKeyboardInput( currentSpace, XR_VIRTUAL_KEYBOARD_INPUT_SOURCE_HAND_INDEX_TIP_META, indexFingerTipPose, /*pressed=*/isPinching, &interactorRootPose); // Sync pending text into the keyboard (e.g., for pre-fill) keyboardHelper.UpdateTextContext("Hello"); ``` -------------------------------- ### Configure OpenGL Sample Common Target Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/SampleXrFramework/CMakeLists.txt Sets up include directories and links necessary libraries for the 'samplecommon_gl' target. Includes platform-specific configurations for Android and Windows. ```cmake target_include_directories( samplecommon_gl INTERFACE ${1STPARTY_PATH}/OVR/Include ${3RDPARTY_PATH}/khronos/openxr/OpenXR-SDK/src/common # Extra vendor-provided headers ${OPENXR_PREVIEW_HEADER} ) target_link_libraries(samplecommon_gl INTERFACE OpenXR::openxr_loader) if(ANDROID) target_include_directories(samplecommon_gl INTERFACE ${ANDROID_NDK}/sources/android/native_app_glue) # Link the interface target to the dependency targets target_link_libraries(samplecommon_gl INTERFACE android EGL GLESv3 log app_glue ) elseif(WIN32) target_compile_definitions(samplecommon_gl INTERFACE _USE_MATH_DEFINES) target_link_libraries(samplecommon_gl INTERFACE samplecommon_win32gl) endif() ``` -------------------------------- ### Get First Element of a List Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Retrieves the first element of a list. Throws an error if the list is empty. ```javascript function Qn(n){if(n.i())throw mu("List is empty.");return n.j(kt(n))} ``` -------------------------------- ### Windows Build Configuration Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrPassthroughOcclusion/CMakeLists.txt Configures the build for Windows by creating an executable and linking it with samplecommon_gl. Includes custom commands to copy assets. ```cmake elseif(WIN32) add_executable(${PROJECT_NAME} ${SRC_FILES}) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_CURRENT_LIST_DIR}/assets" "$/assets" VERBATIM) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_SOURCE_DIR}/SampleXrFramework/res/raw" "$/font/res/raw" VERBATIM) target_link_libraries(${PROJECT_NAME} PRIVATE samplecommon_gl) endif() ``` -------------------------------- ### Windows Build Configuration Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrPassthrough/CMakeLists.txt Configures the build for Windows, creating an executable and linking against samplecommon_gl. It also includes custom commands to copy assets and font resources. ```cmake add_executable(${PROJECT_NAME} ${SRC_FILES}) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_CURRENT_LIST_DIR}/assets" "$/assets" VERBATIM) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_SOURCE_DIR}/SampleXrFramework/res/raw" "$/font/res/raw" VERBATIM) target_link_libraries(${PROJECT_NAME} PRIVATE samplecommon_gl) endif() ``` -------------------------------- ### Find Substring with Options Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Finds the index of a substring within a string, with options for start position and case sensitivity. ```javascript function Wt(n,t,r,i){return r=r===A?0:r,(i=i!==A&&i)||"string"!=typeof n?Kt(n,t,r,Wi(n),i):n.indexOf(t,r)} ``` -------------------------------- ### Constructor for qt Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the qt class with two given values. ```javascript function qt(n,t){this.b2_1=n,this.c2_1=t} ``` -------------------------------- ### Initialize and Use Dynamic Object Tracker Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Initializes the `XrDynamicObjectTrackerHelper` and updates it per frame. Handles asynchronous results for detected objects like keyboards. ```cpp #include "XrDynamicObjectTrackerHelper.h" // In AppInit: if (ExtensionsArePresent(XrDynamicObjectTrackerHelper::RequiredExtensionNames())) { DynamicObjectTracker = std::make_unique(GetInstance()); } // In SessionInit: if (DynamicObjectTracker) { DynamicObjectTracker->SessionInit(GetSession()); DynamicObjectTracker->CreateDynamicObjectTracker(); // async, fires event DynamicObjectTracker->SetDynamicObjectTrackedClasses({ XR_DYNAMIC_OBJECT_CLASS_KEYBOARD_META }); } // In Update (per-frame): if (DynamicObjectTracker) { DynamicObjectTracker->Update(GetCurrentSpace(), GetPredictedDisplayTime()); } // Handle async result events: bool HandleXrEvents(const XrEventDataBaseHeader* baseEventHeader) { if (DynamicObjectTracker && DynamicObjectTracker->HandleXrEvents(baseEventHeader)) { if (DynamicObjectTracker->GetTrackerState() == XrDynamicObjectTrackerHelper::TrackerState::Initialized) { // Query class for a spatial entity space XrDynamicObjectClassMETA classType; if (DynamicObjectTracker->GetDynamicObjectClass(objectSpace, classType)) { if (classType == XR_DYNAMIC_OBJECT_CLASS_KEYBOARD_META) { // Keyboard found — render overlay or interaction UI } } } return true; } return false; } ``` -------------------------------- ### Get Non-Empty String or Empty List Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Returns a non-empty list if the input string has length, otherwise returns an empty list. ```javascript function bt(n){return n.length>0?nu(n):pt()} ``` -------------------------------- ### Set Minimum CMake Version Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/CMakeLists.txt Specifies the minimum version of CMake required to build the project. Ensure your CMake installation meets this requirement. ```cmake cmake_minimum_required(VERSION 3.10.2) ``` -------------------------------- ### Get List Size Based on Type Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Returns the size of a list if it's of type Ti, otherwise returns a provided default value. ```javascript function xt(n,t){return Ue(n,Ti)?n.k():t} ``` -------------------------------- ### Constructor for It Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the It class with a list and a position index, calculating an offset. ```javascript function It(n,t){this.h2_1=n,this.g2_1=n.i2_1.l(function(n,t){if(!(0<=t&&t<=n.k()))throw cu("Position index "+t+" must be in range \["+ Oe(0,n.k())+"].");return n.k()-t|0}(n,t))} ``` -------------------------------- ### Windows Build Configuration Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrBodyFaceEyeSocial/CMakeLists.txt Configures the project as an executable for Windows. It defines a math constant and includes custom commands to copy assets and font resources before building. ```cmake elseif(WIN32) add_definitions(-D_USE_MATH_DEFINES) add_executable(${PROJECT_NAME} ${SRC_FILES}) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_CURRENT_LIST_DIR}/assets" "$/assets" VERBATIM) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_SOURCE_DIR}/SampleXrFramework/res/raw" "$/font/res/raw" VERBATIM) endif() ``` -------------------------------- ### Find Substring with Detailed Logic Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Finds the index of a substring within a string using detailed logic for string or other types, considering start and end points. ```javascript function Kt(n,t,r,i,e,u){var o=(u=u!==A&&u)?Xn(Kn(r,Yt(n)),Wn(i,0)):Oe(Wn(r,0),Kn(i,Wi(n)));if("string"==typeof n&&"string"==typeof t){var f=o.z2_1,s=o.a3_1,c=o.b3_1;if(c>0&&f<=s||c<0&&s<=f)do{var a=f;if(f=f+c|0,xi(t,0,n,a,Wi(t),e))return a}while(a!==s)}else{var h=o.z2_1,l=o.a3_1,\_=o.b3_1;if(\_>0&&h<=l||\_<0&&l<=h)do{var v=h;if(h=h+\_|0,tr(t,0,n,v,Wi(t),e))return v}while(v!==l)}return-1} ``` -------------------------------- ### xrGetHandMeshFB Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Retrieves the hand skeleton and skinning mesh data for a given hand tracker using the two-call idiom. First call with zero capacities to get sizes, then allocate buffers and call again to fill them. ```APIDOC ## xrGetHandMeshFB — Hand Mesh Retrieval (XR_FB_hand_tracking_mesh) ### Description Retrieves the hand skeleton and skinning mesh data for a given hand tracker using the two-call idiom: first call with zero capacities to get sizes, then allocate buffers and call again to fill them. Used in `XrHandsFB` sample. ### Method `xrGetHandMeshFB_` ### Parameters This function uses a pointer to an `XrHandTrackingMeshFB` struct which contains capacities and output counts for joints, vertices, and indices, as well as buffers to be filled with the mesh data. ### Request Example (Two-Call Idiom) ```cpp // Step 1: query sizes XrHandTrackingMeshFB mesh{XR_TYPE_HAND_TRACKING_MESH_FB}; mesh.jointCapacityInput = 0; mesh.vertexCapacityInput = 0; mesh.indexCapacityInput = 0; OXR(xrGetHandMeshFB_(handTrackerL_, &mesh)); // Expected: mesh.jointCountOutput, mesh.vertexCountOutput, mesh.indexCountOutput are populated // Step 2: allocate and fill mesh.jointCapacityInput = mesh.jointCountOutput; mesh.vertexCapacityInput = mesh.vertexCountOutput; mesh.indexCapacityInput = mesh.indexCountOutput; std::vector jointBindPoses(mesh.jointCountOutput); std::vector jointParents(mesh.jointCountOutput); std::vector jointRadii(mesh.jointCountOutput); mesh.jointBindPoses = jointBindPoses.data(); mesh.jointParents = jointParents.data(); mesh.jointRadii = jointRadii.data(); std::vector vertexPositions(mesh.vertexCountOutput); std::vector vertexNormals(mesh.vertexCountOutput); std::vector vertexUVs(mesh.vertexCountOutput); std::vector vertexBlendIndices(mesh.vertexCountOutput); std::vector vertexBlendWeights(mesh.vertexCountOutput); std::vector indices(mesh.indexCountOutput); mesh.vertexPositions = vertexPositions.data(); mesh.vertexNormals = vertexNormals.data(); mesh.vertexUVs = vertexUVs.data(); mesh.vertexBlendIndices = vertexBlendIndices.data(); mesh.vertexBlendWeights = vertexBlendWeights.data(); mesh.indices = indices.data(); OXR(xrGetHandMeshFB_(handTrackerL_, &mesh)); // mesh now contains full skeleton + skinned mesh ready for GPU upload ``` ### Response Upon successful execution, the `mesh` struct will be populated with the hand skeleton and skinning mesh data. `mesh.jointCountOutput`, `mesh.vertexCountOutput`, and `mesh.indexCountOutput` will indicate the number of elements retrieved. The provided buffers will be filled with the corresponding data. ``` -------------------------------- ### Create Parametric Haptics with EXTX1_haptic_parametric Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Query haptic device properties and then build and apply a complex vibration pattern with custom amplitude and frequency curves, and transient events. Ensure to set min/max frequency Hz from queried properties. ```cpp #include // Query properties PFN_xrHapticParametricGetPropertiesEXTX1 xrHapticParametricGetPropertiesEXTX1 = nullptr; OXR(xrGetInstanceProcAddr(instance, "xrHapticParametricGetPropertiesEXTX1", (PFN_xrVoidFunction*)(&xrHapticParametricGetPropertiesEXTX1))); XrHapticParametricPropertiesEXTX1 hapticProps{XR_TYPE_HAPTIC_PARAMETRIC_PROPERTIES_EXTX1}; OXR(xrHapticParametricGetPropertiesEXTX1(session, &hapticActionInfo, &hapticProps)); // hapticProps.minFrequencyHz, maxFrequencyHz, idealFrameSubmissionRate are now set // Build a vibration with amplitude ramp-up and a transient XrHapticParametricPointEXTX1 amplitudePoints[] = { {.time = 0, .value = 0.0f}, {.time = 100 * 1000000LL, .value = 1.0f}, // ramp to full over 100ms {.time = 200 * 1000000LL, .value = 0.0f}, // ramp down }; XrHapticParametricPointEXTX1 frequencyPoints[] = { {.time = 0, .value = 200.0f}, {.time = 200 * 1000000LL, .value = 200.0f}, }; XrHapticParametricTransientEXTX1 transients[] = { {.time = 50 * 1000000LL, .amplitude = 0.8f, .frequency = 300.0f}, }; XrHapticParametricVibrationEXTX1 vibration{XR_TYPE_HAPTIC_PARAMETRIC_VIBRATION_EXTX1}; vibration.amplitudePointCount = 3; vibration.amplitudePoints = amplitudePoints; vibration.frequencyPointCount = 2; vibration.frequencyPoints = frequencyPoints; vibration.transientCount = 1; vibration.transients = transients; vibration.minFrequencyHz = hapticProps.minFrequencyHz; vibration.maxFrequencyHz = hapticProps.maxFrequencyHz; vibration.streamFrameType = XR_HAPTIC_PARAMETRIC_STREAM_FRAME_TYPE_FIRST_FRAME_EXTX1; XrHapticActionInfo hapticAction{XR_TYPE_HAPTIC_ACTION_INFO}; hapticAction.action = hapticActionHandle; hapticAction.subactionPath = XR_NULL_PATH; OXR(xrApplyHapticFeedback(session, &hapticAction, (XrHapticBaseHeader*)&vibration)); ``` -------------------------------- ### Create and Use Dedicated Event Channels with OpenXR Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Use `XR_EXTX1_event_channel` to create separate event channels for different subsystems. This avoids a monolithic event queue and allows multiplexed waiting across channels using `xrSelectEventChannelEXTX1`. Ensure the extension is supported and function pointers are retrieved. ```cpp #include PFN_xrCreateEventChannelEXTX1 xrCreateEventChannelEXTX1 = nullptr; PFN_xrPollEventChannelEXTX1 xrPollEventChannelEXTX1 = nullptr; PFN_xrSelectEventChannelEXTX1 xrSelectEventChannelEXTX1 = nullptr; PFN_xrSetDefaultEventChannelEXTX1 xrSetDefaultEventChannelEXTX1 = nullptr; OXR(xrGetInstanceProcAddr(instance, "xrCreateEventChannelEXTX1", (PFN_xrVoidFunction*)&xrCreateEventChannelEXTX1)); OXR(xrGetInstanceProcAddr(instance, "xrPollEventChannelEXTX1", (PFN_xrVoidFunction*)&xrPollEventChannelEXTX1)); OXR(xrGetInstanceProcAddr(instance, "xrSelectEventChannelEXTX1", (PFN_xrVoidFunction*)&xrSelectEventChannelEXTX1)); // Create a dedicated channel XrEventChannelCreateInfoEXTX1 createInfo{XR_TYPE_EVENT_CHANNEL_CREATE_INFO_EXTX1}; XrEventChannelEXTX1 myChannel = XR_NULL_HANDLE; OXR(xrCreateEventChannelEXTX1(instance, &createInfo, &myChannel)); // Select across channels with timeout XrEventChannelEXTX1 channels[] = {myChannel}; XrSelectEventChannelInfoEXTX1 selectInfo{XR_TYPE_SELECT_EVENT_CHANNEL_INFO_EXTX1}; selectInfo.eventChannelCount = 1; selectInfo.eventChannels = channels; selectInfo.timeout = 0; // non-blocking uint32_t channelWithEvent = 0; XrResult selectResult = xrSelectEventChannelEXTX1(instance, &selectInfo, &channelWithEvent); if (selectResult == XR_SUCCESS) { XrEventDataBuffer event{XR_TYPE_EVENT_DATA_BUFFER}; while (xrPollEventChannelEXTX1(channels[channelWithEvent], &event) == XR_SUCCESS) { // process event } } ``` -------------------------------- ### Windows Executable Build and Asset Copying Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrSceneModel/CMakeLists.txt Configures the build for Windows, creating an executable. It includes custom pre-build commands to copy 'assets' and 'res/raw' directories to the target executable's directory. ```cmake add_executable(${PROJECT_NAME} ${SRC_FILES}) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_CURRENT_LIST_DIR}/assets" "$/assets" VERBATIM) add_custom_command(TARGET ${PROJECT_NAME} PRE_BUILD COMMAND "${CMAKE_COMMAND}" -E copy_directory "${CMAKE_SOURCE_DIR}/SampleXrFramework/res/raw" "$/font/res/raw" VERBATIM) target_link_libraries(${PROJECT_NAME} PRIVATE samplecommon_gl) ``` -------------------------------- ### Constructor for yt Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the yt class with specific values. ```javascript function yt(){e=this,this.z1_1=new de(-1478467534,-1720727600)} ``` -------------------------------- ### Initialize Social Tracking Extensions in OpenXR Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt This C++ code initializes OpenXR by requesting extensions for body, face, and eye tracking. It chains system property structs to query support for each extension and then loads the necessary function pointers if the features are available on the system. Ensure OpenXR version is set correctly and required extensions are listed. ```cpp class XrBodyFaceEyeSocialApp : public OVRFW::XrApp { public: XrBodyFaceEyeSocialApp() : OVRFW::XrApp() { OpenXRVersion = XR_API_VERSION_1_1; } virtual std::vector GetExtensions() override { std::vector extensions = XrApp::GetExtensions(); extensions.push_back(XR_FB_BODY_TRACKING_EXTENSION_NAME); extensions.push_back(XR_FB_EYE_TRACKING_SOCIAL_EXTENSION_NAME); extensions.push_back(XR_FB_FACE_TRACKING2_EXTENSION_NAME); return extensions; } virtual bool AppInit(const xrJava* context) override { // Chain all three property structs in one query XrSystemEyeTrackingPropertiesFB eyeProps{XR_TYPE_SYSTEM_EYE_TRACKING_PROPERTIES_FB}; XrSystemBodyTrackingPropertiesFB bodyProps{XR_TYPE_SYSTEM_BODY_TRACKING_PROPERTIES_FB}; XrSystemFaceTrackingProperties2FB faceProps{XR_TYPE_SYSTEM_FACE_TRACKING_PROPERTIES2_FB}; XrSystemProperties sysProps{XR_TYPE_SYSTEM_PROPERTIES}; sysProps.next = &eyeProps; eyeProps.next = &bodyProps; bodyProps.next = &faceProps; OXR(xrGetSystemProperties(GetInstance(), GetSystemId(), &sysProps)); if (bodyProps.supportsBodyTracking) { OXR(xrGetInstanceProcAddr(GetInstance(), "xrCreateBodyTrackerFB", (PFN_xrVoidFunction*)(&xrCreateBodyTrackerFB_))); OXR(xrGetInstanceProcAddr(GetInstance(), "xrDestroyBodyTrackerFB", (PFN_xrVoidFunction*)(&xrDestroyBodyTrackerFB_))); OXR(xrGetInstanceProcAddr(GetInstance(), "xrLocateBodyJointsFB", (PFN_xrVoidFunction*)(&xrLocateBodyJointsFB_))); OXR(xrGetInstanceProcAddr(GetInstance(), "xrGetBodySkeletonFB", (PFN_xrVoidFunction*)(&xrGetSkeletonFB_))); } if (eyeProps.supportsEyeTracking) { OXR(xrGetInstanceProcAddr(GetInstance(), "xrCreateEyeTrackerFB", (PFN_xrVoidFunction*)(&xrCreateEyeTrackerFB_))); OXR(xrGetInstanceProcAddr(GetInstance(), "xrGetEyeGazesFB", (PFN_xrVoidFunction*)(&xrGetEyeGazesFB_))); } if (faceProps.supportsVisualFaceTracking || faceProps.supportsAudioFaceTracking) { OXR(xrGetInstanceProcAddr(GetInstance(), "xrCreateFaceTracker2FB", (PFN_xrVoidFunction*)(&xrCreateFaceTracker2FB_))); OXR(xrGetInstanceProcAddr(GetInstance(), "xrGetFaceExpressionWeights2FB", (PFN_xrVoidFunction*)(&xrGetFaceExpressionWeights2FB_))); } return true; } private: PFN_xrCreateBodyTrackerFB xrCreateBodyTrackerFB_ = nullptr; PFN_xrDestroyBodyTrackerFB xrDestroyBodyTrackerFB_ = nullptr; PFN_xrLocateBodyJointsFB xrLocateBodyJointsFB_ = nullptr; PFN_xrGetBodySkeletonFB xrGetSkeletonFB_ = nullptr; PFN_xrCreateEyeTrackerFB xrCreateEyeTrackerFB_ = nullptr; PFN_xrDestroyEyeTrackerFB xrDestroyEyeTrackerFB_ = nullptr; PFN_xrGetEyeGazesFB xrGetEyeGazesFB_ = nullptr; PFN_xrCreateFaceTracker2FB xrCreateFaceTracker2FB_ = nullptr; PFN_xrDestroyFaceTracker2FB xrDestroyFaceTracker2FB_ = nullptr; PFN_xrGetFaceExpressionWeights2FB xrGetFaceExpressionWeights2FB_= nullptr; }; ``` -------------------------------- ### Android Library Build Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrSceneModel/CMakeLists.txt Configures the build for Android, creating a MODULE library. It links against 'samplecommon_gl' and sets a linker flag for ANativeActivity_onCreate. ```cmake add_library(${PROJECT_NAME} MODULE ${SRC_FILES}) target_link_libraries(${PROJECT_NAME} PRIVATE samplecommon_gl) set_target_properties(${PROJECT_NAME} PROPERTIES LINK_FLAGS "-u ANativeActivity_onCreate") ``` -------------------------------- ### Android Sample Gradle Build Configuration Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Gradle build configuration for an Android sample, specifying compile SDK version, default config, CMake path, and OpenXR loader dependency. ```groovy // Samples/XrSamples/XrHandsFB/Projects/Android/build.gradle android { compileSdkVersion 34 defaultConfig { applicationId "com.oculus.sdk.handsfb" minSdkVersion 29 targetSdkVersion 34 versionCode 1 versionName "1.0" } externalNativeBuild { cmake { path "../../CMakeLists.txt" } } } dependencies { implementation 'org.khronos.openxr:openxr_loader_for_android:1.1.53' } ``` -------------------------------- ### Constructor for zt Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the zt class with a list and an iterator. ```javascript function zt(n){this.k2_1=n,this.j2_1=n.l2_1.f()} ``` -------------------------------- ### XrHelper Abstract Base Class and Usage Pattern Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Defines the XrHelper abstract base class for extension wrappers and demonstrates its usage in composing helpers based on runtime-detected extensions. ```cpp // XrHelper.h class XrHelper { public: explicit XrHelper(XrInstance instance) : Instance(instance) {} virtual ~XrHelper() = default; virtual void SessionInit(XrSession session) = 0; virtual void SessionEnd() = 0; virtual void Update(XrSpace currentSpace, XrTime predictedDisplayTime) = 0; protected: XrInstance Instance; }; // Usage in XrDynamicObjectsApp — compose helpers from extensions present at runtime // (Samples/XrSamples/XrDynamicObjects/Src/main.cpp) bool AppInit(const xrJava* context) override { if (ExtensionsArePresent(XrHandHelper::RequiredExtensionNames())) HandL = std::make_unique(GetInstance(), /*isLeft=*/true); if (ExtensionsArePresent(XrDynamicObjectTrackerHelper::RequiredExtensionNames())) DynamicObjectTracker = std::make_unique(GetInstance()); if (ExtensionsArePresent(XrSpatialAnchorHelper::RequiredExtensionNames())) SpatialAnchor = std::make_unique(GetInstance()); if (ExtensionsArePresent(XrPassthroughHelper::RequiredExtensionNames())) Passthrough = std::make_unique(GetInstance()); return true; } bool SessionInit() override { if (HandL) HandL->SessionInit(GetSession()); if (DynamicObjectTracker) DynamicObjectTracker->SessionInit(GetSession()); if (SpatialAnchor) SpatialAnchor->SessionInit(GetSession()); if (Passthrough) Passthrough->SessionInit(GetSession()); return true; } void Update(const ovrApplFrameIn& in, ovrRendererOutput& out) override { if (HandL) HandL->Update(GetCurrentSpace(), in.PredictedDisplayTime); if (DynamicObjectTracker) DynamicObjectTracker->Update(GetCurrentSpace(), in.PredictedDisplayTime); } ``` -------------------------------- ### Enable Experimental OpenXR Features on Device Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Use adb to enable experimental OpenXR features on the headset. This setting resets on reboot. ```bash # Enable experimental OpenXR features on the headset (resets on reboot) adb shell setprop debug.oculus.experimentalEnabled 1 ``` -------------------------------- ### Android Build Configuration Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrPassthroughOcclusion/CMakeLists.txt Configures the build for Android by creating a shared library and linking it with samplecommon_gl. Sets a linker flag for ANativeActivity_onCreate. ```cmake if(ANDROID) add_library(${PROJECT_NAME} MODULE ${SRC_FILES}) target_link_libraries(${PROJECT_NAME} PRIVATE samplecommon_gl) set_target_properties(${PROJECT_NAME} PROPERTIES LINK_FLAGS "-u ANativeActivity_onCreate") ``` -------------------------------- ### Access Room Mesh Geometry with XR_META_spatial_entity_room_mesh Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt This snippet demonstrates how to retrieve vertex and face data for a scanned room, including semantic labels for each face. It uses a two-call pattern to first query capacities and then allocate memory before fetching the actual mesh data. Ensure the necessary extension headers are included and function pointers are obtained. ```cpp #include #include PFN_xrGetSpaceRoomMeshMETA xrGetSpaceRoomMeshMETA = nullptr; PFN_xrGetSpaceRoomMeshFaceIndicesMETA xrGetSpaceRoomMeshFaceIndicesMETA = nullptr; OXR(xrGetInstanceProcAddr(instance, "xrGetSpaceRoomMeshMETA", (PFN_xrVoidFunction*)&xrGetSpaceRoomMeshMETA)); OXR(xrGetInstanceProcAddr(instance, "xrGetSpaceRoomMeshFaceIndicesMETA", (PFN_xrVoidFunction*)&xrGetSpaceRoomMeshFaceIndicesMETA)); // Query size first (two-call pattern) XrSemanticLabelMETA recognizedLabels[] = { XR_SEMANTIC_LABEL_FLOOR_META, XR_SEMANTIC_LABEL_CEILING_META, XR_SEMANTIC_LABEL_WALL_FACE_META, XR_SEMANTIC_LABEL_DOOR_FRAME_META, XR_SEMANTIC_LABEL_WINDOW_FRAME_META, }; XrSpaceRoomMeshGetInfoMETA getInfo{XR_TYPE_SPACE_ROOM_MESH_GET_INFO_META}; getInfo.recognizedSemanticLabelCount = 5; getInfo.recognizedSemanticLabels = recognizedLabels; XrRoomMeshMETA roomMesh{XR_TYPE_ROOM_MESH_META}; roomMesh.vertexCapacityInput = 0; roomMesh.faceCapacityInput = 0; OXR(xrGetSpaceRoomMeshMETA(roomSpace, &getInfo, &roomMesh)); // Allocate and fill std::vector vertices(roomMesh.vertexCountOutput); std::vector faces(roomMesh.faceCountOutput); roomMesh.vertexCapacityInput = roomMesh.vertexCountOutput; roomMesh.faceCapacityInput = roomMesh.faceCountOutput; roomMesh.vertices = vertices.data(); roomMesh.faces = faces.data(); OXR(xrGetSpaceRoomMeshMETA(roomSpace, &getInfo, &roomMesh)); // Retrieve per-face triangle indices for (uint32_t i = 0; i < roomMesh.faceCountOutput; ++i) { if (faces[i].semanticLabel == XR_SEMANTIC_LABEL_FLOOR_META) { XrRoomMeshFaceIndicesMETA faceIndices{XR_TYPE_ROOM_MESH_FACE_INDICES_META}; faceIndices.indexCapacityInput = 0; OXR(xrGetSpaceRoomMeshFaceIndicesMETA(roomSpace, &faces[i].uuid, &faceIndices)); std::vector indexBuf(faceIndices.indexCountOutput); faceIndices.indexCapacityInput = faceIndices.indexCountOutput; faceIndices.indices = indexBuf.data(); OXR(xrGetSpaceRoomMeshFaceIndicesMETA(roomSpace, &faces[i].uuid, &faceIndices)); // indexBuf now holds triangle indices into vertices[] for this floor face } } ``` -------------------------------- ### Constructor for St Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the St class, calling parent constructors and setting a list. ```javascript function St(n){st.call(this),this.i2_1=n} ``` -------------------------------- ### Android Build Configuration Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrPassthrough/CMakeLists.txt Configures the build for Android, creating a shared library and linking against samplecommon_gl. It also sets a linker flag required for Android activities. ```cmake if(ANDROID) add_library(${PROJECT_NAME} MODULE ${SRC_FILES}) target_link_libraries(${PROJECT_NAME} PRIVATE samplecommon_gl) set_target_properties(${PROJECT_NAME} PROPERTIES LINK_FLAGS "-u ANativeActivity_onCreate") elseif(WIN32) ``` -------------------------------- ### Common Platform Configuration Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrBodyFaceEyeSocial/CMakeLists.txt Applies common build configurations across all platforms. This includes setting private include directories and linking against a shared sample framework library. ```cmake # Common across platforms target_include_directories(${PROJECT_NAME} PRIVATE Src) target_link_libraries(${PROJECT_NAME} PRIVATE samplexrframework) ``` -------------------------------- ### Constructor for $t Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the $t class with comparison values and a step, determining an initial state. ```javascript function $t(n,t,r){Pt.call(this),this.d3_1=r,this.e3_1=t,this.f3_1=this.d3_1>0?n<=t:n>=t,this.g3_1=this.f3_1?n:this.e3_1} ``` -------------------------------- ### Constructor for ut Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the ut class, calling the parent constructor and setting a width. ```javascript function ut(n,t){this.a1_1=n,et.call(this,n),ft().b1(t,this.a1_1.k()),this.w_1=t} ``` -------------------------------- ### OpenXR Time Conversion Helpers Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt Provides utility functions for converting between OpenXR's XrTime (nanoseconds as int64_t) and double-precision seconds. These are essential for time-based calculations in OpenXR applications. ```cpp #include // XrTime (nanoseconds) to seconds XrTime xrNow = ...; // e.g., predictedDisplayTime from XrFrameState double seconds = FromXrTime(xrNow); // e.g., 1234567890.123456789 ns → 1.234... s // Seconds to XrTime double timeInSeconds = 0.016; // 16 ms XrTime asXrTime = ToXrTime(timeInSeconds); // → 16000000 ns // These are used in display-time arithmetic: XrTime futureTime = ToXrTime(FromXrTime(predictedDisplayTime) + 0.1); // +100ms offset ``` -------------------------------- ### Populate a Target List from a Source List Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Iterates through a source list and adds each element to a target list. ```javascript function Zn(n,t){for(var r=n.f();r.g();){var i=r.h();t.d(i)}return t} ``` -------------------------------- ### XrApp Subclass for Hand Tracking Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt This C++ code defines a sample application that subclasses XrApp to enable hand tracking. It declares necessary OpenXR extensions and initializes hand trackers. ```cpp #include "XrApp.h" #include "Input/HandRenderer.h" class XrHandsApp : public OVRFW::XrApp { public: XrHandsApp() : OVRFW::XrApp() { BackgroundColor = OVR::Vector4f(0.60f, 0.95f, 0.4f, 1.0f); } // Declare required OpenXR extensions virtual std::vector GetExtensions() override { std::vector extensions = XrApp::GetExtensions(); extensions.push_back(XR_EXT_HAND_TRACKING_EXTENSION_NAME); extensions.push_back(XR_FB_HAND_TRACKING_MESH_EXTENSION_NAME); extensions.push_back(XR_FB_HAND_TRACKING_AIM_EXTENSION_NAME); extensions.push_back(XR_FB_HAND_TRACKING_CAPSULES_EXTENSION_NAME); return extensions; } // Initialize app state after XrInstance is created virtual bool AppInit(const xrJava* context) override { // Check system support for hand tracking XrSystemHandTrackingPropertiesEXT handTrackingSystemProperties{ XR_TYPE_SYSTEM_HAND_TRACKING_PROPERTIES_EXT}; XrSystemProperties systemProperties{ XR_TYPE_SYSTEM_PROPERTIES, &handTrackingSystemProperties}; OXR(xrGetSystemProperties(GetInstance(), GetSystemId(), &systemProperties)); if (!handTrackingSystemProperties.supportsHandTracking) { ALOG("Hand tracking not supported."); return false; } // Load extension function pointers OXR(xrGetInstanceProcAddr(GetInstance(), "xrCreateHandTrackerEXT", (PFN_xrVoidFunction*)(&xrCreateHandTrackerEXT_))); OXR(xrGetInstanceProcAddr(GetInstance(), "xrLocateHandJointsEXT", (PFN_xrVoidFunction*)(&xrLocateHandJointsEXT_))); OXR(xrGetInstanceProcAddr(GetInstance(), "xrGetHandMeshFB", (PFN_xrVoidFunction*)(&xrGetHandMeshFB_))); return true; } virtual bool SessionInit() override { // Create hand trackers XrHandTrackerCreateInfoEXT createInfo{XR_TYPE_HAND_TRACKER_CREATE_INFO_EXT}; createInfo.handJointSet = XR_HAND_JOINT_SET_DEFAULT_EXT; createInfo.hand = XR_HAND_LEFT_EXT; OXR(xrCreateHandTrackerEXT_(GetSession(), &createInfo, &handTrackerL_)); createInfo.hand = XR_HAND_RIGHT_EXT; OXR(xrCreateHandTrackerEXT_(GetSession(), &createInfo, &handTrackerR_)); return true; } virtual void AppShutdown(const xrJava* context) override { xrCreateHandTrackerEXT_ = nullptr; xrLocateHandJointsEXT_ = nullptr; xrGetHandMeshFB_ = nullptr; OVRFW::XrApp::AppShutdown(context); } private: PFN_xrCreateHandTrackerEXT xrCreateHandTrackerEXT_ = nullptr; PFN_xrLocateHandJointsEXT xrLocateHandJointsEXT_ = nullptr; PFN_xrGetHandMeshFB xrGetHandMeshFB_ = nullptr; XrHandTrackerEXT handTrackerL_ = XR_NULL_HANDLE; XrHandTrackerEXT handTrackerR_ = XR_NULL_HANDLE; }; // Entry point (Android) #if defined(ANDROID) void android_main(struct android_app* app) { auto appl = std::make_unique(); appl->Run(app); } #endif ``` -------------------------------- ### Constructor for st Class Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html Initializes the st class, calling parent constructors. ```javascript function st(){ft(),it.call(this)} ``` -------------------------------- ### EXTX1_haptic_parametric Source: https://context7.com/meta-quest/meta-openxr-sdk/llms.txt This extension enables per-frame streaming of amplitude/frequency curves and transient haptic events to controllers, replacing the simpler simple-vibration model. ```APIDOC ## EXTX1_haptic_parametric — Parametric Haptics ### Description Enables per-frame streaming of amplitude/frequency curves and transient haptic events to controllers, replacing the simpler simple-vibration model. Supports frequencies from 1 Hz to 1000 Hz and up to 500 transient points per frame. ### Usage Example ```cpp #include // Query properties PFN_xrHapticParametricGetPropertiesEXTX1 xrHapticParametricGetPropertiesEXTX1 = nullptr; OXR(xrGetInstanceProcAddr(instance, "xrHapticParametricGetPropertiesEXTX1", (PFN_xrVoidFunction*)(&xrHapticParametricGetPropertiesEXTX1))); XrHapticParametricPropertiesEXTX1 hapticProps{XR_TYPE_HAPTIC_PARAMETRIC_PROPERTIES_EXTX1}; OXR(xrHapticParametricGetPropertiesEXTX1(session, &hapticActionInfo, &hapticProps)); // hapticProps.minFrequencyHz, maxFrequencyHz, idealFrameSubmissionRate are now set // Build a vibration with amplitude ramp-up and a transient XrHapticParametricPointEXTX1 amplitudePoints[] = { {.time = 0, .value = 0.0f}, {.time = 100 * 1000000LL, .value = 1.0f}, // ramp to full over 100ms {.time = 200 * 1000000LL, .value = 0.0f}, // ramp down }; XrHapticParametricPointEXTX1 frequencyPoints[] = { {.time = 0, .value = 200.0f}, {.time = 200 * 1000000LL, .value = 200.0f}, }; XrHapticParametricTransientEXTX1 transients[] = { {.time = 50 * 1000000LL, .amplitude = 0.8f, .frequency = 300.0f}, }; XrHapticParametricVibrationEXTX1 vibration{XR_TYPE_HAPTIC_PARAMETRIC_VIBRATION_EXTX1}; vibration.amplitudePointCount = 3; vibration.amplitudePoints = amplitudePoints; vibration.frequencyPointCount = 2; vibration.frequencyPoints = frequencyPoints; vibration.transientCount = 1; vibration.transients = transients; vibration.minFrequencyHz = hapticProps.minFrequencyHz; vibration.maxFrequencyHz = hapticProps.maxFrequencyHz; vibration.streamFrameType = XR_HAPTIC_PARAMETRIC_STREAM_FRAME_TYPE_FIRST_FRAME_EXTX1; XrHapticActionInfo hapticAction{XR_TYPE_HAPTIC_ACTION_INFO}; hapticAction.action = hapticActionHandle; hapticAction.subactionPath = XR_NULL_PATH; OXR(xrApplyHapticFeedback(session, &hapticAction, (XrHapticBaseHeader*)&vibration)); ``` ### Functions * `xrHapticParametricGetPropertiesEXTX1` * Description: Retrieves the properties of parametric haptics, such as frequency ranges. * Parameters: * `session` (XrSession) - The OpenXR session handle. * `hapticActionInfo` (const XrHapticActionInfo*) - Information about the haptic action. * `hapticProps` (XrHapticParametricPropertiesEXTX1*) - Pointer to a structure to be filled with haptic properties. * Return Value: `XrResult` ### Structures * `XrHapticParametricPropertiesEXTX1` * Description: Structure to hold properties of parametric haptics. * Fields: * `minFrequencyHz` (float) - Minimum supported frequency in Hz. * `maxFrequencyHz` (float) - Maximum supported frequency in Hz. * `idealFrameSubmissionRate` (float) - The ideal rate for submitting haptic frames. * `XrHapticParametricPointEXTX1` * Description: Represents a point in time for amplitude or frequency curves. * Fields: * `time` (XrTime) - The time in nanoseconds. * `value` (float) - The amplitude or frequency value at the specified time. * `XrHapticParametricTransientEXTX1` * Description: Defines a transient haptic event. * Fields: * `time` (XrTime) - The time in nanoseconds when the transient event occurs. * `amplitude` (float) - The amplitude of the transient event. * `frequency` (float) - The frequency of the transient event. * `XrHapticParametricVibrationEXTX1` * Description: Structure defining a parametric vibration. * Fields: * `amplitudePointCount` (uint32_t) - Number of points in the amplitude curve. * `amplitudePoints` (const XrHapticParametricPointEXTX1*) - Array of amplitude points. * `frequencyPointCount` (uint32_t) - Number of points in the frequency curve. * `frequencyPoints` (const XrHapticParametricPointEXTX1*) - Array of frequency points. * `transientCount` (uint32_t) - Number of transient events. * `transients` (const XrHapticParametricTransientEXTX1*) - Array of transient events. * `minFrequencyHz` (float) - Minimum frequency for this vibration. * `maxFrequencyHz` (float) - Maximum frequency for this vibration. * `streamFrameType` (XrHapticParametricStreamFrameTypeEXTX1) - Type of the haptic stream frame. ``` -------------------------------- ### Project Name and Languages Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/CMakeLists.txt Defines the project name as 'MetaOpenXRSDK' and specifies that it will be built using C and C++ languages. ```cmake project(MetaOpenXRSDK C CXX) ``` -------------------------------- ### Empty Constructor Source: https://github.com/meta-quest/meta-openxr-sdk/blob/main/Samples/XrSamples/XrOverlayKeyboard/Projects/Android/build/reports/problems/problems-report.html A simple constructor function with no arguments. ```javascript function it(){} ```