@cesium/engine 7.0.0 → 8.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (172) hide show
  1. package/Build/Workers/{chunk-MY3VNFGQ.js → chunk-23UFSGND.js} +7 -7
  2. package/Build/Workers/{chunk-IQBYFRVW.js → chunk-2A75IWRS.js} +7 -7
  3. package/Build/Workers/{chunk-VRGFV2UO.js → chunk-2FRVPMCS.js} +10 -10
  4. package/Build/Workers/{chunk-46UD5ABS.js → chunk-2FWRMUTY.js} +4 -4
  5. package/Build/Workers/{chunk-DTAIXKTO.js → chunk-2UPKWTMJ.js} +6 -6
  6. package/Build/Workers/{chunk-6VJVYK2V.js → chunk-34FXV7D7.js} +2 -2
  7. package/Build/Workers/{chunk-ODW7WYM4.js → chunk-3VAZEH7M.js} +2 -2
  8. package/Build/Workers/{chunk-U2VCRRQW.js → chunk-4DO5W5XZ.js} +6 -6
  9. package/Build/Workers/{chunk-VK3EJHWI.js → chunk-4H7PY4U5.js} +2 -2
  10. package/Build/Workers/{chunk-RV7ZYPFT.js → chunk-5QULIR53.js} +4 -4
  11. package/Build/Workers/{chunk-JY5YEZFA.js → chunk-7TC63SJW.js} +8 -8
  12. package/Build/Workers/{chunk-JJ4VBOQ3.js → chunk-7ZFGPDJA.js} +4 -4
  13. package/Build/Workers/{chunk-FP6GYBFX.js → chunk-A5DWLWCY.js} +10 -10
  14. package/Build/Workers/{chunk-5M3U6ZMA.js → chunk-BBWDMCVU.js} +1 -1
  15. package/Build/Workers/{chunk-WZU2YLWG.js → chunk-BG4UCVXN.js} +3 -3
  16. package/Build/Workers/{chunk-5WQ523AW.js → chunk-BIKA3NRA.js} +5 -5
  17. package/Build/Workers/{chunk-PTQQUQC3.js → chunk-BROJAZRZ.js} +13 -13
  18. package/Build/Workers/{chunk-YUCVWAY6.js → chunk-DDUQAJ4P.js} +7 -7
  19. package/Build/Workers/{chunk-2HJWSU7B.js → chunk-EERJKOAF.js} +4 -4
  20. package/Build/Workers/{chunk-LZGHD6NY.js → chunk-EG6PTBY2.js} +15 -15
  21. package/Build/Workers/{chunk-IX2JCCNM.js → chunk-EHWHNOEX.js} +1 -1
  22. package/Build/Workers/{chunk-NKPBIX7F.js → chunk-F3YA3Y2Z.js} +1 -1
  23. package/Build/Workers/{chunk-L2ZN645J.js → chunk-F4HFJMGM.js} +6 -6
  24. package/Build/Workers/{chunk-F6SE42BK.js → chunk-FJKNFAKQ.js} +15 -472
  25. package/Build/Workers/{chunk-PNBGBETF.js → chunk-FNIRWHJB.js} +10 -10
  26. package/Build/Workers/{chunk-RAEV7K66.js → chunk-FZRIVR7Y.js} +5 -5
  27. package/Build/Workers/{chunk-AIPU2VSX.js → chunk-G43QFN4Q.js} +6 -6
  28. package/Build/Workers/{chunk-ZUA2UUNV.js → chunk-GATZHF3K.js} +2 -2
  29. package/Build/Workers/{chunk-ZK5JOS3D.js → chunk-GRC2ZTAF.js} +14 -14
  30. package/Build/Workers/{chunk-5YLJ77FF.js → chunk-HU6N6EXB.js} +10 -10
  31. package/Build/Workers/{chunk-4EBHOMFX.js → chunk-I46ZRR5W.js} +17 -17
  32. package/Build/Workers/{chunk-LZ7JIV3K.js → chunk-JURN7NPV.js} +17 -17
  33. package/Build/Workers/{chunk-JCNXK6EL.js → chunk-KKCR2YOP.js} +11 -11
  34. package/Build/Workers/{chunk-S6SKF6DT.js → chunk-LPR3YNP2.js} +5 -5
  35. package/Build/Workers/{chunk-UDO6BFSF.js → chunk-M7ERACJJ.js} +13 -13
  36. package/Build/Workers/{chunk-BZP4T2JJ.js → chunk-MDWEGWPA.js} +10 -10
  37. package/Build/Workers/{chunk-72SANQJV.js → chunk-OGXZVPPM.js} +9 -5
  38. package/Build/Workers/{chunk-AR5DNBJ4.js → chunk-PGSJK77E.js} +6 -6
  39. package/Build/Workers/{chunk-GEJTYLCO.js → chunk-PPH7OFP3.js} +5 -5
  40. package/Build/Workers/{chunk-OVLG3FRS.js → chunk-SH5USDPI.js} +6 -6
  41. package/Build/Workers/{chunk-6HZQPRUS.js → chunk-SOWMRMWA.js} +1 -1
  42. package/Build/Workers/{chunk-JXDC723O.js → chunk-STW2DGFI.js} +2 -2
  43. package/Build/Workers/{chunk-5HDYHG3F.js → chunk-T3XIFPYR.js} +13 -13
  44. package/Build/Workers/chunk-TTUZP4BO.js +501 -0
  45. package/Build/Workers/{chunk-7XEAYGZK.js → chunk-UEXTBDBE.js} +10 -10
  46. package/Build/Workers/{chunk-GV56Q4LU.js → chunk-VOXYEYJT.js} +11 -11
  47. package/Build/Workers/{chunk-NY3K4IM3.js → chunk-X4356LRH.js} +12 -12
  48. package/Build/Workers/{chunk-S4MAZ3SS.js → chunk-XGI5BXZY.js} +2 -2
  49. package/Build/Workers/{chunk-UAEW6HKG.js → chunk-Y2ME2IJV.js} +13 -13
  50. package/Build/Workers/{chunk-XWXM2O2R.js → chunk-Y5UQJLYE.js} +6 -6
  51. package/Build/Workers/{chunk-QZAD5O7I.js → chunk-YJEBABKH.js} +7 -7
  52. package/Build/Workers/{chunk-UGK3FCDY.js → chunk-YWTJ2B4B.js} +1 -1
  53. package/Build/Workers/{chunk-R5X4OQT4.js → chunk-Z3TIFFGF.js} +7 -7
  54. package/Build/Workers/{chunk-WBQCVXR3.js → chunk-ZT7KWISZ.js} +4 -4
  55. package/Build/Workers/combineGeometry.js +24 -23
  56. package/Build/Workers/createBoxGeometry.js +18 -17
  57. package/Build/Workers/createBoxOutlineGeometry.js +16 -15
  58. package/Build/Workers/createCircleGeometry.js +26 -25
  59. package/Build/Workers/createCircleOutlineGeometry.js +19 -18
  60. package/Build/Workers/createCoplanarPolygonGeometry.js +33 -32
  61. package/Build/Workers/createCoplanarPolygonOutlineGeometry.js +31 -30
  62. package/Build/Workers/createCorridorGeometry.js +29 -28
  63. package/Build/Workers/createCorridorOutlineGeometry.js +28 -27
  64. package/Build/Workers/createCylinderGeometry.js +20 -19
  65. package/Build/Workers/createCylinderOutlineGeometry.js +18 -17
  66. package/Build/Workers/createEllipseGeometry.js +26 -25
  67. package/Build/Workers/createEllipseOutlineGeometry.js +19 -18
  68. package/Build/Workers/createEllipsoidGeometry.js +19 -18
  69. package/Build/Workers/createEllipsoidOutlineGeometry.js +18 -17
  70. package/Build/Workers/createFrustumGeometry.js +18 -17
  71. package/Build/Workers/createFrustumOutlineGeometry.js +18 -17
  72. package/Build/Workers/createGeometry.js +54 -33
  73. package/Build/Workers/createGroundPolylineGeometry.js +22 -21
  74. package/Build/Workers/createPlaneGeometry.js +16 -15
  75. package/Build/Workers/createPlaneOutlineGeometry.js +15 -14
  76. package/Build/Workers/createPolygonGeometry.js +32 -31
  77. package/Build/Workers/createPolygonOutlineGeometry.js +30 -29
  78. package/Build/Workers/createPolylineGeometry.js +25 -24
  79. package/Build/Workers/createPolylineVolumeGeometry.js +31 -30
  80. package/Build/Workers/createPolylineVolumeOutlineGeometry.js +27 -26
  81. package/Build/Workers/createRectangleGeometry.js +27 -26
  82. package/Build/Workers/createRectangleOutlineGeometry.js +20 -19
  83. package/Build/Workers/createSimplePolylineGeometry.js +23 -22
  84. package/Build/Workers/createSphereGeometry.js +19 -18
  85. package/Build/Workers/createSphereOutlineGeometry.js +18 -17
  86. package/Build/Workers/createTaskProcessorWorker.js +3 -3
  87. package/Build/Workers/createVectorTileClampedPolylines.js +14 -14
  88. package/Build/Workers/createVectorTileGeometries.js +24 -23
  89. package/Build/Workers/createVectorTilePoints.js +12 -12
  90. package/Build/Workers/createVectorTilePolygons.js +22 -21
  91. package/Build/Workers/createVectorTilePolylines.js +14 -14
  92. package/Build/Workers/createVerticesFromGoogleEarthEnterpriseBuffer.js +22 -21
  93. package/Build/Workers/createVerticesFromHeightmap.js +22 -21
  94. package/Build/Workers/createVerticesFromQuantizedTerrainMesh.js +19 -18
  95. package/Build/Workers/createWallGeometry.js +24 -23
  96. package/Build/Workers/createWallOutlineGeometry.js +23 -22
  97. package/Build/Workers/decodeDraco.js +11 -11
  98. package/Build/Workers/decodeGoogleEarthEnterprisePacket.js +5 -5
  99. package/Build/Workers/decodeI3S.js +601 -92
  100. package/Build/Workers/transcodeKTX2.js +7 -7
  101. package/Build/Workers/transferTypedArrayTest.js +1 -1
  102. package/Build/Workers/upsampleQuantizedTerrainMesh.js +22 -21
  103. package/Source/Core/Ellipsoid.js +6 -0
  104. package/Source/Core/IntersectionTests.js +6 -3
  105. package/Source/Core/Ion.js +1 -1
  106. package/Source/Core/PixelFormat.js +5 -0
  107. package/Source/Core/Transforms.js +3 -0
  108. package/Source/Core/srgbToLinear.js +32 -0
  109. package/Source/DataSources/CzmlDataSource.js +51 -23
  110. package/Source/DataSources/DataSourceDisplay.js +27 -0
  111. package/Source/DataSources/Entity.js +20 -2
  112. package/Source/DataSources/GeometryUpdaterSet.js +114 -0
  113. package/Source/DataSources/GeometryVisualizer.js +19 -83
  114. package/Source/Renderer/Context.js +10 -0
  115. package/Source/Renderer/ContextLimits.js +2 -0
  116. package/Source/Renderer/demodernizeShader.js +4 -1
  117. package/Source/Scene/ArcGisMapService.js +1 -1
  118. package/Source/Scene/Axis.js +12 -7
  119. package/Source/Scene/Camera.js +46 -4
  120. package/Source/Scene/Cesium3DTileset.js +44 -6
  121. package/Source/Scene/Cesium3DTilesetBaseTraversal.js +2 -4
  122. package/Source/Scene/FrameState.js +5 -0
  123. package/Source/Scene/GlobeTranslucencyState.js +1 -1
  124. package/Source/Scene/GltfPipeline/updateVersion.js +69 -68
  125. package/Source/Scene/I3SDataProvider.js +270 -53
  126. package/Source/Scene/I3SDecoder.js +8 -1
  127. package/Source/Scene/I3SFeature.js +2 -5
  128. package/Source/Scene/I3SField.js +136 -31
  129. package/Source/Scene/I3SGeometry.js +70 -2
  130. package/Source/Scene/I3SLayer.js +55 -10
  131. package/Source/Scene/I3SNode.js +175 -18
  132. package/Source/Scene/I3SStatistics.js +94 -0
  133. package/Source/Scene/I3SSublayer.js +176 -0
  134. package/Source/Scene/I3SSymbology.js +337 -0
  135. package/Source/Scene/KeyframeNode.js +1 -1
  136. package/Source/Scene/Model/pickModel.js +25 -7
  137. package/Source/Scene/PickFramebuffer.js +37 -2
  138. package/Source/Scene/Picking.js +113 -39
  139. package/Source/Scene/Primitive.js +6 -2
  140. package/Source/Scene/Scene.js +126 -42
  141. package/Source/Scene/ScreenSpaceCameraController.js +21 -7
  142. package/Source/Scene/SensorVolumePortionToDisplay.js +69 -0
  143. package/Source/Scene/SpatialNode.js +12 -19
  144. package/Source/Scene/StructuralMetadata.js +1 -1
  145. package/Source/Scene/VoxelBoxShape.js +76 -0
  146. package/Source/Scene/VoxelCell.js +273 -0
  147. package/Source/Scene/VoxelCylinderShape.js +114 -43
  148. package/Source/Scene/VoxelEllipsoidShape.js +158 -116
  149. package/Source/Scene/VoxelPrimitive.js +3 -1
  150. package/Source/Scene/VoxelRenderResources.js +3 -0
  151. package/Source/Scene/VoxelShape.js +13 -0
  152. package/Source/Scene/VoxelTraversal.js +76 -54
  153. package/Source/Scene/buildVoxelDrawCommands.js +23 -0
  154. package/Source/Scene/createGooglePhotorealistic3DTileset.js +1 -0
  155. package/Source/Scene/processVoxelProperties.js +2 -0
  156. package/Source/Shaders/Voxels/IntersectCylinder.glsl +14 -111
  157. package/Source/Shaders/Voxels/IntersectCylinder.js +14 -111
  158. package/Source/Shaders/Voxels/IntersectEllipsoid.glsl +32 -113
  159. package/Source/Shaders/Voxels/IntersectEllipsoid.js +32 -113
  160. package/Source/Shaders/Voxels/IntersectLongitude.glsl +102 -0
  161. package/Source/Shaders/Voxels/IntersectLongitude.js +104 -0
  162. package/Source/Shaders/Voxels/VoxelFS.glsl +39 -1
  163. package/Source/Shaders/Voxels/VoxelFS.js +39 -1
  164. package/Source/Shaders/Voxels/convertUvToCylinder.glsl +19 -37
  165. package/Source/Shaders/Voxels/convertUvToCylinder.js +19 -37
  166. package/Source/Shaders/Voxels/convertUvToEllipsoid.glsl +24 -44
  167. package/Source/Shaders/Voxels/convertUvToEllipsoid.js +24 -44
  168. package/Source/Workers/createGeometry.js +40 -11
  169. package/Source/Workers/decodeI3S.js +720 -94
  170. package/index.d.ts +296 -11
  171. package/index.js +102 -94
  172. package/package.json +1 -1
@@ -1,13 +1,13 @@
1
1
  // See IntersectionUtils.glsl for the definitions of Ray, Intersections,
2
2
  // setIntersection, setIntersectionPair, INF_HIT, NO_HIT
3
+ // See IntersectLongitude.glsl for the definitions of intersectHalfPlane,
4
+ // intersectFlippedWedge, intersectRegularWedge
3
5
 
4
6
  /* Ellipsoid defines (set in Scene/VoxelEllipsoidShape.js)
5
7
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE
6
8
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_ZERO
7
9
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_UNDER_HALF
8
- #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_HALF
9
10
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_OVER_HALF
10
- #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE
11
11
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MAX_UNDER_HALF
12
12
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MAX_EQUAL_HALF
13
13
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MAX_OVER_HALF
@@ -16,7 +16,6 @@
16
16
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MIN_OVER_HALF
17
17
  #define ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MAX
18
18
  #define ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MIN
19
- #define ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_FLAT
20
19
  #define ELLIPSOID_INTERSECTION_INDEX_LONGITUDE
21
20
  #define ELLIPSOID_INTERSECTION_INDEX_LATITUDE_MAX
22
21
  #define ELLIPSOID_INTERSECTION_INDEX_LATITUDE_MIN
@@ -48,78 +47,6 @@ vec2 intersectZPlane(Ray ray)
48
47
  else return vec2(-INF_HIT, t);
49
48
  }
50
49
 
51
- vec4 intersectHalfPlane(Ray ray, float angle) {
52
- vec2 o = ray.pos.xy;
53
- vec2 d = ray.dir.xy;
54
- vec2 planeDirection = vec2(cos(angle), sin(angle));
55
- vec2 planeNormal = vec2(planeDirection.y, -planeDirection.x);
56
-
57
- float a = dot(o, planeNormal);
58
- float b = dot(d, planeNormal);
59
- float t = -a / b;
60
-
61
- vec2 p = o + t * d;
62
- bool outside = dot(p, planeDirection) < 0.0;
63
- if (outside) return vec4(-INF_HIT, +INF_HIT, NO_HIT, NO_HIT);
64
-
65
- return vec4(-INF_HIT, t, t, +INF_HIT);
66
- }
67
-
68
- vec2 intersectHalfSpace(Ray ray, float angle)
69
- {
70
- vec2 o = ray.pos.xy;
71
- vec2 d = ray.dir.xy;
72
- vec2 n = vec2(sin(angle), -cos(angle));
73
-
74
- float a = dot(o, n);
75
- float b = dot(d, n);
76
- float t = -a / b;
77
- float s = sign(a);
78
-
79
- if (t >= 0.0 != s >= 0.0) return vec2(t, +INF_HIT);
80
- else return vec2(-INF_HIT, t);
81
- }
82
-
83
- vec2 intersectRegularWedge(Ray ray, float minAngle, float maxAngle)
84
- {
85
- vec2 o = ray.pos.xy;
86
- vec2 d = ray.dir.xy;
87
- vec2 n1 = vec2(sin(minAngle), -cos(minAngle));
88
- vec2 n2 = vec2(-sin(maxAngle), cos(maxAngle));
89
-
90
- float a1 = dot(o, n1);
91
- float a2 = dot(o, n2);
92
- float b1 = dot(d, n1);
93
- float b2 = dot(d, n2);
94
-
95
- float t1 = -a1 / b1;
96
- float t2 = -a2 / b2;
97
- float s1 = sign(a1);
98
- float s2 = sign(a2);
99
-
100
- float tmin = min(t1, t2);
101
- float tmax = max(t1, t2);
102
- float smin = tmin == t1 ? s1 : s2;
103
- float smax = tmin == t1 ? s2 : s1;
104
-
105
- bool e = tmin >= 0.0;
106
- bool f = tmax >= 0.0;
107
- bool g = smin >= 0.0;
108
- bool h = smax >= 0.0;
109
-
110
- if (e != g && f == h) return vec2(tmin, tmax);
111
- else if (e == g && f == h) return vec2(-INF_HIT, tmin);
112
- else if (e != g && f != h) return vec2(tmax, +INF_HIT);
113
- else return vec2(NO_HIT);
114
- }
115
-
116
- vec4 intersectFlippedWedge(Ray ray, float minAngle, float maxAngle)
117
- {
118
- vec2 planeIntersectMin = intersectHalfSpace(ray, minAngle);
119
- vec2 planeIntersectMax = intersectHalfSpace(ray, maxAngle + czm_pi);
120
- return vec4(planeIntersectMin, planeIntersectMax);
121
- }
122
-
123
50
  vec2 intersectUnitSphere(Ray ray)
124
51
  {
125
52
  vec3 o = ray.pos;
@@ -250,39 +177,32 @@ void intersectShape(in Ray ray, inout Intersections ix) {
250
177
  }
251
178
 
252
179
  // Inner ellipsoid
253
- #if defined(ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_FLAT)
254
- // When the ellipsoid is perfectly thin it's necessary to sandwich the
255
- // inner ellipsoid intersection inside the outer ellipsoid intersection.
256
-
257
- // Without this special case,
258
- // [outerMin, outerMax, innerMin, innerMax] will bubble sort to
259
- // [outerMin, innerMin, outerMax, innerMax] which will cause the back
260
- // side of the ellipsoid to be invisible because it will think the ray
261
- // is still inside the inner (negative) ellipsoid after exiting the
262
- // outer (positive) ellipsoid.
263
-
264
- // With this special case,
265
- // [outerMin, innerMin, innerMax, outerMax] will bubble sort to
266
- // [outerMin, innerMin, innerMax, outerMax] which will work correctly.
267
-
268
- // Note: If initializeIntersections() changes its sorting function
269
- // from bubble sort to something else, this code may need to change.
270
- setIntersection(ix, 0, outerIntersect.x, true, true); // positive, enter
271
- setIntersection(ix, 1, outerIntersect.x, false, true); // negative, enter
272
- setIntersection(ix, 2, outerIntersect.y, false, false); // negative, exit
273
- setIntersection(ix, 3, outerIntersect.y, true, false); // positive, exit
274
- #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MIN)
180
+ #if defined(ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MIN)
275
181
  Ray innerRay = Ray(ray.pos * u_ellipsoidInverseInnerScaleUv, ray.dir * u_ellipsoidInverseInnerScaleUv);
276
182
  vec2 innerIntersect = intersectUnitSphereUnnormalizedDirection(innerRay);
277
183
 
278
184
  if (innerIntersect == vec2(NO_HIT)) {
279
185
  setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_HEIGHT_MIN, innerIntersect);
280
186
  } else {
281
- // When the ellipsoid is very large and thin it's possible for floating
282
- // point math to cause the ray to intersect the inner ellipsoid before
283
- // the outer ellipsoid. To prevent this from happening, clamp innerIntersect
284
- // to outerIntersect and sandwhich the intersections like described above.
285
- //
187
+ // When the ellipsoid is large and thin it's possible for floating point math
188
+ // to cause the ray to intersect the inner ellipsoid before the outer ellipsoid.
189
+ // To prevent this from happening, clamp innerIntersect to outerIntersect and
190
+ // sandwich the inner ellipsoid intersection inside the outer ellipsoid intersection.
191
+
192
+ // Without this special case,
193
+ // [outerMin, outerMax, innerMin, innerMax] will bubble sort to
194
+ // [outerMin, innerMin, outerMax, innerMax] which will cause the back
195
+ // side of the ellipsoid to be invisible because it will think the ray
196
+ // is still inside the inner (negative) ellipsoid after exiting the
197
+ // outer (positive) ellipsoid.
198
+
199
+ // With this special case,
200
+ // [outerMin, innerMin, innerMax, outerMax] will bubble sort to
201
+ // [outerMin, innerMin, innerMax, outerMax] which will work correctly.
202
+
203
+ // Note: If initializeIntersections() changes its sorting function
204
+ // from bubble sort to something else, this code may need to change.
205
+
286
206
  // In theory a similar fix is needed for cylinders, however it's more
287
207
  // complicated to implement because the inner shape is allowed to be
288
208
  // intersected first.
@@ -330,18 +250,17 @@ void intersectShape(in Ray ray, inout Intersections ix) {
330
250
 
331
251
  // Wedge
332
252
  #if defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_ZERO)
333
- vec4 wedgeIntersect = intersectHalfPlane(ray, u_ellipsoidRenderLongitudeMinMax.x);
334
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersect.xy);
335
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersect.zw);
253
+ RayShapeIntersection wedgeIntersects[2];
254
+ intersectHalfPlane(ray, u_ellipsoidRenderLongitudeMinMax.x, wedgeIntersects);
255
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersects[0]);
256
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersects[1]);
336
257
  #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_UNDER_HALF)
337
- vec2 wedgeIntersect = intersectRegularWedge(ray, u_ellipsoidRenderLongitudeMinMax.x, u_ellipsoidRenderLongitudeMinMax.y);
338
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE, wedgeIntersect);
339
- #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_HALF)
340
- vec2 wedgeIntersect = intersectHalfSpace(ray, u_ellipsoidRenderLongitudeMinMax.x);
341
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE, wedgeIntersect);
258
+ RayShapeIntersection wedgeIntersect = intersectRegularWedge(ray, u_ellipsoidRenderLongitudeMinMax);
259
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE, wedgeIntersect);
342
260
  #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_OVER_HALF)
343
- vec4 wedgeIntersect = intersectFlippedWedge(ray, u_ellipsoidRenderLongitudeMinMax.x, u_ellipsoidRenderLongitudeMinMax.y);
344
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersect.xy);
345
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersect.zw);
261
+ RayShapeIntersection wedgeIntersects[2];
262
+ intersectFlippedWedge(ray, u_ellipsoidRenderLongitudeMinMax, wedgeIntersects);
263
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersects[0]);
264
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersects[1]);
346
265
  #endif
347
266
  }
@@ -1,14 +1,14 @@
1
1
  //This file is automatically rebuilt by the Cesium build process.
2
2
  export default "// See IntersectionUtils.glsl for the definitions of Ray, Intersections,\n\
3
3
  // setIntersection, setIntersectionPair, INF_HIT, NO_HIT\n\
4
+ // See IntersectLongitude.glsl for the definitions of intersectHalfPlane,\n\
5
+ // intersectFlippedWedge, intersectRegularWedge\n\
4
6
  \n\
5
7
  /* Ellipsoid defines (set in Scene/VoxelEllipsoidShape.js)\n\
6
8
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE\n\
7
9
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_ZERO\n\
8
10
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_UNDER_HALF\n\
9
- #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_HALF\n\
10
11
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_OVER_HALF\n\
11
- #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE\n\
12
12
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MAX_UNDER_HALF\n\
13
13
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MAX_EQUAL_HALF\n\
14
14
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MAX_OVER_HALF\n\
@@ -17,7 +17,6 @@ export default "// See IntersectionUtils.glsl for the definitions of Ray, Inters
17
17
  #define ELLIPSOID_HAS_RENDER_BOUNDS_LATITUDE_MIN_OVER_HALF\n\
18
18
  #define ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MAX\n\
19
19
  #define ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MIN\n\
20
- #define ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_FLAT\n\
21
20
  #define ELLIPSOID_INTERSECTION_INDEX_LONGITUDE\n\
22
21
  #define ELLIPSOID_INTERSECTION_INDEX_LATITUDE_MAX\n\
23
22
  #define ELLIPSOID_INTERSECTION_INDEX_LATITUDE_MIN\n\
@@ -49,78 +48,6 @@ vec2 intersectZPlane(Ray ray)\n\
49
48
  else return vec2(-INF_HIT, t);\n\
50
49
  }\n\
51
50
  \n\
52
- vec4 intersectHalfPlane(Ray ray, float angle) {\n\
53
- vec2 o = ray.pos.xy;\n\
54
- vec2 d = ray.dir.xy;\n\
55
- vec2 planeDirection = vec2(cos(angle), sin(angle));\n\
56
- vec2 planeNormal = vec2(planeDirection.y, -planeDirection.x);\n\
57
- \n\
58
- float a = dot(o, planeNormal);\n\
59
- float b = dot(d, planeNormal);\n\
60
- float t = -a / b;\n\
61
- \n\
62
- vec2 p = o + t * d;\n\
63
- bool outside = dot(p, planeDirection) < 0.0;\n\
64
- if (outside) return vec4(-INF_HIT, +INF_HIT, NO_HIT, NO_HIT);\n\
65
- \n\
66
- return vec4(-INF_HIT, t, t, +INF_HIT);\n\
67
- }\n\
68
- \n\
69
- vec2 intersectHalfSpace(Ray ray, float angle)\n\
70
- {\n\
71
- vec2 o = ray.pos.xy;\n\
72
- vec2 d = ray.dir.xy;\n\
73
- vec2 n = vec2(sin(angle), -cos(angle));\n\
74
- \n\
75
- float a = dot(o, n);\n\
76
- float b = dot(d, n);\n\
77
- float t = -a / b;\n\
78
- float s = sign(a);\n\
79
- \n\
80
- if (t >= 0.0 != s >= 0.0) return vec2(t, +INF_HIT);\n\
81
- else return vec2(-INF_HIT, t);\n\
82
- }\n\
83
- \n\
84
- vec2 intersectRegularWedge(Ray ray, float minAngle, float maxAngle)\n\
85
- {\n\
86
- vec2 o = ray.pos.xy;\n\
87
- vec2 d = ray.dir.xy;\n\
88
- vec2 n1 = vec2(sin(minAngle), -cos(minAngle));\n\
89
- vec2 n2 = vec2(-sin(maxAngle), cos(maxAngle));\n\
90
- \n\
91
- float a1 = dot(o, n1);\n\
92
- float a2 = dot(o, n2);\n\
93
- float b1 = dot(d, n1);\n\
94
- float b2 = dot(d, n2);\n\
95
- \n\
96
- float t1 = -a1 / b1;\n\
97
- float t2 = -a2 / b2;\n\
98
- float s1 = sign(a1);\n\
99
- float s2 = sign(a2);\n\
100
- \n\
101
- float tmin = min(t1, t2);\n\
102
- float tmax = max(t1, t2);\n\
103
- float smin = tmin == t1 ? s1 : s2;\n\
104
- float smax = tmin == t1 ? s2 : s1;\n\
105
- \n\
106
- bool e = tmin >= 0.0;\n\
107
- bool f = tmax >= 0.0;\n\
108
- bool g = smin >= 0.0;\n\
109
- bool h = smax >= 0.0;\n\
110
- \n\
111
- if (e != g && f == h) return vec2(tmin, tmax);\n\
112
- else if (e == g && f == h) return vec2(-INF_HIT, tmin);\n\
113
- else if (e != g && f != h) return vec2(tmax, +INF_HIT);\n\
114
- else return vec2(NO_HIT);\n\
115
- }\n\
116
- \n\
117
- vec4 intersectFlippedWedge(Ray ray, float minAngle, float maxAngle)\n\
118
- {\n\
119
- vec2 planeIntersectMin = intersectHalfSpace(ray, minAngle);\n\
120
- vec2 planeIntersectMax = intersectHalfSpace(ray, maxAngle + czm_pi);\n\
121
- return vec4(planeIntersectMin, planeIntersectMax);\n\
122
- }\n\
123
- \n\
124
51
  vec2 intersectUnitSphere(Ray ray)\n\
125
52
  {\n\
126
53
  vec3 o = ray.pos;\n\
@@ -251,39 +178,32 @@ void intersectShape(in Ray ray, inout Intersections ix) {\n\
251
178
  }\n\
252
179
  \n\
253
180
  // Inner ellipsoid\n\
254
- #if defined(ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_FLAT)\n\
255
- // When the ellipsoid is perfectly thin it's necessary to sandwich the\n\
256
- // inner ellipsoid intersection inside the outer ellipsoid intersection.\n\
257
- \n\
258
- // Without this special case,\n\
259
- // [outerMin, outerMax, innerMin, innerMax] will bubble sort to\n\
260
- // [outerMin, innerMin, outerMax, innerMax] which will cause the back\n\
261
- // side of the ellipsoid to be invisible because it will think the ray\n\
262
- // is still inside the inner (negative) ellipsoid after exiting the\n\
263
- // outer (positive) ellipsoid.\n\
264
- \n\
265
- // With this special case,\n\
266
- // [outerMin, innerMin, innerMax, outerMax] will bubble sort to\n\
267
- // [outerMin, innerMin, innerMax, outerMax] which will work correctly.\n\
268
- \n\
269
- // Note: If initializeIntersections() changes its sorting function\n\
270
- // from bubble sort to something else, this code may need to change.\n\
271
- setIntersection(ix, 0, outerIntersect.x, true, true); // positive, enter\n\
272
- setIntersection(ix, 1, outerIntersect.x, false, true); // negative, enter\n\
273
- setIntersection(ix, 2, outerIntersect.y, false, false); // negative, exit\n\
274
- setIntersection(ix, 3, outerIntersect.y, true, false); // positive, exit\n\
275
- #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MIN)\n\
181
+ #if defined(ELLIPSOID_HAS_RENDER_BOUNDS_HEIGHT_MIN)\n\
276
182
  Ray innerRay = Ray(ray.pos * u_ellipsoidInverseInnerScaleUv, ray.dir * u_ellipsoidInverseInnerScaleUv);\n\
277
183
  vec2 innerIntersect = intersectUnitSphereUnnormalizedDirection(innerRay);\n\
278
184
  \n\
279
185
  if (innerIntersect == vec2(NO_HIT)) {\n\
280
186
  setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_HEIGHT_MIN, innerIntersect);\n\
281
187
  } else {\n\
282
- // When the ellipsoid is very large and thin it's possible for floating\n\
283
- // point math to cause the ray to intersect the inner ellipsoid before\n\
284
- // the outer ellipsoid. To prevent this from happening, clamp innerIntersect\n\
285
- // to outerIntersect and sandwhich the intersections like described above.\n\
286
- //\n\
188
+ // When the ellipsoid is large and thin it's possible for floating point math\n\
189
+ // to cause the ray to intersect the inner ellipsoid before the outer ellipsoid.\n\
190
+ // To prevent this from happening, clamp innerIntersect to outerIntersect and\n\
191
+ // sandwich the inner ellipsoid intersection inside the outer ellipsoid intersection.\n\
192
+ \n\
193
+ // Without this special case,\n\
194
+ // [outerMin, outerMax, innerMin, innerMax] will bubble sort to\n\
195
+ // [outerMin, innerMin, outerMax, innerMax] which will cause the back\n\
196
+ // side of the ellipsoid to be invisible because it will think the ray\n\
197
+ // is still inside the inner (negative) ellipsoid after exiting the\n\
198
+ // outer (positive) ellipsoid.\n\
199
+ \n\
200
+ // With this special case,\n\
201
+ // [outerMin, innerMin, innerMax, outerMax] will bubble sort to\n\
202
+ // [outerMin, innerMin, innerMax, outerMax] which will work correctly.\n\
203
+ \n\
204
+ // Note: If initializeIntersections() changes its sorting function\n\
205
+ // from bubble sort to something else, this code may need to change.\n\
206
+ \n\
287
207
  // In theory a similar fix is needed for cylinders, however it's more\n\
288
208
  // complicated to implement because the inner shape is allowed to be\n\
289
209
  // intersected first.\n\
@@ -331,19 +251,18 @@ void intersectShape(in Ray ray, inout Intersections ix) {\n\
331
251
  \n\
332
252
  // Wedge\n\
333
253
  #if defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_ZERO)\n\
334
- vec4 wedgeIntersect = intersectHalfPlane(ray, u_ellipsoidRenderLongitudeMinMax.x);\n\
335
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersect.xy);\n\
336
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersect.zw);\n\
254
+ RayShapeIntersection wedgeIntersects[2];\n\
255
+ intersectHalfPlane(ray, u_ellipsoidRenderLongitudeMinMax.x, wedgeIntersects);\n\
256
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersects[0]);\n\
257
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersects[1]);\n\
337
258
  #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_UNDER_HALF)\n\
338
- vec2 wedgeIntersect = intersectRegularWedge(ray, u_ellipsoidRenderLongitudeMinMax.x, u_ellipsoidRenderLongitudeMinMax.y);\n\
339
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE, wedgeIntersect);\n\
340
- #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_EQUAL_HALF)\n\
341
- vec2 wedgeIntersect = intersectHalfSpace(ray, u_ellipsoidRenderLongitudeMinMax.x);\n\
342
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE, wedgeIntersect);\n\
259
+ RayShapeIntersection wedgeIntersect = intersectRegularWedge(ray, u_ellipsoidRenderLongitudeMinMax);\n\
260
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE, wedgeIntersect);\n\
343
261
  #elif defined(ELLIPSOID_HAS_RENDER_BOUNDS_LONGITUDE_RANGE_OVER_HALF)\n\
344
- vec4 wedgeIntersect = intersectFlippedWedge(ray, u_ellipsoidRenderLongitudeMinMax.x, u_ellipsoidRenderLongitudeMinMax.y);\n\
345
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersect.xy);\n\
346
- setIntersectionPair(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersect.zw);\n\
262
+ RayShapeIntersection wedgeIntersects[2];\n\
263
+ intersectFlippedWedge(ray, u_ellipsoidRenderLongitudeMinMax, wedgeIntersects);\n\
264
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 0, wedgeIntersects[0]);\n\
265
+ setShapeIntersection(ix, ELLIPSOID_INTERSECTION_INDEX_LONGITUDE + 1, wedgeIntersects[1]);\n\
347
266
  #endif\n\
348
267
  }\n\
349
268
  ";
@@ -0,0 +1,102 @@
1
+ // See IntersectionUtils.glsl for the definitions of Ray, NO_HIT, INF_HIT,
2
+ // RayShapeIntersection
3
+
4
+ vec4 intersectLongitude(in Ray ray, in float angle, in bool positiveNormal) {
5
+ float normalSign = positiveNormal ? 1.0 : -1.0;
6
+ vec2 planeNormal = vec2(-sin(angle), cos(angle)) * normalSign;
7
+
8
+ vec2 position = ray.pos.xy;
9
+ vec2 direction = ray.dir.xy;
10
+ float approachRate = dot(direction, planeNormal);
11
+ float distance = -dot(position, planeNormal);
12
+
13
+ float t = (approachRate == 0.0)
14
+ ? NO_HIT
15
+ : distance / approachRate;
16
+
17
+ return vec4(planeNormal, 0.0, t);
18
+ }
19
+
20
+ RayShapeIntersection intersectHalfSpace(in Ray ray, in float angle, in bool positiveNormal)
21
+ {
22
+ vec4 intersection = intersectLongitude(ray, angle, positiveNormal);
23
+ vec4 farSide = vec4(normalize(ray.dir), INF_HIT);
24
+
25
+ bool hitFront = (intersection.w > 0.0) == (dot(ray.pos.xy, intersection.xy) > 0.0);
26
+ if (!hitFront) {
27
+ return RayShapeIntersection(intersection, farSide);
28
+ } else {
29
+ return RayShapeIntersection(-1.0 * farSide, intersection);
30
+ }
31
+ }
32
+
33
+ void intersectFlippedWedge(in Ray ray, in vec2 minMaxAngle, out RayShapeIntersection intersections[2])
34
+ {
35
+ intersections[0] = intersectHalfSpace(ray, minMaxAngle.x, false);
36
+ intersections[1] = intersectHalfSpace(ray, minMaxAngle.y, true);
37
+ }
38
+
39
+ bool hitPositiveHalfPlane(in Ray ray, in vec4 intersection, in bool positiveNormal) {
40
+ float normalSign = positiveNormal ? 1.0 : -1.0;
41
+ vec2 planeDirection = vec2(intersection.y, -intersection.x) * normalSign;
42
+ vec2 hit = ray.pos.xy + intersection.w * ray.dir.xy;
43
+ return dot(hit, planeDirection) > 0.0;
44
+ }
45
+
46
+ void intersectHalfPlane(in Ray ray, in float angle, out RayShapeIntersection intersections[2]) {
47
+ vec4 intersection = intersectLongitude(ray, angle, true);
48
+ vec4 farSide = vec4(normalize(ray.dir), INF_HIT);
49
+
50
+ if (hitPositiveHalfPlane(ray, intersection, true)) {
51
+ intersections[0].entry = -1.0 * farSide;
52
+ intersections[0].exit = vec4(-1.0 * intersection.xy, 0.0, intersection.w);
53
+ intersections[1].entry = intersection;
54
+ intersections[1].exit = farSide;
55
+ } else {
56
+ vec4 miss = vec4(normalize(ray.dir), NO_HIT);
57
+ intersections[0].entry = -1.0 * farSide;
58
+ intersections[0].exit = farSide;
59
+ intersections[1].entry = miss;
60
+ intersections[1].exit = miss;
61
+ }
62
+ }
63
+
64
+ RayShapeIntersection intersectRegularWedge(in Ray ray, in vec2 minMaxAngle)
65
+ {
66
+ // Note: works for maxAngle > minAngle + pi, where the "regular wedge"
67
+ // is actually a negative volume.
68
+ // Compute intersections with the two planes.
69
+ // Normals will point toward the "outside" (negative space)
70
+ vec4 intersect1 = intersectLongitude(ray, minMaxAngle.x, false);
71
+ vec4 intersect2 = intersectLongitude(ray, minMaxAngle.y, true);
72
+
73
+ // Choose intersection with smallest T as the "first", the other as "last"
74
+ // Note: first or last could be in the "shadow" wedge, beyond the tip
75
+ bool inOrder = intersect1.w <= intersect2.w;
76
+ vec4 first = inOrder ? intersect1 : intersect2;
77
+ vec4 last = inOrder ? intersect2 : intersect1;
78
+
79
+ bool firstIsAhead = first.w >= 0.0;
80
+ bool startedInsideFirst = dot(ray.pos.xy, first.xy) < 0.0;
81
+ bool exitFromInside = firstIsAhead == startedInsideFirst;
82
+ bool lastIsAhead = last.w > 0.0;
83
+ bool startedOutsideLast = dot(ray.pos.xy, last.xy) >= 0.0;
84
+ bool enterFromOutside = lastIsAhead == startedOutsideLast;
85
+
86
+ vec4 farSide = vec4(normalize(ray.dir), INF_HIT);
87
+ vec4 miss = vec4(normalize(ray.dir), NO_HIT);
88
+
89
+ if (exitFromInside && enterFromOutside) {
90
+ // Ray crosses both faces of negative wedge, exiting then entering the positive shape
91
+ return RayShapeIntersection(first, last);
92
+ } else if (!exitFromInside && enterFromOutside) {
93
+ // Ray starts inside wedge. last is in shadow wedge, and first is actually the entry
94
+ return RayShapeIntersection(-1.0 * farSide, first);
95
+ } else if (exitFromInside && !enterFromOutside) {
96
+ // First intersection was in the shadow wedge, so last is actually the exit
97
+ return RayShapeIntersection(last, farSide);
98
+ } else { // !exitFromInside && !enterFromOutside
99
+ // Both intersections were in the shadow wedge
100
+ return RayShapeIntersection(miss, miss);
101
+ }
102
+ }
@@ -0,0 +1,104 @@
1
+ //This file is automatically rebuilt by the Cesium build process.
2
+ export default "// See IntersectionUtils.glsl for the definitions of Ray, NO_HIT, INF_HIT,\n\
3
+ // RayShapeIntersection\n\
4
+ \n\
5
+ vec4 intersectLongitude(in Ray ray, in float angle, in bool positiveNormal) {\n\
6
+ float normalSign = positiveNormal ? 1.0 : -1.0;\n\
7
+ vec2 planeNormal = vec2(-sin(angle), cos(angle)) * normalSign;\n\
8
+ \n\
9
+ vec2 position = ray.pos.xy;\n\
10
+ vec2 direction = ray.dir.xy;\n\
11
+ float approachRate = dot(direction, planeNormal);\n\
12
+ float distance = -dot(position, planeNormal);\n\
13
+ \n\
14
+ float t = (approachRate == 0.0)\n\
15
+ ? NO_HIT\n\
16
+ : distance / approachRate;\n\
17
+ \n\
18
+ return vec4(planeNormal, 0.0, t);\n\
19
+ }\n\
20
+ \n\
21
+ RayShapeIntersection intersectHalfSpace(in Ray ray, in float angle, in bool positiveNormal)\n\
22
+ {\n\
23
+ vec4 intersection = intersectLongitude(ray, angle, positiveNormal);\n\
24
+ vec4 farSide = vec4(normalize(ray.dir), INF_HIT);\n\
25
+ \n\
26
+ bool hitFront = (intersection.w > 0.0) == (dot(ray.pos.xy, intersection.xy) > 0.0);\n\
27
+ if (!hitFront) {\n\
28
+ return RayShapeIntersection(intersection, farSide);\n\
29
+ } else {\n\
30
+ return RayShapeIntersection(-1.0 * farSide, intersection);\n\
31
+ }\n\
32
+ }\n\
33
+ \n\
34
+ void intersectFlippedWedge(in Ray ray, in vec2 minMaxAngle, out RayShapeIntersection intersections[2])\n\
35
+ {\n\
36
+ intersections[0] = intersectHalfSpace(ray, minMaxAngle.x, false);\n\
37
+ intersections[1] = intersectHalfSpace(ray, minMaxAngle.y, true);\n\
38
+ }\n\
39
+ \n\
40
+ bool hitPositiveHalfPlane(in Ray ray, in vec4 intersection, in bool positiveNormal) {\n\
41
+ float normalSign = positiveNormal ? 1.0 : -1.0;\n\
42
+ vec2 planeDirection = vec2(intersection.y, -intersection.x) * normalSign;\n\
43
+ vec2 hit = ray.pos.xy + intersection.w * ray.dir.xy;\n\
44
+ return dot(hit, planeDirection) > 0.0;\n\
45
+ }\n\
46
+ \n\
47
+ void intersectHalfPlane(in Ray ray, in float angle, out RayShapeIntersection intersections[2]) {\n\
48
+ vec4 intersection = intersectLongitude(ray, angle, true);\n\
49
+ vec4 farSide = vec4(normalize(ray.dir), INF_HIT);\n\
50
+ \n\
51
+ if (hitPositiveHalfPlane(ray, intersection, true)) {\n\
52
+ intersections[0].entry = -1.0 * farSide;\n\
53
+ intersections[0].exit = vec4(-1.0 * intersection.xy, 0.0, intersection.w);\n\
54
+ intersections[1].entry = intersection;\n\
55
+ intersections[1].exit = farSide;\n\
56
+ } else {\n\
57
+ vec4 miss = vec4(normalize(ray.dir), NO_HIT);\n\
58
+ intersections[0].entry = -1.0 * farSide;\n\
59
+ intersections[0].exit = farSide;\n\
60
+ intersections[1].entry = miss;\n\
61
+ intersections[1].exit = miss;\n\
62
+ }\n\
63
+ }\n\
64
+ \n\
65
+ RayShapeIntersection intersectRegularWedge(in Ray ray, in vec2 minMaxAngle)\n\
66
+ {\n\
67
+ // Note: works for maxAngle > minAngle + pi, where the \"regular wedge\"\n\
68
+ // is actually a negative volume.\n\
69
+ // Compute intersections with the two planes.\n\
70
+ // Normals will point toward the \"outside\" (negative space)\n\
71
+ vec4 intersect1 = intersectLongitude(ray, minMaxAngle.x, false);\n\
72
+ vec4 intersect2 = intersectLongitude(ray, minMaxAngle.y, true);\n\
73
+ \n\
74
+ // Choose intersection with smallest T as the \"first\", the other as \"last\"\n\
75
+ // Note: first or last could be in the \"shadow\" wedge, beyond the tip\n\
76
+ bool inOrder = intersect1.w <= intersect2.w;\n\
77
+ vec4 first = inOrder ? intersect1 : intersect2;\n\
78
+ vec4 last = inOrder ? intersect2 : intersect1;\n\
79
+ \n\
80
+ bool firstIsAhead = first.w >= 0.0;\n\
81
+ bool startedInsideFirst = dot(ray.pos.xy, first.xy) < 0.0;\n\
82
+ bool exitFromInside = firstIsAhead == startedInsideFirst;\n\
83
+ bool lastIsAhead = last.w > 0.0;\n\
84
+ bool startedOutsideLast = dot(ray.pos.xy, last.xy) >= 0.0;\n\
85
+ bool enterFromOutside = lastIsAhead == startedOutsideLast;\n\
86
+ \n\
87
+ vec4 farSide = vec4(normalize(ray.dir), INF_HIT);\n\
88
+ vec4 miss = vec4(normalize(ray.dir), NO_HIT);\n\
89
+ \n\
90
+ if (exitFromInside && enterFromOutside) {\n\
91
+ // Ray crosses both faces of negative wedge, exiting then entering the positive shape\n\
92
+ return RayShapeIntersection(first, last);\n\
93
+ } else if (!exitFromInside && enterFromOutside) {\n\
94
+ // Ray starts inside wedge. last is in shadow wedge, and first is actually the entry\n\
95
+ return RayShapeIntersection(-1.0 * farSide, first);\n\
96
+ } else if (exitFromInside && !enterFromOutside) {\n\
97
+ // First intersection was in the shadow wedge, so last is actually the exit\n\
98
+ return RayShapeIntersection(last, farSide);\n\
99
+ } else { // !exitFromInside && !enterFromOutside\n\
100
+ // Both intersections were in the shadow wedge\n\
101
+ return RayShapeIntersection(miss, miss);\n\
102
+ }\n\
103
+ }\n\
104
+ ";
@@ -9,7 +9,11 @@
9
9
  // See Megatexture.glsl for the definition of accumulatePropertiesFromMegatexture
10
10
 
11
11
  #define STEP_COUNT_MAX 1000 // Harcoded value because GLSL doesn't like variable length loops
12
- #define ALPHA_ACCUM_MAX 0.98 // Must be > 0.0 and <= 1.0
12
+ #if defined(PICKING_VOXEL)
13
+ #define ALPHA_ACCUM_MAX 0.1
14
+ #else
15
+ #define ALPHA_ACCUM_MAX 0.98 // Must be > 0.0 and <= 1.0
16
+ #endif
13
17
 
14
18
  uniform mat3 u_transformDirectionViewToLocal;
15
19
  uniform vec3 u_cameraPositionUv;
@@ -42,6 +46,30 @@ vec4 getStepSize(in SampleData sampleData, in Ray viewRay, in RayShapeIntersecti
42
46
  #endif
43
47
  }
44
48
 
49
+ vec2 packIntToVec2(int value) {
50
+ float shifted = float(value) / 255.0;
51
+ float lowBits = fract(shifted);
52
+ float highBits = floor(shifted) / 255.0;
53
+ return vec2(highBits, lowBits);
54
+ }
55
+
56
+ vec2 packFloatToVec2(float value) {
57
+ float lowBits = fract(value);
58
+ float highBits = floor(value) / 255.0;
59
+ return vec2(highBits, lowBits);
60
+ }
61
+
62
+ int getSampleIndex(in vec3 tileUv) {
63
+ ivec3 voxelDimensions = u_dimensions;
64
+ vec3 tileCoordinate = clamp(tileUv, 0.0, 1.0) * vec3(voxelDimensions);
65
+ ivec3 tileIndex = ivec3(floor(tileCoordinate));
66
+ #if defined(PADDING)
67
+ voxelDimensions += u_paddingBefore + u_paddingAfter;
68
+ tileIndex += u_paddingBefore;
69
+ #endif
70
+ return tileIndex.x + voxelDimensions.x * (tileIndex.y + voxelDimensions.y * tileIndex.z);
71
+ }
72
+
45
73
  void main()
46
74
  {
47
75
  vec4 fragCoord = gl_FragCoord;
@@ -102,6 +130,8 @@ void main()
102
130
  fragmentInput.voxel.viewDirWorld = viewDirWorld;
103
131
  fragmentInput.voxel.surfaceNormal = step.xyz;
104
132
  fragmentInput.voxel.travelDistance = step.w;
133
+ fragmentInput.voxel.tileIndex = sampleDatas[0].megatextureIndex;
134
+ fragmentInput.voxel.sampleIndex = getSampleIndex(sampleDatas[0].tileUv);
105
135
 
106
136
  // Run the custom shader
107
137
  czm_modelMaterial materialOutput;
@@ -164,6 +194,14 @@ void main()
164
194
  discard;
165
195
  }
166
196
  out_FragColor = u_pickColor;
197
+ #elif defined(PICKING_VOXEL)
198
+ // If alpha is 0.0 there is nothing to pick
199
+ if (colorAccum.a == 0.0) {
200
+ discard;
201
+ }
202
+ vec2 megatextureId = packIntToVec2(sampleDatas[0].megatextureIndex);
203
+ vec2 sampleIndex = packIntToVec2(getSampleIndex(sampleDatas[0].tileUv));
204
+ out_FragColor = vec4(megatextureId, sampleIndex);
167
205
  #else
168
206
  out_FragColor = colorAccum;
169
207
  #endif