XR_ANDROID_spatial_discovery_raycast

מחרוזת שם

XR_ANDROID_spatial_discovery_raycast

סוג התוסף

תוסף למכונה

מספר השלוחה הרשום

787

גרסה

1

סטטוס האישור

לא אושר

תלויות של תוספים וגרסאות

XR_EXT_spatial_entity

תאריך השינוי האחרון

2025-08-12

סטטוס IP

אין תלונות ידועות על הפרת קניין רוחני.

שותפים ביצירת התוכן

בריאן צ'ן, Google
לבנה צ'ן, Google
קייל צ'ן, Google
ניהב ג'יין, Google
ספנסר קווין, Google
נטלי פלורי, Meta
יויצ'י טגוצ'י, Meta
ג'ימי אלמפרמביל, ByteDance
ז'יפנג ליו, ByteDance

סקירה כללית

התוסף הזה מבוסס על XR_EXT_spatial_entity ומספק פונקציונליות של Raycast ליכולות מרחביות קיימות, כמו XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT , כדי לגלות ישויות מרחביות.

התוסף הזה גם מציג יכולת מרחבית חדשה להטלת קרניים (raycasting) על מאגר עומק.

הרשאות

ההרשאות הנדרשות תלויות ביכולות שבהן האפליקציה ל-Android משתמשת. אם משתמשים ב-XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID, לאפליקציה חייבת להיות ההרשאה android.permission.SCENE_UNDERSTANDING_FINE. אם משתמשים ב-XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT, האפליקציה חייבת לקבל את ההרשאה android.permission.SCENE_UNDERSTANDING_COARSE. ההרשאה android.permission.SCENE_UNDERSTANDING_FINE כוללת גם את ההרשאה android.permission.SCENE_UNDERSTANDING_COARSE. אם האפליקציה משתמשת בשתי היכולות, היא לא צריכה לבקש את שתי ההרשאות בנפרד.

שתי ההרשאות android.permission.SCENE_UNDERSTANDING_COARSE ו-android.permission.SCENE_UNDERSTANDING_FINE נחשבות להרשאות מסוכנות.

(רמת הגנה: מסוכן)

תמיכה בסביבת זמן הריצה

אם סביבת זמן הריצה תומכת בגילוי של ישויות מרחביות באמצעות הטלת קרניים, היא חייבת לציין זאת על ידי ספירת XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID ב-xrEnumerateSpatialCapabilityComponentTypesEXT עבור היכולות שתומכות בגילוי באמצעות הטלת קרניים.

אם זמן הריצה תומך בהטלת קרניים (raycasting) במאגר העומק, הוא חייב למנות את XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID ב-xrEnumerateSpatialCapabilitiesEXT .

גילוי ישויות מרחביות באמצעות הטלת קרניים (raycasting)

המבנה של XrSpatialRaycastInfoANDROID מוגדר כך:

typedef struct XrSpatialRaycastInfoANDROID {
    XrStructureType    type;
    const void*        next;
    XrSpace            space;
    XrTime             time;
    XrVector3f         origin;
    XrVector3f         direction;
    float              maxDistance;
} XrSpatialRaycastInfoANDROID;

תיאורי חברים

  • ‫type הוא ה-XrStructureType של המבנה הזה.
  • ‫next הוא NULL או מצביע למבנה הבא בשרשרת מבנים.
  • ‫space הוא ה-XrSpace שבו תהיה התנוחה של XrSpatialRaycastResultDataANDROID.
  • ‫time הוא XrTime שבו מוגדרת התנוחה של XrSpatialRaycastResultDataANDROID.
  • ‫origin הוא XrVector3f שמתאר את מקור הקרן.
  • ‫direction הוא XrVector3f שמתאר את כיוון הקרן.
  • ‫maxDistance הוא המרחק במטרים שהאפליקציה יכולה לציין כדי להגביל את החיפוש של ישויות שנמצאות במרחק שצוין מה-origin , לאורך direction .

אפליקציה יכולה לכלול את XrSpatialRaycastInfoANDROID בשרשרת XrSpatialDiscoverySnapshotCreateInfoEXT :: next כדי לגלות ישויות מרחביות שמצטלבות עם הקרן שמוגדרת במבנה הזה.

אם אפליקציה משתמשת ב-XrSpatialRaycastInfoANDROID עם XrSpatialContextEXT שהוגדר בלי להפעיל את XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID לאף יכולת, זמן הריצה חייב להחזיר את XR_ERROR_SPATIAL_COMPONENT_NOT_ENABLED_EXT מ-xrCreateSpatialDiscoverySnapshotAsyncEXT או מ-xrCreateSpatialRaycastSnapshotANDROID .

זמן הריצה חייב לכלול את נתוני הרכיבים והמזהים רק של הישויות המרחביות ב-XrSpatialSnapshotEXT שמגיעות מיכולות שתומכות ברכיב XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID.

אם אפליקציה מגדירה את maxDistance לערך חיובי, זמן הריצה לא יכול לכלול ישויות מרחביות שמופיעות בתמונת המצב שנמצאות במרחק של יותר מ-maxDistance מ-panme:origin לאורך direction . אם הערך של maxDistance הוא 0 או ערך שלילי, זמן הריצה חייב להתייחס לקרן כלא מוגבלת.

שימוש תקין (משתמע)

רכיב תוצאת הטלת קרניים

המבנה של XrSpatialRaycastResultDataANDROID מוגדר כך:

typedef struct XrSpatialRaycastResultDataANDROID {
    XrPosef    hitPose;
    float      distanceSquared;
} XrSpatialRaycastResultDataANDROID;

תיאורי חברים

  • ‫hitPose הוא XrPosef שמגדיר את הנקודה שבה הקרן מצטלבת עם הישות המרחבית.
  • ‫distanceSquared הוא המרחק בריבוע מנקודת המוצא של הקרן לנקודת החיתוך.

הרכיב XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID יהיה קיים רק ב-XrSpatialSnapshotEXT שנוצר מ-xrCreateSpatialDiscoverySnapshotAsyncEXT שבו XrSpatialRaycastInfoANDROID נכלל בשרשרת XrSpatialDiscoverySnapshotCreateInfoEXT :: next או ב-XrSpatialSnapshotEXT שנוצר מ-xrCreateSpatialRaycastSnapshotANDROID .

סביבת זמן הריצה לא יכולה לכלול את הרכיב הזה באף XrSpatialSnapshotEXT שנוצר באמצעות xrCreateSpatialUpdateSnapshotEXT .

סביבת זמן הריצה חייבת להחזיר את הערך XR_ERROR_VALIDATION_FAILURE מ-xrCreateSpatialUpdateSnapshotEXT אם האפליקציה כוללת את XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID ב-XrSpatialUpdateSnapshotCreateInfoEXT :: componentTypes .

אם המדיניות XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID מופעלת רק ליכולות מסוימות, סביבת זמן הריצה חייבת לכלול בתמונת המצב רק ישויות מרחביות שסופקו על ידי היכולות האלה. לדוגמה, אם אובייקט ומטוס נמצאים באותו כיוון, והתכונה XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID מופעלת רק בשביל XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT, רק המטוס יזוהה.

ה-hitPose של ה-XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID יהיה ב-XrCreateSpatialDiscoverySnapshotCompletionInfoEXT :: baseSpace ב-XrCreateSpatialDiscoverySnapshotCompletionInfoEXT :: time . ציר Z החיובי הוא הנורמל של המשטח שבו פגעה הקרן, וציר Y השלילי מצביע בערך לכיוון המקור של הקרן.

שימוש תקין (משתמע)

מבנה של רשימת רכיבים לשאילתת נתונים

המבנה של XrSpatialComponentRaycastResultListANDROID מוגדר כך:

typedef struct XrSpatialComponentRaycastResultListANDROID {
    XrStructureType                       type;
    void*                                 next;
    uint32_t                              raycastResultCount;
    XrSpatialRaycastResultDataANDROID*    raycastResults;
} XrSpatialComponentRaycastResultListANDROID;

תיאורי חברים

  • ‫type הוא ה-XrStructureType של המבנה הזה.
  • ‫next הוא NULL או מצביע למבנה הבא בשרשרת מבנים.
  • ‫raycastResultCount הוא uint32_t שמתאר את מספר הרכיבים במערך raycastResults.
  • ‫raycastResults הוא מערך של XrSpatialRaycastResultDataANDROID .

כדי לשלוח שאילתה לרכיב של תוצאת ה-raycast של הישויות המרחביות ב-XrSpatialSnapshotEXT , צריך לכלול את XR_TYPE_SPATIAL_COMPONENT_RAYCAST_RESULT_LIST_ANDROID ב-XrSpatialComponentDataQueryConditionEXT :: componentTypes ולהוסיף את XrSpatialComponentRaycastResultListANDROID לשרשרת XrSpatialComponentDataQueryResultEXT :: next.

‫חובה שסביבת זמן הריצה תחזיר את הערך XR_ERROR_VALIDATION_FAILURE מ-xrQuerySpatialComponentDataEXT אם XrSpatialComponentRaycastResultListANDROID נמצא בשרשרת XrSpatialComponentDataQueryResultEXT :: next אבל XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID לא נכלל ב-XrSpatialComponentDataQueryConditionEXT :: componentTypes .

זמן הריצה חייב להחזיר את הערך XR_ERROR_SIZE_INSUFFICIENT מ-xrQuerySpatialComponentDataEXT אם raycastResultCount קטן מ-XrSpatialComponentDataQueryResultEXT :: entityIdCountOutput .

הערכים של raycastResults שמוחזרים לא מסודרים. אפליקציה יכולה להשתמש ב-XrSpatialRaycastResultDataANDROID :: distanceSquared כדי למיין את התוצאות לפי מרחק.

שימוש תקין (משתמע)

הגדרות אישיות

אם XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID מופיע ב-XrSpatialCapabilityComponentTypesEXT :: componentTypes עבור יכולת מסוימת, האפליקציה יכולה להפעיל אותה על ידי הכללת ערך ה-enum ברשימה XrSpatialCapabilityConfigurationBaseHeaderEXT :: enabledComponents. הרכיב הזה לא דורש הגדרה מיוחדת כדי להיכלל בשרשרת הבאה של XrSpatialCapabilityConfigurationBaseHeaderEXT .

סביבת זמן הריצה חייבת להחזיר את הערך XR_ERROR_VALIDATION_FAILURE מ-xrCreateSpatialUpdateSnapshotEXT אם האפליקציה כוללת את XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID ב-XrSpatialUpdateSnapshotCreateInfoEXT :: componentTypes . הרכיב הזה ספציפי לתמונות מצב של Discovery.

יכולת מרחבית של Depth Raycast

הגדרות אישיות

המבנה של XrSpatialCapabilityConfigurationDepthRaycastANDROID מוגדר כך:

typedef struct XrSpatialCapabilityConfigurationDepthRaycastANDROID {
    XrStructureType                     type;
    const void*                         next;
    XrSpatialCapabilityEXT              capability;
    uint32_t                            enabledComponentCount;
    const XrSpatialComponentTypeEXT*    enabledComponents;
} XrSpatialCapabilityConfigurationDepthRaycastANDROID;

תיאורי חברים

  • ‫type הוא ה-XrStructureType של המבנה הזה.
  • ‫next הוא NULL או מצביע למבנה הבא בשרשרת מבנים.
  • ‫capability הוא XrSpatialCapabilityEXT וחייב להיות XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID .
  • ‫enabledComponentCount הוא uint32_t שמתאר את מספר הרכיבים במערך enabledComponents. הערך חייב להיות גדול מ-0.
  • ‫enabledComponents הוא מצביע למערך של XrSpatialComponentTypeEXT .

אפליקציות יכולות להפעיל את היכולת המרחבית XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID על ידי הכללת מצביע למבנה XrSpatialCapabilityConfigurationDepthRaycastANDROID ב-XrSpatialContextCreateInfoEXT :: capabilityConfigs .

זמן הריצה חייב להחזיר את הערך XR_ERROR_VALIDATION_FAILURE אם capability הוא לא XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID .

המזהה של ישויות שמתגלות באמצעות היכולת הזו הוא תמיד XR_NULL_SPATIAL_ENTITY_ID_EXT . זה גם אומר שהאפליקציה לא יכולה ליצור נקודת אחיזה מסוג XrSpatialEntityEXT לישויות האלה, ולכן אי אפשר לכלול אותן ב-XrSpatialUpdateSnapshotCreateInfoEXT :: entities כדי ליצור תמונת מצב של עדכון.

שימוש תקין (משתמע)

רכיבים מובטחים

סביבת זמן ריצה שתומכת ב-XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID חייבת לתמוך ברכיבים המרחביים הבאים כרכיבים מובטחים של הישויות שזוהו על ידי היכולת הזו, וחייבת למנות אותם ב-xrEnumerateSpatialCapabilityComponentTypesEXT –

  • XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID

Raycast סינכרוני

הפונקציה xrCreateSpatialRaycastSnapshotANDROID מוגדרת כך:

XrResult xrCreateSpatialRaycastSnapshotANDROID(
    XrSpatialContextEXT                         spatialContext,
    const XrSpatialRaycastSnapshotCreateInfoANDROID* createInfo,
    XrSpatialSnapshotEXT*                       snapshot);

תיאורי פרמטרים

הפונקציה xrCreateSpatialDiscoverySnapshotAsyncEXT מספיקה לרוב תרחישי השימוש, אבל היא נחשבת איטית לאפליקציות שדורשות תוצאות מיידיות של הטלת קרניים. הפונקציה xrCreateSpatialRaycastSnapshotANDROID מתחילה הטלת קרניים סינכרונית כדי ליצור תמונת מצב, וכך מאפשרת לאפליקציות להתחיל לשלוח שאילתות לגבי תוצאות של הטלת קרניים באופן מיידי.

סביבת זמן הריצה חייבת להחזיר את הערך XR_ERROR_SPATIAL_COMPONENT_NOT_ENABLED_EXT אם אחד מהערכים של XrSpatialComponentTypeEXT ב-XrSpatialRaycastSnapshotCreateInfoANDROID :: componentTypes לא מופעל ליכולות המרחביות שמועברות אל XrSpatialContextCreateInfoEXT :: capabilityConfigs כשיוצרים את spatialContext .

אם האפליקציה לא מספקת רשימה של סוגי רכיבים מרחביים ב-XrSpatialRaycastSnapshotCreateInfoANDROID :: componentTypes , זמן הריצה חייב לכלול את כל הישויות המרחביות בתמונת המצב שיש להן את קבוצת הרכיבים שמפורטים ב-XrSpatialCapabilityConfigurationBaseHeaderEXT ::enabledComponents ליכולות נתמכות של הטלת קרן שמוגדרות ל-spatialContext . סביבת זמן הריצה חייבת לכלול את הנתונים של כל הרכיבים המופעלים של היכולות הנתמכות של Raycast שהוגדרו עבור spatialContext .

שימוש תקין (משתמע)

קודי החזרה

הצלחה

  • XR_SUCCESS
  • XR_SESSION_LOSS_PENDING

נכשל

  • XR_ERROR_FUNCTION_UNSUPPORTED
  • XR_ERROR_HANDLE_INVALID
  • XR_ERROR_INSTANCE_LOST
  • XR_ERROR_LIMIT_REACHED
  • XR_ERROR_OUT_OF_MEMORY
  • XR_ERROR_RUNTIME_FAILURE
  • XR_ERROR_SESSION_LOST
  • XR_ERROR_SPATIAL_COMPONENT_NOT_ENABLED_EXT
  • XR_ERROR_TIME_INVALID
  • XR_ERROR_VALIDATION_FAILURE

המבנה של XrSpatialRaycastSnapshotCreateInfoANDROID מוגדר כך:

typedef struct XrSpatialRaycastSnapshotCreateInfoANDROID {
    XrStructureType                       type;
    const void*                           next;
    uint32_t                              componentTypeCount;
    const XrSpatialComponentTypeEXT*      componentTypes;
    const XrSpatialRaycastInfoANDROID*    raycastInfo;
} XrSpatialRaycastSnapshotCreateInfoANDROID;

תיאורי חברים

  • ‫type הוא ה-XrStructureType של המבנה הזה.
  • ‫next הוא NULL או מצביע למבנה הבא בשרשרת מבנים. מבנים כאלה לא מוגדרים ב-OpenXR או בתוסף הזה.
  • ‫componentTypeCount הוא uint32_t שמתאר את מספר הרכיבים במערך componentTypes.
  • ‫componentTypes הוא מערך של XrSpatialComponentTypeEXT .
  • ‫raycastInfo הוא המבנה של XrSpatialRaycastInfoANDROID שמתאר את המידע של קרן.

שימוש תקין (משתמע)

קוד לדוגמה

הגדרת יכולת מעקב אחר מישור ו-Raycast של עומק

הקוד לדוגמה הבא מדגים איך ליצור הקשר מרחבי עם יכולות שתומכות בפונקציונליות של Raycast. בדוגמה הזו, נעשה שימוש ב-XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID וב-XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT.

// Check runtime supported capabilities
uint32_t capabilityCount;
CHK_XR(xrEnumerateSpatialCapabilitiesEXT(instance, systemId, 0, &capabilityCount, nullptr));
std::vector<XrSpatialCapabilityEXT> capabilities(capabilityCount);
CHK_XR(xrEnumerateSpatialCapabilitiesEXT(instance, systemId, capabilityCount, &capabilityCount, capabilities.data()));

if (std::find(capabilities.begin(), capabilities.end(), XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID) == capabilities.end()) {
  return;
}

if (std::find(capabilities.begin(), capabilities.end(), XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT) == capabilities.end()) {
  return;
}

// Create capability config for depth raycasting
std::vector<XrSpatialComponentTypeEXT> depthRaycastComponents {
  XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID
};

// Create capability config for depth raycasting
XrSpatialCapabilityConfigurationDepthRaycastANDROID depthRaycastConfig {
  .type = XR_TYPE_SPATIAL_CAPABILITY_CONFIGURATION_DEPTH_RAYCAST_ANDROID,
  .next = nullptr,
  .capability = XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID,
  .enabledComponentCount = (uint32_t)depthRaycastComponents.size(),
  .enabledComponents = depthRaycastComponents.data(),
};

// Enumerate runtime supported components for plane tracking capability
XrSpatialCapabilityComponentTypesEXT capabilityComponentTypes {
  XR_TYPE_SPATIAL_CAPABILITY_COMPONENT_TYPES_EXT
};

bool isRaycastSupportedViaPlaneTracking;
std::vector<XrSpatialComponentTypeEXT> planeTrackingComponents {
  XR_SPATIAL_COMPONENT_TYPE_BOUNDED_2D_EXT,
  XR_SPATIAL_COMPONENT_TYPE_PLANE_ALIGNMENT_EXT,
};

CHK_XR(xrEnumerateSpatialCapabilityComponentTypesEXT(instance, systemId,
       XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT, &capabilityComponentTypes));

planeTrackingComponents.resize(capabilityComponentTypes.componentTypeCountOutput);
capabilityComponentTypes.componentTypeCapacityInput = (uint32_t)planeTrackingComponents.size();
capabilityComponentTypes.componentTypes = planeTrackingComponents.data();

CHK_XR(xrEnumerateSpatialCapabilityComponentTypesEXT(instance, systemId,
       XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT, &capabilityComponentTypes));

// Check if raycast is supported by plane tracking
isRaycastSupportedViaPlaneTracking = std::find(planeTrackingComponents.begin(),
planeTrackingComponents.end(), XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID)
!= planeTrackingComponents.end();

// Create capability config for plane tracking
XrSpatialCapabilityConfigurationPlaneTrackingEXT planeTrackingConfig {
  .type = XR_TYPE_SPATIAL_CAPABILITY_CONFIGURATION_PLANE_TRACKING_EXT,
  .next = nullptr,
  .capability = XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT,
  .enabledComponentCount = (uint32_t)planeTrackingComponents.size(),
  .enabledComponents = planeTrackingComponents.data(),
};

// Create spatial context
// Types of raycast is determined by configs included in XrSpatialContextCreateInfoEXT
// For this example, both plane raycast & depth raycast are performed
std::vector<const XrSpatialCapabilityConfigurationBaseHeaderEXT*> capabilityConfigs;
capabilityConfigs.push_back(reinterpret_cast<const XrSpatialCapabilityConfigurationBaseHeaderEXT*>(&depthRaycastConfig));
if(isRaycastSupportedViaPlaneTracking) capabilityConfigs.push_back(reinterpret_cast<const XrSpatialCapabilityConfigurationBaseHeaderEXT*>(&planeTrackingConfig));

XrSpatialContextCreateInfoEXT contextCreateInfo {
  .type = XR_TYPE_SPATIAL_CONTEXT_CREATE_INFO_EXT,
  .next = nullptr,
  .capabilityConfigCount = (uint32_t)capabilityConfigs.size(),
  .capabilityConfigs = capabilityConfigs.data(),
};

CHK_XR(xrCreateSpatialContextAsyncEXT(session, &contextCreateInfo, &future))

// Completes creating spatial context
XrCreateSpatialContextCompletionEXT contextCompletion{
XR_TYPE_CREATE_SPATIAL_CONTEXT_COMPLETION_EXT};

CHK_XR(xrCreateSpatialContextCompleteEXT(session, future, &contextCompletion))

חיפוש ישויות מרחביות ושאילתות על נתוני רכיבים

הקוד לדוגמה הבא מדגים איך לגלות ישויות מרחביות בהקשר שמוגדר עם XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID ו-XR_SPATIAL_CAPABILITY_PLANE_TRACKING_EXT, ולשלוח שאילתות לגבי נתוני הרכיבים שלו.

// Fill in the raycast info.
XrSpatialRaycastInfoANDROID raycastInfo {
  .type        = XR_TYPE_SPATIAL_RAYCAST_INFO_ANDROID,
  .next        = nullptr,
  .space       = viewSpace,
  .time        = updateTime,
  .origin      = {0.0f, 0.0f, 0.0f},
  .direction   = {0.0f, 0.0f,-1.0f},
  .maxDistance = 0.0f  // ray is unbounded
};

// Next pointing to the raycast info.
XrSpatialDiscoverySnapshotCreateInfoEXT discoverySnapshotCreateInfo {
  .type = XR_TYPE_SPATIAL_DISCOVERY_SNAPSHOT_CREATE_INFO_EXT,
  .next = &raycastInfo
};

// Create snapshot
CHK_XR(xrCreateSpatialDiscoverySnapshotAsyncEXT (
spatialContext, &discoverySnapshotCreateInfo, &future));

waitUntilReady(future);

// Complete async operation.
XrCreateSpatialDiscoverySnapshotCompletionInfoEXT
  createSnapshotCompletionInfo {
    .type      = XR_TYPE_CREATE_SPATIAL_DISCOVERY_SNAPSHOT_COMPLETION_INFO_EXT,
    .baseSpace = viewSpace,
    .time      = updateTime,
    .future    = future,
  };

XrCreateSpatialDiscoverySnapshotCompletionEXT completion {
  XR_TYPE_CREATE_SPATIAL_DISCOVERY_SNAPSHOT_COMPLETION_EXT};

CHK_XR(xrCreateSpatialDiscoverySnapshotCompleteEXT(
           spatialContext, &createSnapshotCompletionInfo,
           &completion));

if(completion.futureResult != XR_SUCCESS) return;

// Query hit result components
std::array<XrSpatialComponentTypeEXT, 1> enabledComponents = {
  XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID
};

XrSpatialComponentDataQueryConditionEXT queryCond {
  .type = XR_TYPE_SPATIAL_COMPONENT_DATA_QUERY_CONDITION_EXT,
  .componentTypeCount = 1,
  .componentTypes     = enabledComponents.data(),
};

XrSpatialComponentDataQueryResultEXT queryResult {
  .type = XR_TYPE_SPATIAL_COMPONENT_DATA_QUERY_RESULT_EXT,
};

XrResult result = xrQuerySpatialComponentDataEXT(
           completion.snapshot, &queryCond, &queryResult);

// Check query result.
if(result != XR_SUCCESS) return;

// Query again for the hit result list.
std::vector<XrSpatialRaycastResultDataANDROID> raycastResults;
raycastResults.resize(queryResult.entityIdCountOutput);
XrSpatialComponentRaycastResultListANDROID raycastResultList {
  .type               = XR_TYPE_SPATIAL_COMPONENT_RAYCAST_RESULT_LIST_ANDROID,
  .raycastResultCount = (uint32_t)raycastResults.size(),
  .raycastResults     = raycastResults.data(),
};

queryResult.next = &raycastResultList;
result = xrQuerySpatialComponentDataEXT(completion.snapshot, &queryCond, &queryResult);

// Check query result again.
if(result != XR_SUCCESS) return;

std::vector<XrSpatialEntityEXT> hitEntities;
std::vector<XrPosef> depthHitPoses;
for(uint32_t i = 0; i < queryResult.entityIdCountOutput; ++i) {
    // access raycastResults[i] for id & pose
    XrSpatialEntityIdEXT   id   = queryResult.entityIds[i];
    XrPosef                pose = raycastResults[i].hitPose;

    if (id != XR_NULL_SPATIAL_ENTITY_ID_EXT) {
        // hit entities (e.g. planes)
    // get entity handle via entity id
    XrSpatialEntityFromIdCreateInfoEXT entityCreateInfo {
      .type = XR_TYPE_SPATIAL_ENTITY_FROM_ID_CREATE_INFO_EXT,
      .entityId = id,
    };

    XrSpatialEntityEXT entity = XR_NULL_HANDLE;
    xrCreateSpatialEntityFromIdEXT(spatialContext, &entityCreateInfo, &entity);

    hitEntities.push_back(entity);
  } else {
    // hit depth
    depthHitPoses.push_back(pose);
  }
}

// Cleanup
xrDestroySpatialSnapshotEXT(completion.snapshot);

יצירת תמונת מצב של Raycast

הקוד לדוגמה הבא מדגים איך ליצור תמונת מצב סינכרונית של Raycast.

// fill in create info
XrSpatialRaycastSnapshotCreateInfoANDROID createInfo {
  .type = XR_TYPE_SPATIAL_RAYCAST_SNAPSHOT_CREATE_INFO_ANDROID,
  .componentTypeCount = 0,   // include all hit spatial entities
  .componentTypes = nullptr,
  .raycastInfo = &raycastInfo
};

// create raycast snapshot
XrSpatialSnapshotEXT raycastSnapshot = XR_NULL_HANDLE;
CHK_XR(xrCreateSpatialRaycastSnapshotANDROID(
  spatialContext, &createInfo, &raycastSnapshot));

// ...
// query component data as previous example
// ...

// Cleanup
xrDestroySpatialSnapshotEXT(raycastSnapshot);

פקודות חדשות

מבנים חדשים

קבועי Enum חדשים

  • XR_ANDROID_SPATIAL_DISCOVERY_RAYCAST_EXTENSION_NAME
  • XR_ANDROID_spatial_discovery_raycast_SPEC_VERSION
  • הרחבה של XrSpatialCapabilityEXT :

    • XR_SPATIAL_CAPABILITY_DEPTH_RAYCAST_ANDROID
  • הרחבה של XrSpatialComponentTypeEXT :

    • XR_SPATIAL_COMPONENT_TYPE_RAYCAST_RESULT_ANDROID
  • הרחבה של XrStructureType :

    • XR_TYPE_SPATIAL_CAPABILITY_CONFIGURATION_DEPTH_RAYCAST_ANDROID
    • XR_TYPE_SPATIAL_COMPONENT_RAYCAST_RESULT_LIST_ANDROID
    • XR_TYPE_SPATIAL_RAYCAST_INFO_ANDROID
    • XR_TYPE_SPATIAL_RAYCAST_SNAPSHOT_CREATE_INFO_ANDROID

בעיות

היסטוריית הגרסאות

  • גרסה 1, 15.07.2025 (בריאן צ'ן)

    • תיאור התוסף הראשוני.