trianglev_intersector.h 8.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207
  1. // Copyright 2009-2021 Intel Corporation
  2. // SPDX-License-Identifier: Apache-2.0
  3. #pragma once
  4. #include "triangle.h"
  5. #include "triangle_intersector_pluecker.h"
  6. #include "triangle_intersector_moeller.h"
  7. #include "triangle_intersector_woop.h"
  8. namespace embree
  9. {
  10. namespace isa
  11. {
  12. /*! Intersects M triangles with 1 ray */
  13. template<int M, bool filter>
  14. struct TriangleMvIntersector1Moeller
  15. {
  16. typedef TriangleMv<M> Primitive;
  17. typedef MoellerTrumboreIntersector1<M> Precalculations;
  18. /*! Intersect a ray with M triangles and updates the hit. */
  19. static __forceinline void intersect(Precalculations& pre, RayHit& ray, IntersectContext* context, const Primitive& tri)
  20. {
  21. STAT3(normal.trav_prims,1,1,1);
  22. pre.intersect(ray,tri.v0,tri.v1,tri.v2,/*UVIdentity<M>(),*/Intersect1EpilogM<M,filter>(ray,context,tri.geomID(),tri.primID()));
  23. }
  24. /*! Test if the ray is occluded by one of the M triangles. */
  25. static __forceinline bool occluded(const Precalculations& pre, Ray& ray, IntersectContext* context, const Primitive& tri)
  26. {
  27. STAT3(shadow.trav_prims,1,1,1);
  28. return pre.intersect(ray,tri.v0,tri.v1,tri.v2,/*UVIdentity<M>(),*/Occluded1EpilogM<M,filter>(ray,context,tri.geomID(),tri.primID()));
  29. }
  30. static __forceinline bool pointQuery(PointQuery* query, PointQueryContext* context, const Primitive& tri)
  31. {
  32. return PrimitivePointQuery1<Primitive>::pointQuery(query, context, tri);
  33. }
  34. };
  35. template<int M, bool filter>
  36. struct TriangleMvIntersector1Woop
  37. {
  38. typedef TriangleMv<M> Primitive;
  39. typedef WoopIntersector1<M> intersec;
  40. typedef WoopPrecalculations1<M> Precalculations;
  41. /*! Intersect a ray with M triangles and updates the hit. */
  42. static __forceinline void intersect(const Precalculations& pre, RayHit& ray, IntersectContext* context, const Primitive& tri)
  43. {
  44. STAT3(normal.trav_prims,1,1,1);
  45. intersec::intersect(ray,pre,tri.v0,tri.v1,tri.v2,Intersect1EpilogM<M,filter>(ray,context,tri.geomID(),tri.primID()));
  46. }
  47. /*! Test if the ray is occluded by one of the M triangles. */
  48. static __forceinline bool occluded(const Precalculations& pre, Ray& ray, IntersectContext* context, const Primitive& tri)
  49. {
  50. STAT3(shadow.trav_prims,1,1,1);
  51. return intersec::intersect(ray,pre,tri.v0,tri.v1,tri.v2,Occluded1EpilogM<M,filter>(ray,context,tri.geomID(),tri.primID()));
  52. }
  53. static __forceinline bool pointQuery(PointQuery* query, PointQueryContext* context, const Primitive& tri)
  54. {
  55. return PrimitivePointQuery1<Primitive>::pointQuery(query, context, tri);
  56. }
  57. };
  58. /*! Intersects M triangles with K rays */
  59. template<int M, int K, bool filter>
  60. struct TriangleMvIntersectorKMoeller
  61. {
  62. typedef TriangleMv<M> Primitive;
  63. typedef MoellerTrumboreIntersectorK<M,K> Precalculations;
  64. /*! Intersects K rays with M triangles. */
  65. static __forceinline void intersect(const vbool<K>& valid_i, Precalculations& pre, RayHitK<K>& ray, IntersectContext* context, const Primitive& tri)
  66. {
  67. for (size_t i=0; i<M; i++)
  68. {
  69. if (!tri.valid(i)) break;
  70. STAT3(normal.trav_prims,1,popcnt(valid_i),K);
  71. const Vec3vf<K> v0 = broadcast<vfloat<K>>(tri.v0,i);
  72. const Vec3vf<K> v1 = broadcast<vfloat<K>>(tri.v1,i);
  73. const Vec3vf<K> v2 = broadcast<vfloat<K>>(tri.v2,i);
  74. pre.intersectK(valid_i,ray,v0,v1,v2,/*UVIdentity<K>(),*/IntersectKEpilogM<M,K,filter>(ray,context,tri.geomID(),tri.primID(),i));
  75. }
  76. }
  77. /*! Test for K rays if they are occluded by any of the M triangles. */
  78. static __forceinline vbool<K> occluded(const vbool<K>& valid_i, Precalculations& pre, RayK<K>& ray, IntersectContext* context, const Primitive& tri)
  79. {
  80. vbool<K> valid0 = valid_i;
  81. for (size_t i=0; i<M; i++)
  82. {
  83. if (!tri.valid(i)) break;
  84. STAT3(shadow.trav_prims,1,popcnt(valid_i),K);
  85. const Vec3vf<K> v0 = broadcast<vfloat<K>>(tri.v0,i);
  86. const Vec3vf<K> v1 = broadcast<vfloat<K>>(tri.v1,i);
  87. const Vec3vf<K> v2 = broadcast<vfloat<K>>(tri.v2,i);
  88. pre.intersectK(valid0,ray,v0,v1,v2,/*UVIdentity<K>(),*/OccludedKEpilogM<M,K,filter>(valid0,ray,context,tri.geomID(),tri.primID(),i));
  89. if (none(valid0)) break;
  90. }
  91. return !valid0;
  92. }
  93. /*! Intersect a ray with M triangles and updates the hit. */
  94. static __forceinline void intersect(Precalculations& pre, RayHitK<K>& ray, size_t k, IntersectContext* context, const Primitive& tri)
  95. {
  96. STAT3(normal.trav_prims,1,1,1);
  97. pre.intersect(ray,k,tri.v0,tri.v1,tri.v2,/*UVIdentity<M>(),*/Intersect1KEpilogM<M,K,filter>(ray,k,context,tri.geomID(),tri.primID())); //FIXME: M
  98. }
  99. /*! Test if the ray is occluded by one of the M triangles. */
  100. static __forceinline bool occluded(Precalculations& pre, RayK<K>& ray, size_t k, IntersectContext* context, const Primitive& tri)
  101. {
  102. STAT3(shadow.trav_prims,1,1,1);
  103. return pre.intersect(ray,k,tri.v0,tri.v1,tri.v2,/*UVIdentity<M>(),*/Occluded1KEpilogM<M,K,filter>(ray,k,context,tri.geomID(),tri.primID())); //FIXME: M
  104. }
  105. };
  106. /*! Intersects M triangles with 1 ray */
  107. template<int M, bool filter>
  108. struct TriangleMvIntersector1Pluecker
  109. {
  110. typedef TriangleMv<M> Primitive;
  111. typedef PlueckerIntersector1<M> Precalculations;
  112. /*! Intersect a ray with M triangles and updates the hit. */
  113. static __forceinline void intersect(Precalculations& pre, RayHit& ray, IntersectContext* context, const Primitive& tri)
  114. {
  115. STAT3(normal.trav_prims,1,1,1);
  116. pre.intersect(ray,tri.v0,tri.v1,tri.v2,UVIdentity<M>(),Intersect1EpilogM<M,filter>(ray,context,tri.geomID(),tri.primID()));
  117. }
  118. /*! Test if the ray is occluded by one of the M triangles. */
  119. static __forceinline bool occluded(const Precalculations& pre, Ray& ray, IntersectContext* context, const Primitive& tri)
  120. {
  121. STAT3(shadow.trav_prims,1,1,1);
  122. return pre.intersect(ray,tri.v0,tri.v1,tri.v2,UVIdentity<M>(),Occluded1EpilogM<M,filter>(ray,context,tri.geomID(),tri.primID()));
  123. }
  124. static __forceinline bool pointQuery(PointQuery* query, PointQueryContext* context, const Primitive& tri)
  125. {
  126. return PrimitivePointQuery1<Primitive>::pointQuery(query, context, tri);
  127. }
  128. };
  129. /*! Intersects M triangles with K rays */
  130. template<int M, int K, bool filter>
  131. struct TriangleMvIntersectorKPluecker
  132. {
  133. typedef TriangleMv<M> Primitive;
  134. typedef PlueckerIntersectorK<M,K> Precalculations;
  135. /*! Intersects K rays with M triangles. */
  136. static __forceinline void intersect(const vbool<K>& valid_i, Precalculations& pre, RayHitK<K>& ray, IntersectContext* context, const Primitive& tri)
  137. {
  138. for (size_t i=0; i<M; i++)
  139. {
  140. if (!tri.valid(i)) break;
  141. STAT3(normal.trav_prims,1,popcnt(valid_i),K);
  142. const Vec3vf<K> v0 = broadcast<vfloat<K>>(tri.v0,i);
  143. const Vec3vf<K> v1 = broadcast<vfloat<K>>(tri.v1,i);
  144. const Vec3vf<K> v2 = broadcast<vfloat<K>>(tri.v2,i);
  145. pre.intersectK(valid_i,ray,v0,v1,v2,UVIdentity<K>(),IntersectKEpilogM<M,K,filter>(ray,context,tri.geomID(),tri.primID(),i));
  146. }
  147. }
  148. /*! Test for K rays if they are occluded by any of the M triangles. */
  149. static __forceinline vbool<K> occluded(const vbool<K>& valid_i, Precalculations& pre, RayK<K>& ray, IntersectContext* context, const Primitive& tri)
  150. {
  151. vbool<K> valid0 = valid_i;
  152. for (size_t i=0; i<M; i++)
  153. {
  154. if (!tri.valid(i)) break;
  155. STAT3(shadow.trav_prims,1,popcnt(valid_i),K);
  156. const Vec3vf<K> v0 = broadcast<vfloat<K>>(tri.v0,i);
  157. const Vec3vf<K> v1 = broadcast<vfloat<K>>(tri.v1,i);
  158. const Vec3vf<K> v2 = broadcast<vfloat<K>>(tri.v2,i);
  159. pre.intersectK(valid0,ray,v0,v1,v2,UVIdentity<K>(),OccludedKEpilogM<M,K,filter>(valid0,ray,context,tri.geomID(),tri.primID(),i));
  160. if (none(valid0)) break;
  161. }
  162. return !valid0;
  163. }
  164. /*! Intersect a ray with M triangles and updates the hit. */
  165. static __forceinline void intersect(Precalculations& pre, RayHitK<K>& ray, size_t k, IntersectContext* context, const Primitive& tri)
  166. {
  167. STAT3(normal.trav_prims,1,1,1);
  168. pre.intersect(ray,k,tri.v0,tri.v1,tri.v2,UVIdentity<M>(),Intersect1KEpilogM<M,K,filter>(ray,k,context,tri.geomID(),tri.primID()));
  169. }
  170. /*! Test if the ray is occluded by one of the M triangles. */
  171. static __forceinline bool occluded(Precalculations& pre, RayK<K>& ray, size_t k, IntersectContext* context, const Primitive& tri)
  172. {
  173. STAT3(shadow.trav_prims,1,1,1);
  174. return pre.intersect(ray,k,tri.v0,tri.v1,tri.v2,UVIdentity<M>(),Occluded1KEpilogM<M,K,filter>(ray,k,context,tri.geomID(),tri.primID()));
  175. }
  176. };
  177. }
  178. }