1// Copyright 2018-2023 The Khronos Group Inc. 2// 3// SPDX-License-Identifier: CC-BY-4.0 4 5[[ray-traversal]] 6= Ray Traversal 7 8The ray traversal process identifies and handles intersections between a ray 9and geometries in an acceleration structure. 10 11Ray traversal cannot be started by a Vulkan API command directly - a shader 12must execute 13ifdef::VK_KHR_ray_query[code:OpRayQueryProceedKHR] 14ifdef::VK_KHR_ray_query+VK_KHR_ray_tracing_pipeline[or] 15ifdef::VK_KHR_ray_tracing_pipeline[code:OpTraceRayKHR] 16. 17ifdef::VK_KHR_ray_tracing_pipeline[] 18When the <<features-rayTracingPipeline, pname:rayTracingPipeline>> feature 19is enabled, code:OpTraceRayKHR can: be used for <<ray-tracing, ray tracing>> 20in a <<pipelines-ray-tracing, ray tracing pipeline>>. 21endif::VK_KHR_ray_tracing_pipeline[] 22ifdef::VK_KHR_ray_query[] 23When the <<features-rayQuery, pname:rayQuery>> feature is enabled, 24code:OpRayQueryProceedKHR can: be used in any shader stage. 25endif::VK_KHR_ray_query[] 26 27 28[[ray-intersection-candidate-determination]] 29== Ray Intersection Candidate Determination 30 31Once tracing begins, rays are first tested against instances in a top-level 32acceleration structure. 33A ray that intersects an instance will be transformed into the space of the 34instance to continue traversal within that instance; therefore the transform 35matrix stored in the instance must be invertible. 36 37In case multiple instances are intersected by a ray, the ray transformation 38into the space of the instance is invariant under the order in which these 39instances are encountered in the top-level acceleration structure. 40 41[NOTE] 42.Note 43==== 44Applying multiple forward and reverse transforms to a ray to transition from 45one instance to another could result in accumulated errors. 46Thus an implementation should behave as if the ray is transformed from the 47origin for each instance independently. 48==== 49 50Next, rays are tested against geometries in an bottom-level acceleration 51structure to determine if a hit occurred between them, initially based only 52on their geometric properties (i.e. their vertices). 53The implementation performs similar operations to that of rasterization, but 54with the effective viewport determined by the parameters of the ray, and the 55geometry transformed into a space determined by that viewport. 56 57The vertices of each primitive are transformed from acceleration structure 58space #~as~# to ray space #~r~# according to the ray origin and direction as 59follows: 60 61[latexmath] 62++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 63\left( 64 \begin{array}{c} 65 x_{r} \\ 66 y_{r}\\ 67 z_{r} 68 \end{array} 69\right) = 70\left( 71 \begin{matrix} 72 a_x^2(1-c) + c & a_xa_y(1-c) - sa_z & a_xa_z(1-c) + sa_y \\ 73 a_xa_y(1-c) + sa_z & a_y^2(1-c) + c & a_ya_z(1-c) - sa_x \\ 74 a_xa_z(1-c) - sa_y & a_ya_z(1-c) + sa_x & a_z^2(1-c) + c 75 \end{matrix} 76\right) 77\left( 78 \begin{array}{c} 79 x_{as} - o_x \\ 80 y_{as} - o_y \\ 81 z_{as} - o_z 82 \end{array} 83\right) 84++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 85 86latexmath:[\mathbf{a}] is the axis of rotation from the unnormalized ray 87direction vector latexmath:[\mathbf{d}] to the axis vector 88latexmath:[\mathbf{k}]: 89 90[latexmath] 91++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 92\mathbf{a} = \begin{cases} 93 \frac{\mathbf{d} \times \mathbf{k}}{|| \mathbf{d} \times \mathbf{k} ||} & \mathrm{if}\; || \mathbf{d} \times \mathbf{k} || \ne 0 \\ 94 \left(\begin{array}{c} 95 0 \\ 96 1 \\ 97 0 98 \end{array} 99 \right) & \mathrm{if}\; || \mathbf{d} \times \mathbf{k} || = 0 \\ 100 \end{cases} 101++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 102 103latexmath:[\mathit{s}] and latexmath:[\mathit{c}] are the sine and cosine of 104the angle of rotation about latexmath:[\mathbf{a}] from 105latexmath:[\mathbf{d}] to latexmath:[\mathbf{k}]: 106 107[latexmath] 108++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 109\begin{aligned} 110c &= {{\mathbf{d} \cdot \mathbf{k}}\over{||\mathbf{d}||}} \\ 111s &= \sqrt{1 - c^2} 112\end{aligned} 113++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 114 115latexmath:[\mathbf{k}] is the unit vector: 116 117[latexmath] 118++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 119\mathbf{k} = \left( 120 \begin{array}{c} 121 0 \\ 122 0 \\ 123 -1 124 \end{array} 125\right) 126++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 127 128latexmath:[\mathbf{o}] and latexmath:[\mathbf{d}] are the ray origin and 129unnormalized direction, respectively; the vector described by [eq]#x~as~#, 130[eq]#y~as~#, and [eq]#z~as~# is any position in acceleration structure 131space; and the vector described by [eq]#x~r~#, [eq]#y~r~#, and [eq]#z~r~# is 132the same position in ray space. 133 134An _intersection candidate_ is a unique point of intersection between a ray 135and a geometric primitive. 136For any primitive that has within its bounds a position 137latexmath:[\mathbf{xyz_{as}}] such that 138 139[latexmath] 140++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 141\begin{aligned} 142 x_r &= 0 \\ 143 y_r &= 0 \\ 144t_\mathit{min} \lt {-{z_r}\over{||\mathbf{d}||}} &\lt t_\mathit{max} & \text{if the primitive is a triangle,} \\ 145t_\mathit{min} \leq {-{z_r}\over{||\mathbf{d}||}} &\leq t_\mathit{max} & \text{otherwise} \\ 146\end{aligned} 147++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 148 149(where latexmath:[t = {-{z_r}\over{||\mathbf{d}||}}]), an intersection 150candidate exists. 151 152Triangle primitive bounds consist of all points on the plane formed by the 153three vertices and within the bounds of the edges between the vertices, 154subject to the watertightness constraints below. 155AABB primitive bounds consist of all points within an implementation-defined 156bound which includes the specified box. 157 158[NOTE] 159.Note 160==== 161The bounds of the AABB including all points internal to the bound implies 162that a ray started within the AABB will hit that AABB. 163==== 164 165[[raytraversal-ray-intersection-candidate-diagram]] 166image::{images}/ray_intersection_candidate.svg[align="center",title="Ray intersection candidate",opts="{imageopts}"] 167 168The determination of this condition is performed in an implementation 169specific manner, and may: be performed with floating point operations. 170Due to the complexity and number of operations involved, inaccuracies are 171expected, particularly as the scale of values involved begins to diverge. 172Implementations should: take efforts to maintain as much precision as 173possible. 174 175[NOTE] 176.Note 177==== 178One very common case is when geometries are close to each other at some 179distance from the origin in acceleration structure space, where an effect 180similar to "`z-fighting`" is likely to be observed. 181Applications can mitigate this by ensuring their detailed geometries remain 182close to the origin. 183 184Another likely case is when the origin of a ray is set to a position on a 185previously intersected surface, and its [eq]#t~min~# is zero or near zero; 186an intersection may be detected on the emitting surface. 187This case can usually be mitigated by offsetting [eq]#t~min~# slightly. 188==== 189 190ifdef::VK_NV_ray_tracing_motion_blur[] 191For a motion primitive or a motion instance, the positions for intersection 192are evaluated at the time specified in the code:time parameter to 193code:OpTraceRayMotionNV by interpolating between the two endpoints as 194specified for the given motion type. 195If a motion acceleration structure is traced with code:OpTraceRayKHR, it 196behaves as a code:OpTraceRayMotionNV with code:time of 0.0. 197endif::VK_NV_ray_tracing_motion_blur[] 198 199In the case of AABB geometries, implementations may: increase their size in 200an acceleration structure in order to mitigate precision issues. 201This may: result in false positive intersections being reported to the 202application. 203 204For triangle intersection candidates, the [eq]#b# and [eq]#c# 205<<primsrast-polygon-barycentrics,barycentric coordinates>> on the triangle 206where the above condition is met are made available to future shading. 207ifdef::VK_KHR_ray_tracing_pipeline[] 208If the ray was traced with code:OpTraceRayKHR, these values are available as 209a vector of 2 32-bit floating point values in the code:HitAttributeKHR 210storage class. 211endif::VK_KHR_ray_tracing_pipeline[] 212 213Once an intersection candidate is determined, it proceeds through the 214following operations, in order: 215 216 . <<ray-intersection-culling>> 217 . <<ray-intersection-confirmation>> 218 . <<ray-closest-hit-determination>> 219 . <<ray-result-determination>> 220 221The sections below describe the exact details of these tests. 222There is no ordering guarantee between operations performed on different 223intersection candidates. 224 225 226[[ray-traversal-watertight]] 227=== Watertightness 228 229For a set of triangles with identical transforms, within a single instance: 230 231 * Any set of two or more triangles where all triangles have one vertex 232 with an identical position value, that vertex is a _shared vertex_. 233 * Any set of two triangles with two shared vertices that were specified in 234 the same <<drawing-triangle-lists, winding order>> in each triangle have 235 a _shared edge_ defined by those vertices. 236 237A _closed fan_ is a set of three or more triangles where: 238 239 * All triangles in the set have the same shared vertex as one of their 240 vertices. 241 * All edges that include the above vertex are shared edges. 242 * All above shared edges are shared by exactly two triangles from the set. 243 * No two triangles in the set intersect, except at shared edges. 244 * Every triangle in the set is joined to every other triangle in the set 245 by a series of the above shared edges. 246 247Implementations should: not double-hit or miss when a ray intersects a 248shared edge, or a shared vertex of a closed fan. 249 250 251[[ray-intersection-culling]] 252== Ray Intersection Culling 253 254Candidate intersections go through several phases of culling before 255confirmation as an actual hit. 256There is no particular ordering dependency between the different culling 257operations. 258 259 260[[ray-traversal-culling-primitive]] 261=== Ray Primitive Culling 262 263If the <<features-rayTraversalPrimitiveCulling, 264pname:rayTraversalPrimitiveCulling>> or <<features-rayQuery, 265pname:rayQuery>> features are enabled, the code:SkipTrianglesKHR and 266code:SkipAABBsKHR ray flags can: be specified when tracing a ray. 267code:SkipTrianglesKHR and code:SkipAABBsKHR are mutually exclusive. 268code:SkipTrianglesKHR is also mutually exclusive with 269code:CullBackFacingTrianglesKHR and code:CullFrontFacingTrianglesKHR. 270 271If code:SkipTrianglesKHR was included in the `Ray Flags` operand of the ray 272trace instruction, and the intersection is with a triangle primitive, the 273intersection is dropped, and no further processing of this intersection 274occurs. 275If ename:VK_PIPELINE_CREATE_RAY_TRACING_SKIP_TRIANGLES_BIT_KHR was included 276in the pipeline, traversal with code:OpTraceRayKHR calls will all behave as 277if code:SkipTrianglesKHR was included in its `Ray Flags` operand. 278 279If code:SkipAABBsKHR was included in the `Ray Flags` operand of the ray 280trace instruction, and the intersection is with an AABB primitive, the 281intersection is dropped, and no further processing of this intersection 282occurs. 283If ename:VK_PIPELINE_CREATE_RAY_TRACING_SKIP_AABBS_BIT_KHR was included in 284the pipeline, traversal with code:OpTraceRayKHR calls will all behave as if 285code:SkipAABBsKHR was included in its `Ray Flags` operand. 286 287 288=== Ray Mask Culling 289 290Instances can: be made invisible to particular rays based on the value of 291slink:VkAccelerationStructureInstanceKHR::pname:mask used to add that 292instance to a top-level acceleration structure, and the `Cull Mask` 293parameter used to trace the ray. 294 295For the instance which is intersected, if [eq]#pname:mask & `Cull Mask` == 2960#, the intersection is dropped, and no further processing occurs. 297 298 299[[ray-traversal-culling-face]] 300=== Ray Face Culling 301 302As in <<primsrast-polygons-basic,polygon rasterization>>, one of the stages 303of ray traversal is to determine if a triangle primitive is back- or 304front-facing, and primitives can: be culled based on that facing. 305 306If the intersection candidate is with an AABB primitive, this operation is 307skipped. 308 309.Determination 310 311When a ray intersects a triangle primitive, the order that vertices are 312specified for the polygon affects whether the ray intersects the front or 313back face. 314Front or back facing is determined in the same way as they are for 315<<primsrast-polygons-basic,rasterization>>, based on the sign of the 316polygon's area but using the ray space coordinates instead of framebuffer 317coordinates. 318One way to compute this area is: 319 320[latexmath] 321++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 322a = -{1 \over 2}\sum_{i=0}^{n-1} 323 x_r^i y_r^{i \oplus 1} - 324 x_r^{i \oplus 1} y_r^i 325++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 326 327where latexmath:[x_r^i] and latexmath:[y_r^i] are the [eq]#x# and [eq]#y# 328<<ray-intersection-candidate-determination,ray space coordinates>> of the 329[eq]##i##th vertex of the [eq]#n#-vertex polygon (vertices are numbered 330starting at zero for the purposes of this computation) and [eq]#i {oplus} 1# 331is [eq]#(i {plus} 1) mod n#. 332 333By default, if [eq]#a# is negative then the intersection is with the front 334face of the triangle, otherwise it is with the back face. 335If ename:VK_GEOMETRY_INSTANCE_TRIANGLE_FLIP_FACING_BIT_KHR is included in 336slink:VkAccelerationStructureInstanceKHR::pname:flags for the instance 337containing the intersected triangle, this determination is reversed. 338Additionally, if [eq]#a# is 0, the intersection candidate is treated as not 339intersecting with any face, irrespective of the sign. 340 341[NOTE] 342.Note 343==== 344In a left-handed coordinate system, an intersection will be with the front 345face of a triangle if the vertices of the triangle, as defined in index 346order, appear from the ray's perspective in a clockwise rotation order. 347ename:VK_GEOMETRY_INSTANCE_TRIANGLE_FLIP_FACING_BIT_KHR was previously 348annotated as 349ename:VK_GEOMETRY_INSTANCE_TRIANGLE_FRONT_COUNTERCLOCKWISE_BIT_KHR because 350of this. 351==== 352 353ifdef::VK_KHR_ray_tracing_pipeline[] 354If the ray was traced with code:OpTraceRayKHR, the code:HitKindKHR built-in 355is set to code:HitKindFrontFacingTriangleKHR if the intersection is with 356front-facing geometry, and code:HitKindBackFacingTriangleKHR if the 357intersection is with back-facing geometry, for shader stages considering 358this intersection. 359endif::VK_KHR_ray_tracing_pipeline[] 360 361ifdef::VK_KHR_ray_query[] 362If the ray was traced with code:OpRayQueryProceedKHR, 363code:OpRayQueryGetIntersectionFrontFaceKHR will return true for intersection 364candidates with front faces, or false for back faces. 365endif::VK_KHR_ray_query[] 366 367.Culling 368 369If code:CullBackFacingTrianglesKHR was included in the `Ray Flags` parameter 370of the ray trace instruction, and the intersection is determined as with the 371back face of a triangle primitive, the intersection is dropped, and no 372further processing of this intersection occurs. 373 374If code:CullFrontFacingTrianglesKHR was included in the `Ray Flags` 375parameter of the ray trace instruction, and the intersection is determined 376as with the front face of a triangle primitive, the intersection is dropped, 377and no further processing of this intersection occurs. 378 379This culling is disabled if 380ename:VK_GEOMETRY_INSTANCE_TRIANGLE_FACING_CULL_DISABLE_BIT_KHR was included 381in slink:VkAccelerationStructureInstanceKHR::pname:flags for the instance 382which the intersected geometry belongs to. 383 384Intersection candidates that have not intersected with any face ([eq]#a == 3850#) are unconditionally culled, irrespective of ray flags and geometry 386instance flags. 387 388The code:CullBackFacingTrianglesKHR and code:CullFrontFacingTrianglesKHR 389`Ray Flags` are mutually exclusive. 390 391 392=== Ray Opacity Culling 393 394Each geometry in the acceleration structure may: be considered either opaque 395or not. 396Opaque geometries continue through traversal as normal, whereas non-opaque 397geometries need to be either confirmed or discarded by shader code. 398Intersection candidates can: also be culled based on their opacity. 399 400.Determination 401 402Each individual intersection candidate is initially determined as opaque if 403ename:VK_GEOMETRY_OPAQUE_BIT_KHR was included in the 404slink:VkAccelerationStructureGeometryKHR::pname:flags when the geometry it 405intersected with was built, otherwise it is considered non-opaque. 406 407ifdef::VK_EXT_opacity_micromap[] 408If the geometry includes an opacity micromap, the opacity of the 409intersection at this point is instead derived as described in 410<<ray-opacity-micromap,Ray Opacity Micromap>>. 411endif::VK_EXT_opacity_micromap[] 412 413ifdef::VK_KHR_ray_tracing_pipeline[] 414If the intersection candidate was generated by an <<shaders-intersection, 415intersection shader>>, the intersection is initially considered to have 416opacity matching the AABB candidate that it was generated from. 417endif::VK_KHR_ray_tracing_pipeline[] 418 419However, this opacity can be overridden when it is built into an instance. 420Setting ename:VK_GEOMETRY_INSTANCE_FORCE_OPAQUE_BIT_KHR in 421slink:VkAccelerationStructureInstanceKHR::pname:flags will force all 422geometries in the instance to be considered opaque. 423Similarly, setting ename:VK_GEOMETRY_INSTANCE_FORCE_NO_OPAQUE_BIT_KHR will 424force all geometries in the instance to be considered non-opaque. 425 426This can again be overridden by including code:OpaqueKHR or code:NoOpaqueKHR 427in the `Ray Flags` parameter when tracing a ray. 428code:OpaqueKHR forces all geometries to behave as if they are opaque, 429regardless of their build parameters. 430Similarly, code:NoOpaqueKHR forces all geometries to behave as if they are 431non-opaque. 432 433ifdef::VK_KHR_ray_query[] 434If the ray was traced with code:OpRayQueryProceedKHR, to determine the 435opacity of AABB intersection candidates, 436code:OpRayQueryGetIntersectionCandidateAABBOpaqueKHR can: be used. 437This instruction will return code:true for opaque intersection candidates, 438and code:false for non-opaque intersection candidates. 439endif::VK_KHR_ray_query[] 440 441.Culling 442 443If code:CullOpaqueKHR is included in the `Ray Flags` parameter when tracing 444a ray, an intersection with a geometry that is considered opaque is dropped, 445and no further processing occurs. 446 447If code:CullNoOpaqueKHR is included in the `Ray Flags` parameter when 448tracing a ray, an intersection with a geometry that is considered non-opaque 449is dropped, and no further processing occurs. 450 451The code:OpaqueKHR, code:NoOpaqueKHR, code:CullOpaqueKHR, and 452code:CullNoOpaqueKHR `Ray Flags` are mutually exclusive. 453 454ifdef::VK_EXT_opacity_micromap[] 455[[ray-opacity-micromap]] 456=== Ray Opacity Micromap 457 458A ename:VK_GEOMETRY_TYPE_TRIANGLES_KHR geometry in the acceleration 459structure may: have an opacity micromap associated with it to give 460finer-grained opacity information. 461 462If the intersection candidate is with a geometry with an associated opacity 463micromap and ename:VK_GEOMETRY_INSTANCE_DISABLE_OPACITY_MICROMAPS_EXT is not 464set in its instance then the micromap is used to determine geometry opacity 465instead of the ename:VK_GEOMETRY_OPAQUE_BIT_KHR flag in the geometry. 466 467The opacity information in the micromap object is accessed using the 468candidate intersection [eq]#u# and [eq]#v# coordinates. 469The integer [eq]#u# and [eq]#v# are computed from [eq]#{lfloor}u{rfloor} 470{plus} {lfloor}v{rfloor}#, clamping [eq]#{lfloor}u{rfloor}# as needed to 471keep the sum less than or equal to [eq]#1 << subdivisionlevel#. 472These values are mapped into a linear index with a space filling curve which 473is defined recursively by traversing into the sub-triangle nearest vertex 0, 474then the middle triangle with ordering flipped, then nearest vertex 1 then 475nearest vertex 2. 476 477image::{images}/micromap-subd.svg[align="center",title="Example ordering for micromap data",align="center",opts="{imageopts}"] 478 479[NOTE] 480.Note 481==== 482This encoding is spatially coherent, purely hierarchical, and allows a 483bit-parallel conversion between barycentric address and index values. 484 485See the appendix for reference code implementing this mapping. 486==== 487 488The result of the opacity micromap lookup and operations is to treat the 489intersection as opaque, non-opaque, or ignored. 490The interpretation of the values depends on 491ename:VK_GEOMETRY_INSTANCE_FORCE_OPACITY_MICROMAP_2_STATE_EXT in the 492instance of the candidate intersection or 493ename:ForceOpacityMicromap2StateEXT ray flags on the ray. 494If either is set, the opacity micromap information is interpreted in 2 state 495override mode. 496If the result of the micromap lookup is to treat the intersection candidate 497as ignored, no further processing of that candidate is done. 498 499If the associated opacity micromap has format 500ename:VK_OPACITY_MICROMAP_FORMAT_2_STATE_EXT, each element of the micromap 501is represented by a single bit at the index derived above. 502 503If the associated opacity micromap has format 504ename:VK_OPACITY_MICROMAP_FORMAT_4_STATE_EXT, each element is represented by 505a two bit value at the index derived above. 506 507 508[options="header"] 509|==== 510| 4 State value | 2 State value | Special index value | 2 State override | Result 511| 0 | 0 | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_TRANSPARENT_EXT | Y | Ignored 512| 0 | 0 | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_TRANSPARENT_EXT | N | Ignored 513| 1 | 1 | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_OPAQUE_EXT | Y | Opaque 514| 1 | 1 | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_OPAQUE_EXT | N | Opaque 515| 2 | | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_UNKNOWN_TRANSPARENT_EXT | Y | Ignored 516| 2 | | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_UNKNOWN_TRANSPARENT_EXT | N | Non-opaque 517| 3 | | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_UNKNOWN_OPAQUE_EXT | Y | Opaque 518| 3 | | ename:VK_OPACITY_MICROMAP_SPECIAL_INDEX_FULLY_UNKNOWN_OPAQUE_EXT | N | Non-opaque 519|==== 520 521 522endif::VK_EXT_opacity_micromap[] 523 524 525[[ray-intersection-confirmation]] 526== Ray Intersection Confirmation 527 528Depending on the opacity of intersected geometry and whether it is a 529triangle or an AABB, candidate intersections are further processed to 530determine the eventual hit result. 531Candidates generated from AABB intersections run through the same 532confirmation process as triangle hits. 533 534 535=== AABB Intersection Candidates 536 537For an intersection candidate with an AABB geometry generated by 538<<ray-intersection-candidate-determination>>, shader code is executed to 539determine whether any hits should be reported to the traversal 540infrastructure; no further processing of this intersection candidate occurs. 541The occurrence of an AABB intersection candidate does not guarantee the ray 542intersects the primitive bounds. 543To avoid propagating false intersections the application should: verify the 544intersection candidate before reporting any hits. 545 546ifdef::VK_KHR_ray_tracing_pipeline[] 547If the ray was traced with code:OpTraceRayKHR, an <<shaders-intersection, 548intersection shader>> is invoked from the <<shader-binding-table>> according 549to the <<shader-binding-table-indexing-rules, specified indexing>> for the 550intersected geometry. 551If this shader calls code:OpReportIntersectionKHR, a new intersection 552candidate is generated as described 553<<aabb-intersection-candidate-generation, below>>. 554If the intersection shader is ename:VK_SHADER_UNUSED_KHR (which is only 555allowed for a zero shader group) then no further processing of the 556intersection candidate occurs. 557endif::VK_KHR_ray_tracing_pipeline[] 558 559[[aabb-intersection-candidate-generation]] 560ifdef::VK_KHR_ray_tracing_pipeline[] 561Each new candidate generated as a result of this processing is a generated 562intersection candidate that intersects the AABB geometry, with a [eq]#t# 563value equal to the `Hit` parameter of the code:OpReportIntersectionKHR 564instruction. 565The new generated candidate is then independently run through 566<<ray-intersection-confirmation>> as a 567<<ray-triangle-and-generated-intersection-candidates, generated 568intersection>>. 569endif::VK_KHR_ray_tracing_pipeline[] 570 571ifdef::VK_KHR_ray_query[] 572If the ray was traced with code:OpRayQueryProceedKHR, control is returned to 573the shader which executed code:OpRayQueryProceedKHR, returning code:true. 574The resulting ray query has a candidate intersection type of 575code:RayQueryCandidateIntersectionAABBKHR. 576code:OpRayQueryGenerateIntersectionKHR can: be called to commit a new 577intersection candidate with committed intersection type of 578code:RayQueryCommittedIntersectionGeneratedKHR. 579Further ray query processing can: be continued by executing 580code:OpRayQueryProceedKHR with the same ray query, or intersection can: be 581terminated with code:OpRayQueryTerminateKHR. 582endif::VK_KHR_ray_query[] 583ifdef::VK_KHR_ray_tracing_pipeline+VK_KHR_ray_query[] 584Unlike rays traced with code:OpTraceRayKHR, candidates generated in this way 585skip generated intersection candidate confirmation; applications should: 586make this determination before generating the intersection. 587endif::VK_KHR_ray_tracing_pipeline+VK_KHR_ray_query[] 588 589This operation may: be executed multiple times for the same intersection 590candidate. 591 592 593[[ray-triangle-and-generated-intersection-candidates]] 594=== Triangle and Generated Intersection Candidates 595 596For triangle and <<aabb-intersection-candidate-generation, generated 597intersection candidates>>, additional shader code may: be executed based on 598the intersection's opacity. 599 600If the intersection is opaque, the candidate is immediately confirmed as a 601valid hit and passes to the next stage of processing. 602 603For non-opaque intersection candidates, shader code is executed to determine 604whether a hit occurred or not. 605 606ifdef::VK_KHR_ray_tracing_pipeline[] 607If the ray was traced with code:OpTraceRayKHR, an <<shaders-any-hit, any-hit 608shader>> is invoked from the <<shader-binding-table>> according to the 609specified indexing. 610If this shader calls code:OpIgnoreIntersectionKHR, the candidate is dropped 611and no further processing of the candidate occurs. 612If the <<shaders-any-hit, any-hit shader>> identified is 613ename:VK_SHADER_UNUSED_KHR, the candidate is immediately confirmed as a 614valid hit and passes to the next stage of processing. 615endif::VK_KHR_ray_tracing_pipeline[] 616 617ifdef::VK_KHR_ray_query[] 618If the ray was traced with code:OpRayQueryProceedKHR, control is returned to 619the shader which executed code:OpRayQueryProceedKHR, returning code:true. 620As only triangle candidates participate in this operation with ray queries, 621the resulting candidate intersection type is always 622code:RayQueryCandidateIntersectionTriangleKHR. 623code:OpRayQueryConfirmIntersectionKHR can: be called on the ray query to 624confirm the candidate as a hit with committed intersection type of 625code:RayQueryCommittedIntersectionTriangleKHR. 626Further ray query processing can: be continued by executing 627code:OpRayQueryProceedKHR with the same ray query, or intersection can: be 628terminated with code:OpRayQueryTerminateKHR. 629If code:OpRayQueryConfirmIntersectionKHR has not been executed, the 630candidate is dropped and no further processing of the candidate occurs. 631endif::VK_KHR_ray_query[] 632 633This operation may: be executed multiple times for the same intersection 634candidate unless ename:VK_GEOMETRY_NO_DUPLICATE_ANY_HIT_INVOCATION_BIT_KHR 635was specified for the intersected geometry. 636 637 638[[ray-closest-hit-determination]] 639== Ray Closest Hit Determination 640 641Unless the ray was traced with the code:TerminateOnFirstHitKHR ray flag, the 642implementation must: track the closest confirmed hit until all geometries 643have been tested and either confirmed or dropped. 644 645After an intersection candidate is confirmed, its [eq]#t# value is compared 646to [eq]#t~max~# to determine which intersection is closer, where [eq]#t# is 647the parametric distance along the ray at which the intersection occurred. 648 649 * If [eq]#t < t~max~#, [eq]#t~max~# is set to [eq]#t# and the candidate is 650 set as the current closest hit. 651 * If [eq]#t > t~max~#, the candidate is dropped and no further processing 652 of that candidate occurs. 653 * If [eq]#t = t~max~#, the candidate may: be set as the current closest 654 hit or dropped. 655 656If code:TerminateOnFirstHitKHR was included in the `Ray Flags` used to trace 657the ray, once the first hit is confirmed, the ray trace is terminated. 658 659 660[[ray-result-determination]] 661== Ray Result Determination 662 663Once all candidates have finished processing the prior stages, or if the ray 664is forcibly terminated, the final result of the ray trace is determined. 665 666If a closest hit result was identified by <<ray-closest-hit-determination>>, 667a closest hit has occurred, otherwise the final result is a miss. 668 669ifdef::VK_KHR_ray_tracing_pipeline[] 670For rays traced with code:OpTraceRayKHR, if a closest hit result was 671identified, a <<shaders-closest-hit, closest hit shader>> is invoked from 672the <<shader-binding-table>> according to the 673<<shader-binding-table-indexing-rules, specified indexing>> for the 674intersected geometry. 675Control returns to the shader that executed code:OpTraceRayKHR once this 676shader returns. 677This shader is skipped if either the ray flags included 678code:SkipClosestHitShaderKHR, or if the <<shaders-closest-hit, closest hit 679shader>> identified is ename:VK_SHADER_UNUSED_KHR. 680 681For rays traced with code:OpTraceRayKHR where no hit result was identified, 682the <<shaders-miss, miss shader>> identified by the `Miss Index` parameter 683of code:OpTraceRayKHR is invoked. 684Control returns to the shader that executed code:OpTraceRayKHR once this 685shader returns. 686This shader is skipped if the miss shader identified is 687ename:VK_SHADER_UNUSED_KHR. 688endif::VK_KHR_ray_tracing_pipeline[] 689 690ifdef::VK_KHR_ray_query[] 691If the ray was traced with code:OpRayQueryProceedKHR, control is returned to 692the shader which executed code:OpRayQueryProceedKHR, returning code:false. 693If a closest hit was identified by <<ray-closest-hit-determination>>, the 694ray query will now have a committed intersection type of 695code:RayQueryCommittedIntersectionGeneratedKHR or 696code:RayQueryCommittedIntersectionTriangleKHR. 697If no closest hit was identified, the committed intersection type will be 698code:RayQueryCommittedIntersectionNoneKHR. 699 700No further processing of a ray query occurs after this result is determined. 701endif::VK_KHR_ray_query[] 702