@pirireis/webglobeplugins 1.0.3 → 1.0.4

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 (210) hide show
  1. package/package.json +2 -2
  2. package/plugins/alarms/alarmFadeInFadeOutPlugin/AlarmTimeLineFadeInFadeOutPlugin.js +399 -0
  3. package/{Math → webglobeplugins/Math}/tessellation/triangle-tessellation.js +82 -4
  4. package/{heatwave → webglobeplugins/heatwave}/isobar.js +3 -0
  5. package/{programs → webglobeplugins/programs}/polygon-on-globe/texture-dem-triangles.js +17 -4
  6. package/webglobeplugins/programs/totems/attachments/adaptive-opacity.js +131 -0
  7. package/{programs/totems → webglobeplugins/programs/totems/attachments}/dem-textures-manager.js +11 -5
  8. package/{programs → webglobeplugins/programs}/vectorfields/logics/drawrectangleparticles.js +34 -28
  9. package/{programs → webglobeplugins/programs}/vectorfields/logics/particle-ubo.js +7 -4
  10. package/{programs → webglobeplugins/programs}/vectorfields/logics/pixelbased.js +3 -7
  11. package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/data/cache.js +10 -8
  12. package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/data/master-worker.js +104 -40
  13. package/webglobeplugins/semiplugins/shape-on-terrain/terrain-polygon/data/polygon-to-triangles.js +76 -0
  14. package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/data/worker-contact.js +3 -2
  15. package/webglobeplugins/semiplugins/shape-on-terrain/terrain-polygon/data/worker.js +162 -0
  16. package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/terrain-polygon.js +66 -3
  17. package/webglobeplugins/semiplugins/shape-on-terrain/terrain-polygon/test-records.js +14 -0
  18. package/{semiplugins → webglobeplugins/semiplugins}/shell/bbox-renderer/object.js +5 -2
  19. package/{tracks → webglobeplugins/tracks}/timetracks/program-line-strip.js +2 -0
  20. package/{util → webglobeplugins/util}/gl-util/buffer/attribute-loader.js +18 -6
  21. package/{util → webglobeplugins/util}/gl-util/uniform-block/manager.js +13 -4
  22. package/{vectorfield → webglobeplugins/vectorfield}/waveparticles/plugin.js +77 -37
  23. package/{vectorfield → webglobeplugins/vectorfield}/wind/adapters/image-to-fields.js +46 -15
  24. package/{vectorfield → webglobeplugins/vectorfield}/wind/plugin-persistant.js +32 -17
  25. package/{vectorfield → webglobeplugins/vectorfield}/wind/plugin.js +4 -4
  26. package/semiplugins/shape-on-terrain/terrain-polygon/data/polygon-to-triangles.js +0 -100
  27. package/semiplugins/shape-on-terrain/terrain-polygon/data/worker.js +0 -125
  28. package/vectorfield/wind/plugin-persistant copy.js +0 -364
  29. package/{Math → webglobeplugins/Math}/angle-calculation.js +0 -0
  30. package/{Math → webglobeplugins/Math}/arc-cdf-points.js +0 -0
  31. package/{Math → webglobeplugins/Math}/arc-generate-points-exponantial.js +0 -0
  32. package/{Math → webglobeplugins/Math}/arc.js +0 -0
  33. package/{Math → webglobeplugins/Math}/bounds/line-bbox.js +0 -0
  34. package/{Math → webglobeplugins/Math}/circle-cdf-points.js +0 -0
  35. package/{Math → webglobeplugins/Math}/circle.js +0 -0
  36. package/{Math → webglobeplugins/Math}/constants.js +0 -0
  37. package/{Math → webglobeplugins/Math}/contour/quadtreecontours.js +0 -0
  38. package/{Math → webglobeplugins/Math}/contour/quadtreecontours1.js +0 -0
  39. package/{Math → webglobeplugins/Math}/finite-line-2d.js +0 -0
  40. package/{Math → webglobeplugins/Math}/haversine.js +0 -0
  41. package/{Math → webglobeplugins/Math}/index.js +0 -0
  42. package/{Math → webglobeplugins/Math}/juction/arc-plane.js +0 -0
  43. package/{Math → webglobeplugins/Math}/juction/line-sphere.js +0 -0
  44. package/{Math → webglobeplugins/Math}/juction/plane-plane.js +0 -0
  45. package/{Math → webglobeplugins/Math}/line.js +0 -0
  46. package/{Math → webglobeplugins/Math}/matrix4.js +0 -0
  47. package/{Math → webglobeplugins/Math}/methods.js +0 -0
  48. package/{Math → webglobeplugins/Math}/plane.js +0 -0
  49. package/{Math → webglobeplugins/Math}/quaternion.js +0 -0
  50. package/{Math → webglobeplugins/Math}/templete-shapes/grid-visually-equal.js +0 -0
  51. package/{Math → webglobeplugins/Math}/tessellation/constants.js +0 -0
  52. package/{Math → webglobeplugins/Math}/tessellation/methods.js +0 -0
  53. package/{Math → webglobeplugins/Math}/tessellation/nearest-value-padding.js +0 -0
  54. package/{Math → webglobeplugins/Math}/tessellation/spherical-triangle-area.js +0 -0
  55. package/{Math → webglobeplugins/Math}/tessellation/tile-merger.js +0 -0
  56. package/{Math → webglobeplugins/Math}/tessellation/types.js +0 -0
  57. package/{Math → webglobeplugins/Math}/types.js +0 -0
  58. package/{Math → webglobeplugins/Math}/utils.js +0 -0
  59. package/{Math → webglobeplugins/Math}/vec3.js +0 -0
  60. package/{Math → webglobeplugins/Math}/xyz-tile.js +0 -0
  61. package/{algorithms → webglobeplugins/algorithms}/search-binary.js +0 -0
  62. package/{altitude-locator → webglobeplugins/altitude-locator}/adaptors.js +0 -0
  63. package/{altitude-locator → webglobeplugins/altitude-locator}/keymethod.js +0 -0
  64. package/{altitude-locator → webglobeplugins/altitude-locator}/plugin.js +0 -0
  65. package/{altitude-locator → webglobeplugins/altitude-locator}/types.js +0 -0
  66. package/{compass-rose → webglobeplugins/compass-rose}/compass-rose-padding-flat.js +0 -0
  67. package/{compass-rose → webglobeplugins/compass-rose}/compass-text-writer.js +0 -0
  68. package/{compass-rose → webglobeplugins/compass-rose}/index.js +0 -0
  69. package/{constants.js → webglobeplugins/constants.js} +0 -0
  70. package/{heatwave → webglobeplugins/heatwave}/datamanager.js +0 -0
  71. package/{heatwave → webglobeplugins/heatwave}/heatwave.js +0 -0
  72. package/{heatwave → webglobeplugins/heatwave}/index.js +0 -0
  73. package/{heatwave → webglobeplugins/heatwave}/texture-point-sampler.js +0 -0
  74. package/{investigation-tools → webglobeplugins/investigation-tools}/draw/tiles/adapters.js +0 -0
  75. package/{investigation-tools → webglobeplugins/investigation-tools}/draw/tiles/tiles.js +0 -0
  76. package/{jest.config.js → webglobeplugins/jest.config.js} +0 -0
  77. package/{pin → webglobeplugins/pin}/pin-object-array1.js +0 -0
  78. package/{pin → webglobeplugins/pin}/pin-point-totem1.js +0 -0
  79. package/{programs → webglobeplugins/programs}/arrowfield/arrow-field.js +0 -0
  80. package/{programs → webglobeplugins/programs}/arrowfield/logic.js +0 -0
  81. package/{programs → webglobeplugins/programs}/data2legend/density-to-legend.js +0 -0
  82. package/{programs → webglobeplugins/programs}/data2legend/point-to-density-texture.js +0 -0
  83. package/{programs → webglobeplugins/programs}/float2legendwithratio/index.js +0 -0
  84. package/{programs → webglobeplugins/programs}/float2legendwithratio/logic.js +0 -0
  85. package/{programs → webglobeplugins/programs}/float2legendwithratio/object.js +0 -0
  86. package/{programs → webglobeplugins/programs}/helpers/blender.js +0 -0
  87. package/{programs → webglobeplugins/programs}/helpers/fadeaway.js +0 -0
  88. package/{programs → webglobeplugins/programs}/index.js +0 -0
  89. package/{programs → webglobeplugins/programs}/line-on-globe/circle-accurate-3d.js +0 -0
  90. package/{programs → webglobeplugins/programs}/line-on-globe/circle-accurate-flat.js +0 -0
  91. package/{programs → webglobeplugins/programs}/line-on-globe/degree-padding-around-circle-3d.js +0 -0
  92. package/{programs → webglobeplugins/programs}/line-on-globe/index.js +0 -0
  93. package/{programs → webglobeplugins/programs}/line-on-globe/lines-color-instanced-flat.js +0 -0
  94. package/{programs → webglobeplugins/programs}/line-on-globe/linestrip/data.js +0 -0
  95. package/{programs → webglobeplugins/programs}/line-on-globe/linestrip/linestrip.js +0 -0
  96. package/{programs → webglobeplugins/programs}/line-on-globe/naive-accurate-flexible.js +0 -0
  97. package/{programs → webglobeplugins/programs}/line-on-globe/util.js +0 -0
  98. package/{programs → webglobeplugins/programs}/picking/pickable-polygon-renderer.js +0 -0
  99. package/{programs → webglobeplugins/programs}/picking/pickable-renderer.js +0 -0
  100. package/{programs → webglobeplugins/programs}/point-on-globe/element-globe-surface-glow.js +0 -0
  101. package/{programs → webglobeplugins/programs}/point-on-globe/element-point-glow.js +0 -0
  102. package/{programs → webglobeplugins/programs}/point-on-globe/square-pixel-point.js +0 -0
  103. package/{programs → webglobeplugins/programs}/programcache.js +0 -0
  104. package/{programs → webglobeplugins/programs}/rings/index.js +0 -0
  105. package/{programs → webglobeplugins/programs}/rings/partial-ring/piece-of-pie.js +0 -0
  106. package/{programs → webglobeplugins/programs}/totems/camera-totem-attactment-interface.js +0 -0
  107. package/{programs → webglobeplugins/programs}/totems/camerauniformblock.js +0 -0
  108. package/{programs → webglobeplugins/programs}/totems/canvas-webglobe-info.js +0 -0
  109. package/{programs → webglobeplugins/programs}/totems/globe-changes.js +0 -0
  110. package/{programs → webglobeplugins/programs}/totems/gpu-selection-uniform-block.js +0 -0
  111. package/{programs → webglobeplugins/programs}/totems/index.js +0 -0
  112. package/{programs → webglobeplugins/programs}/two-d/pixel-padding-for-compass.js +0 -0
  113. package/{programs → webglobeplugins/programs}/util.js +0 -0
  114. package/{programs → webglobeplugins/programs}/vectorfields/logics/constants.js +0 -0
  115. package/{programs → webglobeplugins/programs}/vectorfields/logics/index.js +0 -0
  116. package/{programs → webglobeplugins/programs}/vectorfields/logics/ubo.js +0 -0
  117. package/{programs → webglobeplugins/programs}/vectorfields/pingpongbuffermanager.js +0 -0
  118. package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/bearing-line/adapters.js +0 -0
  119. package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/bearing-line/plugin.js +1 -1
  120. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/bearing-line/types.js +0 -0
  121. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/circle-line-chain/adapters.js +0 -0
  122. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/circle-line-chain/chain-list-map.js +0 -0
  123. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/circle-line-chain/plugin.js +0 -0
  124. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/circle-line-chain/types.js +0 -0
  125. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/range-ring/adapters.js +0 -0
  126. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/range-ring/enum.js +0 -0
  127. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/range-ring/plugin.js +0 -0
  128. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/range-ring/rangeringangletext.js +0 -0
  129. /package/{range-tools-on-terrain → webglobeplugins/range-tools-on-terrain}/range-ring/types.js +0 -0
  130. /package/{semiplugins → webglobeplugins/semiplugins}/interface.js +0 -0
  131. /package/{semiplugins → webglobeplugins/semiplugins}/lightweight/line-plugin.js +0 -0
  132. /package/{semiplugins → webglobeplugins/semiplugins}/lightweight/piece-of-pie-plugin.js +0 -0
  133. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/arc-plugin.js +0 -0
  134. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/circle-plugin.js +0 -0
  135. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/padding-1-degree.js +0 -0
  136. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/adapters.js +0 -0
  137. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/data/index-polygon-map.js +0 -0
  138. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/data/manager.js +0 -0
  139. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/data/random.js +0 -0
  140. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/data/types.js +0 -0
  141. /package/{semiplugins → webglobeplugins/semiplugins}/shape-on-terrain/terrain-polygon/types.js +0 -0
  142. /package/{semiplugins → webglobeplugins/semiplugins}/shell/bbox-renderer/index.js +0 -0
  143. /package/{semiplugins → webglobeplugins/semiplugins}/shell/bbox-renderer/logic.js +0 -0
  144. /package/{semiplugins → webglobeplugins/semiplugins}/type.js +0 -0
  145. /package/{semiplugins → webglobeplugins/semiplugins}/utility/container-plugin.js +0 -0
  146. /package/{semiplugins → webglobeplugins/semiplugins}/utility/object-pass-container-plugin.js +0 -0
  147. /package/{shaders → webglobeplugins/shaders}/fragment-toy/firework.js +0 -0
  148. /package/{shaders → webglobeplugins/shaders}/fragment-toy/singularity.js +0 -0
  149. /package/{tracks → webglobeplugins/tracks}/point-heat-map/adaptors/timetracksplugin-format-to-this.js +0 -0
  150. /package/{tracks → webglobeplugins/tracks}/point-heat-map/index.js +0 -0
  151. /package/{tracks → webglobeplugins/tracks}/point-heat-map/plugin-webworker.js +0 -0
  152. /package/{tracks → webglobeplugins/tracks}/point-heat-map/point-to-heat-map-flow.js +0 -0
  153. /package/{tracks → webglobeplugins/tracks}/point-tracks/key-methods.js +0 -0
  154. /package/{tracks → webglobeplugins/tracks}/point-tracks/plugin.js +0 -0
  155. /package/{tracks → webglobeplugins/tracks}/timetracks/adaptors-line-strip.js +0 -0
  156. /package/{tracks → webglobeplugins/tracks}/timetracks/plugin-line-strip.js +0 -0
  157. /package/{tracks → webglobeplugins/tracks}/timetracks/programpoint-line-strip.js +0 -0
  158. /package/{types.js → webglobeplugins/types.js} +0 -0
  159. /package/{util → webglobeplugins/util}/account/bufferoffsetmanager.js +0 -0
  160. /package/{util → webglobeplugins/util}/account/create-buffermap-orchastration.js +0 -0
  161. /package/{util → webglobeplugins/util}/account/index.js +0 -0
  162. /package/{util → webglobeplugins/util}/account/single-attribute-buffer-management/buffer-manager.js +0 -0
  163. /package/{util → webglobeplugins/util}/account/single-attribute-buffer-management/buffer-orchestrator.js +0 -0
  164. /package/{util → webglobeplugins/util}/account/single-attribute-buffer-management/buffer-orchestrator1.js +0 -0
  165. /package/{util → webglobeplugins/util}/account/single-attribute-buffer-management/index.js +0 -0
  166. /package/{util → webglobeplugins/util}/account/single-attribute-buffer-management/object-store.js +0 -0
  167. /package/{util → webglobeplugins/util}/account/single-attribute-buffer-management/types.js +0 -0
  168. /package/{util → webglobeplugins/util}/account/util.js +0 -0
  169. /package/{util → webglobeplugins/util}/algorithms/index.js +0 -0
  170. /package/{util → webglobeplugins/util}/algorithms/search-binary.js +0 -0
  171. /package/{util → webglobeplugins/util}/build-strategy/static-dynamic.js +0 -0
  172. /package/{util → webglobeplugins/util}/check/index.js +0 -0
  173. /package/{util → webglobeplugins/util}/check/typecheck.js +0 -0
  174. /package/{util → webglobeplugins/util}/frame-counter-trigger.js +0 -0
  175. /package/{util → webglobeplugins/util}/geometry/index.js +0 -0
  176. /package/{util → webglobeplugins/util}/gl-util/buffer/index.js +0 -0
  177. /package/{util → webglobeplugins/util}/gl-util/draw-options/methods.js +0 -0
  178. /package/{util → webglobeplugins/util}/globe-default-gl-states.js +0 -0
  179. /package/{util → webglobeplugins/util}/helper-methods.js +0 -0
  180. /package/{util → webglobeplugins/util}/index.js +0 -0
  181. /package/{util → webglobeplugins/util}/interpolation/index.js +0 -0
  182. /package/{util → webglobeplugins/util}/interpolation/timetrack/index.js +0 -0
  183. /package/{util → webglobeplugins/util}/interpolation/timetrack/timetrack-interpolator.js +0 -0
  184. /package/{util → webglobeplugins/util}/interpolation/timetrack/web-worker.js +0 -0
  185. /package/{util → webglobeplugins/util}/picking/fence.js +0 -0
  186. /package/{util → webglobeplugins/util}/picking/picker-displayer.js +0 -0
  187. /package/{util → webglobeplugins/util}/programs/draw-from-pixel-coords.js +0 -0
  188. /package/{util → webglobeplugins/util}/programs/draw-texture-on-canvas.js +0 -0
  189. /package/{util → webglobeplugins/util}/programs/supersampletotextures.js +0 -0
  190. /package/{util/programs/texturetoglobe.js → webglobeplugins/util/programs/texturetoglobe_delete.js} +0 -0
  191. /package/{util → webglobeplugins/util}/shaderfunctions/geometrytransformations.js +0 -0
  192. /package/{util → webglobeplugins/util}/shaderfunctions/index.js +0 -0
  193. /package/{util → webglobeplugins/util}/shaderfunctions/nodata.js +0 -0
  194. /package/{util → webglobeplugins/util}/shaderfunctions/noisefunctions.js +0 -0
  195. /package/{util → webglobeplugins/util}/webglobjectbuilders.js +0 -0
  196. /package/{vectorfield → webglobeplugins/vectorfield}/arrowfield/adaptor.js +0 -0
  197. /package/{vectorfield → webglobeplugins/vectorfield}/arrowfield/index.js +0 -0
  198. /package/{vectorfield → webglobeplugins/vectorfield}/arrowfield/plugin.js +0 -0
  199. /package/{vectorfield → webglobeplugins/vectorfield}/waveparticles/adaptor.js +0 -0
  200. /package/{vectorfield → webglobeplugins/vectorfield}/waveparticles/index.js +0 -0
  201. /package/{vectorfield → webglobeplugins/vectorfield}/wind/adapters/types.js +0 -0
  202. /package/{vectorfield → webglobeplugins/vectorfield}/wind/imagetovectorfieldandmagnitude.js +0 -0
  203. /package/{vectorfield → webglobeplugins/vectorfield}/wind/index.js +0 -0
  204. /package/{vectorfield → webglobeplugins/vectorfield}/wind/vectorfieldimage.js +0 -0
  205. /package/{write-text → webglobeplugins/write-text}/context-text-bulk.js +0 -0
  206. /package/{write-text → webglobeplugins/write-text}/context-text3.js +0 -0
  207. /package/{write-text → webglobeplugins/write-text}/context-text4.js +0 -0
  208. /package/{write-text → webglobeplugins/write-text}/context-textDELETE.js +0 -0
  209. /package/{write-text → webglobeplugins/write-text}/objectarraylabels/index.js +0 -0
  210. /package/{write-text → webglobeplugins/write-text}/objectarraylabels/objectarraylabels.js +0 -0
@@ -0,0 +1,131 @@
1
+ import { noRegisterGlobeProgramCache } from "../../programcache";
2
+ import { CameraUniformBlockTotemCache } from "../camerauniformblock";
3
+ const epsilon = 0.1;
4
+ export function createSmoothstepOpacityPolicy(minZoom = 4, maxZoom = 12) {
5
+ const denom = maxZoom - minZoom;
6
+ if (!Number.isFinite(denom) || denom === 0) {
7
+ throw new Error("createSmoothstepOpacityPolicy: invalid zoom range");
8
+ }
9
+ const smoothstep = (x) => x * x * (3 - 2 * x);
10
+ return (zoomLevel) => {
11
+ const t = (zoomLevel - minZoom) / denom;
12
+ const c = Math.min(1, Math.max(0, t));
13
+ return 1 - smoothstep(c);
14
+ };
15
+ }
16
+ /**
17
+ * Hysteresis policy: reduces flicker by using separate enter/exit zooms.
18
+ * Example: fade-in begins at enterStart, but won’t fade-out until exitEnd.
19
+ */
20
+ export function createHysteresisOpacityPolicy(params) {
21
+ const { enterStart, enterEnd, exitStart, exitEnd } = params;
22
+ if (!(exitEnd <= exitStart && exitStart <= enterStart && enterStart <= enterEnd)) {
23
+ throw new Error("createHysteresisOpacityPolicy: expected exitEnd <= exitStart <= enterStart <= enterEnd");
24
+ }
25
+ const lerp01 = (x, a, b) => {
26
+ if (a === b)
27
+ return x >= b ? 1 : 0;
28
+ const t = (x - a) / (b - a);
29
+ return Math.min(1, Math.max(0, t));
30
+ };
31
+ return (zoomLevel, prevOpacity) => {
32
+ // If we were mostly “off”, only allow rising once we hit the enter band.
33
+ if (prevOpacity <= 0.5) {
34
+ if (zoomLevel <= exitStart)
35
+ return lerp01(zoomLevel, exitEnd, exitStart) * 0; // clamp to 0 band
36
+ if (zoomLevel < enterStart)
37
+ return 0;
38
+ return lerp01(zoomLevel, enterStart, enterEnd);
39
+ }
40
+ // If we were mostly “on”, only allow falling once we hit the exit band.
41
+ if (zoomLevel >= enterStart)
42
+ return lerp01(zoomLevel, enterStart, enterEnd);
43
+ if (zoomLevel > exitStart)
44
+ return 1;
45
+ // decreasing band
46
+ return 1 - lerp01(zoomLevel, exitEnd, exitStart);
47
+ };
48
+ }
49
+ /**
50
+ * Curve policy: caller supplies any curve f(t) where t is normalized [0..1].
51
+ * This is the most flexible option (e.g., gamma, custom spline, etc.).
52
+ */
53
+ export function createCurveOpacityPolicy(params) {
54
+ const { minZoom, maxZoom, curve } = params;
55
+ const denom = maxZoom - minZoom;
56
+ if (!Number.isFinite(denom) || denom === 0) {
57
+ throw new Error("createCurveOpacityPolicy: invalid zoom range");
58
+ }
59
+ return (zoomLevel) => {
60
+ const t = (zoomLevel - minZoom) / denom;
61
+ const c = Math.min(1, Math.max(0, t));
62
+ const y = curve(c);
63
+ return Math.min(1, Math.max(0, y));
64
+ };
65
+ }
66
+ class AdaptiveOpacityAttachment {
67
+ globe;
68
+ cameraUniformBlock;
69
+ lastZoomLevel = -1;
70
+ isChangedFlag = false;
71
+ registry = new Map();
72
+ defaultAdaptiveOpacityPolicy = createSmoothstepOpacityPolicy(5.5, 7);
73
+ constructor(globe) {
74
+ this.globe = globe;
75
+ this.cameraUniformBlock = CameraUniformBlockTotemCache.get(this.globe);
76
+ this.cameraUniformBlock.registerAttachment(this);
77
+ }
78
+ update() {
79
+ const zoomLevel = this.globe.api_GetCurrentLODWithDecimal();
80
+ if (epsilon > Math.abs(this.lastZoomLevel - zoomLevel)) {
81
+ this._setIsChanged(false);
82
+ return;
83
+ }
84
+ ;
85
+ this._setIsChanged(true);
86
+ this.lastZoomLevel = zoomLevel;
87
+ this.registry.forEach((plugin) => {
88
+ plugin.__adaptiveOpacity_set((plugin.__adaptivePolicy || this.defaultAdaptiveOpacityPolicy)(zoomLevel, plugin.__adaptiveOpacity));
89
+ });
90
+ }
91
+ registerPlugin(plugin) {
92
+ if (this.registry.has(plugin.id)) {
93
+ return false;
94
+ }
95
+ this.registry.set(plugin.id, plugin);
96
+ plugin.__adaptiveOpacity_set((plugin.__adaptivePolicy ||
97
+ this.defaultAdaptiveOpacityPolicy)(this.lastZoomLevel));
98
+ return true;
99
+ }
100
+ unregisterPlugin(plugin) {
101
+ if (!this.registry.has(plugin.id)) {
102
+ return false;
103
+ }
104
+ this.registry.delete(plugin.id);
105
+ return true;
106
+ }
107
+ _setIsChanged(value) {
108
+ this.isChangedFlag = value;
109
+ }
110
+ get isChanged() {
111
+ return this.isChangedFlag;
112
+ }
113
+ free() {
114
+ this.cameraUniformBlock.unregisterAttachment(this);
115
+ }
116
+ }
117
+ export const AdaptiveOpacityAttachmentObserver = Object.freeze({
118
+ subscribe: (subscriber) => {
119
+ const attachment = noRegisterGlobeProgramCache.getProgram(subscriber.globe, AdaptiveOpacityAttachment);
120
+ if (!attachment.registerPlugin(subscriber)) {
121
+ noRegisterGlobeProgramCache.releaseProgram(subscriber.globe, AdaptiveOpacityAttachment);
122
+ }
123
+ },
124
+ unsubscribe: (subscriber) => {
125
+ const attachment = noRegisterGlobeProgramCache.getProgram(subscriber.globe, AdaptiveOpacityAttachment);
126
+ if (attachment.unregisterPlugin(subscriber)) {
127
+ subscriber.__adaptiveOpacity_set(1);
128
+ noRegisterGlobeProgramCache.releaseProgram(subscriber.globe, AdaptiveOpacityAttachment);
129
+ }
130
+ }
131
+ });
@@ -1,7 +1,7 @@
1
- import { mergeMeshes } from "../../Math/tessellation/tile-merger";
2
- import { globeBBoxToXYBBOX } from "../../Math/methods";
3
- import { noRegisterGlobeProgramCache } from "../programcache";
4
- import { CameraUniformBlockTotemCache } from "./camerauniformblock";
1
+ import { mergeMeshes } from "../../../Math/tessellation/tile-merger";
2
+ import { globeBBoxToXYBBOX } from "../../../Math/methods";
3
+ import { noRegisterGlobeProgramCache } from "../../programcache";
4
+ import { CameraUniformBlockTotemCache } from "../camerauniformblock";
5
5
  export const DEM_TEXTURE_BLOCK_STRING = `
6
6
  layout(std140) uniform DemTextureUniformBlock {
7
7
  vec4 u_demTextureBBOX[6]; // 96 bytes
@@ -256,10 +256,16 @@ export class DemTextureManager {
256
256
  export const DemTextureManagerCache = Object.freeze({
257
257
  get: (globe) => {
258
258
  const result = noRegisterGlobeProgramCache.getProgram(globe, DemTextureManager);
259
- window.demManager = result;
259
+ // window.demManager = result;
260
260
  return result;
261
261
  },
262
262
  release: (globe) => {
263
263
  noRegisterGlobeProgramCache.releaseProgram(globe, DemTextureManager);
264
264
  }
265
265
  });
266
+ // // declare demManager window global
267
+ // declare global {
268
+ // interface Window {
269
+ // demManager: DemTextureManager;
270
+ // }
271
+ // }
@@ -1,3 +1,6 @@
1
+ /**
2
+ * Author: Toprak Nihat Deniz Ozturk
3
+ */
1
4
  import { createProgram } from "../../../util/webglobjectbuilders";
2
5
  import { glProgramCache } from "../../programcache";
3
6
  import { ParticleUBO } from "./particle-ubo";
@@ -9,7 +12,7 @@ precision highp float;
9
12
  ` + ParticleUBO.glslCode() + `
10
13
  uniform sampler2D u_vector_field;
11
14
  uniform sampler2D u_color_field;
12
- uniform sampler2D u_speed_field;
15
+ uniform sampler2D u_magnitude_field;
13
16
  in vec2 in_position;
14
17
  out vec4 base_color;
15
18
 
@@ -24,35 +27,38 @@ vec2 read_value(const vec2 uv) {
24
27
 
25
28
 
26
29
  vec2 lookup_wind(const vec2 uv) { // gerek kalmayabilir. sampler linear methodu ayni isi yapiyor
27
- // return texture(u_vector_field, uv).rg; // lower-res hardware filtering
28
- vec2 res = vec2(textureSize(u_vector_field, 0));
29
- vec2 px = 1.0 / res;
30
- vec2 vc = (floor(uv * res)) * px;
31
- vec2 f = fract(uv * res);
32
- vec2 tl = read_value(vc).rg;
33
- vec2 tr = read_value(vc + vec2(px.x, 0)).rg;
34
- vec2 bl = read_value(vc + vec2(0, px.y)).rg;
35
- vec2 br = read_value(vc + px).rg;
30
+ vec2 value =texture(u_vector_field, uv).rg; // lower-res hardware filtering
31
+ // normalize value
32
+ float length = length(value);
33
+ if ( length == 0.0 || value.x == escape_value || value.y == escape_value) {
34
+ return vec2(0.0);
35
+ }
36
+ return value/length;
36
37
 
37
- return mix(mix(tl, tr, f.x), mix(bl, br, f.x), f.y);
38
+ // vec2 res = vec2(textureSize(u_vector_field, 0));
39
+ // vec2 px = 1.0 / res;
40
+ // vec2 vc = (floor(uv * res)) * px;
41
+ // vec2 f = fract(uv * res);
42
+ // vec2 tl = read_value(vc).rg;
43
+ // vec2 tr = read_value(vc + vec2(px.x, 0)).rg;
44
+ // vec2 bl = read_value(vc + vec2(0, px.y)).rg;
45
+ // vec2 br = read_value(vc + px).rg;
46
+
47
+ // return mix(mix(tl, tr, f.x), mix(bl, br, f.x), f.y);
38
48
  }
39
49
 
40
50
 
41
51
  void main(){
42
- if ( use_speed_field != 0.0 ) {
43
- base_color = vec4(0.0);
44
- return;
45
- float speed = texture(u_speed_field, in_position).r;
46
- if ( speed < min_speed_threshold || speed > max_speed_threshold ) {
52
+ if ( use_magnitude_field > 0.5) {
53
+ float magnitude = texture(u_magnitude_field, in_position).r;
54
+
55
+ if ( magnitude < min_magnitude_threshold || magnitude > max_magnitude_threshold ) {
47
56
  base_color = vec4(0.0);
48
57
  return;
49
58
  }
50
59
  }
51
60
 
52
61
  vec2 direction_vector = lookup_wind(in_position);
53
- if (direction_vector.r == 0.0 && direction_vector.g == 0.0) return;
54
-
55
-
56
62
  vec2 limp;
57
63
  if ( 0 == gl_VertexID) { limp = -tail_wing_base_limp; }
58
64
  else if ( 1 == gl_VertexID) { limp = vec2( tail_wing_base_limp.x, -tail_wing_base_limp.y); }
@@ -65,7 +71,7 @@ void main(){
65
71
  vec2 pos = in_position * 2.0 - 1.0;
66
72
  gl_Position = vec4(pos + limp, 0.0, 1.0);
67
73
 
68
- base_color = use_color_field != 0.0 ? texture(u_color_field, in_position).rgba : vec4(color, 1.0);
74
+ base_color = use_color_field != 0.0 ? texture(u_color_field, in_position).rgba : color;
69
75
  }`;
70
76
  const fragmentShaderSource = `#version 300 es
71
77
  precision highp float;
@@ -79,15 +85,15 @@ export class DrawRectangleParticleProgram {
79
85
  program;
80
86
  _vector_field_location;
81
87
  _color_texture_location;
82
- _speed_field_location;
88
+ _magnitude_field_location;
83
89
  constructor(gl) {
84
90
  this.gl = gl;
85
91
  // this.decoyBuffer = new DecoyBufferManager(gl);
86
- const { program, _vector_field_location, _color_texture_location, _speed_field_location } = this._createProgram();
92
+ const { program, _vector_field_location, _color_texture_location, _magnitude_field_location } = this._createProgram();
87
93
  this.program = program;
88
94
  this._vector_field_location = _vector_field_location;
89
95
  this._color_texture_location = _color_texture_location;
90
- this._speed_field_location = _speed_field_location;
96
+ this._magnitude_field_location = _magnitude_field_location;
91
97
  }
92
98
  _createProgram() {
93
99
  const gl = this.gl;
@@ -100,7 +106,7 @@ export class DrawRectangleParticleProgram {
100
106
  program,
101
107
  _vector_field_location: gl.getUniformLocation(program, 'u_vector_field'),
102
108
  _color_texture_location: gl.getUniformLocation(program, 'u_color_field'),
103
- _speed_field_location: gl.getUniformLocation(program, 'u_speed_field')
109
+ _magnitude_field_location: gl.getUniformLocation(program, 'u_magnitude_field')
104
110
  };
105
111
  }
106
112
  /**
@@ -108,7 +114,7 @@ export class DrawRectangleParticleProgram {
108
114
  * @param vectorFieldTexture | RG32F texture R: x, G: y
109
115
  * @param uboManager | WaveParticalUboManager under ubo.js
110
116
  */
111
- draw(bufferManager, vectorFieldTexture, uboManager, colorFieldTexture, speedFieldTexture) {
117
+ draw(bufferManager, vectorFieldTexture, uboManager, colorFieldTexture, magnitudeFieldTexture) {
112
118
  const { gl, program } = this;
113
119
  gl.useProgram(program);
114
120
  gl.bindVertexArray(bufferManager.getSourceVao());
@@ -119,10 +125,10 @@ export class DrawRectangleParticleProgram {
119
125
  gl.uniform1i(this._color_texture_location, 1);
120
126
  gl.bindTexture(gl.TEXTURE_2D, colorFieldTexture);
121
127
  }
122
- if (speedFieldTexture) {
128
+ if (magnitudeFieldTexture) {
123
129
  gl.activeTexture(gl.TEXTURE2);
124
- gl.uniform1i(this._speed_field_location, 2);
125
- gl.bindTexture(gl.TEXTURE_2D, speedFieldTexture);
130
+ gl.uniform1i(this._magnitude_field_location, 2);
131
+ gl.bindTexture(gl.TEXTURE_2D, magnitudeFieldTexture);
126
132
  }
127
133
  gl.activeTexture(gl.TEXTURE0);
128
134
  gl.uniform1i(this._vector_field_location, 0);
@@ -1,16 +1,19 @@
1
+ /**
2
+ * Author: Toprak Nihat Deniz Ozturk
3
+ */
1
4
  import { UBO_BINDING_POINTS } from "./constants";
2
5
  import { UniformBlockManager } from "../../../util/gl-util/uniform-block/manager";
3
6
  const INITIAL_UBO_DATA = /*@__PURE__*/ new Float32Array([93.17, 0.2, 1.0, 7.0, 1.0, 1.0, 1.0, 0.05, 2000, 2000, 0]);
4
7
  export const ParticleUBO = /*@__PURE__*/ new UniformBlockManager("Seawave_UBO", [
8
+ { name: "color", type: "vec4", value: new Float32Array([1.0, 1.0, 1.0, 1.0]) },
5
9
  { name: "tail_wing_base_limp", type: "vec2", value: INITIAL_UBO_DATA.slice(2, 4) },
6
10
  { name: "draw_texture_size", type: "vec2", value: INITIAL_UBO_DATA.slice(8, 10) },
7
11
  { name: "random_seed", type: "float", value: INITIAL_UBO_DATA.slice(0, 1) },
8
12
  { name: "range", type: "float", value: INITIAL_UBO_DATA.slice(1, 2) },
9
13
  { name: "escape_value", type: "float", value: INITIAL_UBO_DATA.slice(10, 11) },
10
14
  { name: "drop_rate", type: "float", value: INITIAL_UBO_DATA.slice(7, 8) },
11
- { name: "color", type: "vec3", value: INITIAL_UBO_DATA.slice(4, 7) },
12
15
  { name: "use_color_field", type: "float", value: new Float32Array([0]) },
13
- { name: "use_speed_field", type: "float", value: new Float32Array([0]) },
14
- { name: "min_speed_threshold", type: "float", value: new Float32Array([0]) },
15
- { name: "max_speed_threshold", type: "float", value: new Float32Array([10000]) },
16
+ { name: "use_magnitude_field", type: "float", value: new Float32Array([0]) },
17
+ { name: "min_magnitude_threshold", type: "float", value: new Float32Array([0]) },
18
+ { name: "max_magnitude_threshold", type: "float", value: new Float32Array([10000]) },
16
19
  ], UBO_BINDING_POINTS.SEAWAVE);
@@ -45,17 +45,13 @@ vec2 random_position(vec2 st){
45
45
 
46
46
  void main(){
47
47
  vec2 vec = lookup_wind(in_position).xy;
48
- if (vec.x == 0.0 && vec.y == 0.0){
49
- out_position = random_position(in_position);
50
- return;
51
- }
52
48
  float random_value = random(in_position + random_seed);
53
- if (random_value < drop_rate){
49
+ if (vec.x == 0.0 && vec.y == 0.0 || random_value < drop_rate) {
54
50
  out_position = random_position(in_position);
55
51
  return;
56
52
  }
57
- float speed_multiplier = use_speed_field != 0.0 ? texture(speed_field, in_position).r : 1.0;
58
- out_position = in_position + (vec / draw_texture_size) * range * speed_multiplier * tail_wing_base_limp.y;
53
+
54
+ out_position = in_position + (vec / draw_texture_size) * range * tail_wing_base_limp.x;
59
55
  }
60
56
  `;
61
57
  const fragmentShaderSource = `#version 300 es
@@ -1,20 +1,24 @@
1
1
  import { createTriangleTessellationMeta } from "../../../../Math/tessellation/triangle-tessellation";
2
- import { triangulation } from "./polygon-to-triangles";
2
+ import { triangulation, calculateRealEdges } from "./polygon-to-triangles";
3
3
  import RBush from "rbush";
4
4
  import { RADIAN } from "../../../../Math/methods";
5
5
  // TODO: use type instead of any
6
- function _entry(polygon, kmThreshold) {
6
+ function _entry(polygon) {
7
7
  __polygonInputWGS84ToRadian(polygon);
8
- const trianglesData = triangulation(polygon, kmThreshold);
8
+ const trianglesData = triangulation(polygon);
9
9
  const cacheTriangles = [];
10
+ const realEdges = calculateRealEdges(polygon.geometry, trianglesData.indices);
10
11
  for (let i = 0; i < trianglesData.indices.length; i += 3) {
11
12
  const idx0 = trianglesData.indices[i] * 2;
12
13
  const idx1 = trianglesData.indices[i + 1] * 2;
13
14
  const idx2 = trianglesData.indices[i + 2] * 2;
15
+ const idx0RealEdge = realEdges[i];
16
+ const idx1RealEdge = realEdges[i + 1];
17
+ const idx2RealEdge = realEdges[i + 2];
14
18
  const v0 = [trianglesData.vertices[idx0], trianglesData.vertices[idx0 + 1]];
15
19
  const v1 = [trianglesData.vertices[idx1], trianglesData.vertices[idx1 + 1]];
16
20
  const v2 = [trianglesData.vertices[idx2], trianglesData.vertices[idx2 + 1]];
17
- const tessellationMeta = createTriangleTessellationMeta(v0, v1, v2);
21
+ const tessellationMeta = createTriangleTessellationMeta(v0, v1, v2, idx0RealEdge, idx1RealEdge, idx2RealEdge);
18
22
  cacheTriangles.push({
19
23
  polygon: polygon,
20
24
  offset: i / 3,
@@ -38,11 +42,9 @@ function __polygonInputWGS84ToRadian(polygon) {
38
42
  }
39
43
  export class Cache {
40
44
  cache = new Map();
41
- kmThreshold;
42
45
  rbush = new RBush();
43
46
  bboxes = [];
44
- constructor(kmThreshold) {
45
- this.kmThreshold = kmThreshold;
47
+ constructor() {
46
48
  }
47
49
  clear() {
48
50
  this.cache.clear();
@@ -52,7 +54,7 @@ export class Cache {
52
54
  if (this.cache.has(key)) {
53
55
  this.remove(key);
54
56
  }
55
- const triangles = _entry(polygon, this.kmThreshold);
57
+ const triangles = _entry(polygon);
56
58
  this.rbush.load(triangles);
57
59
  this.cache.set(key, { polygon: polygon, triangles });
58
60
  }
@@ -1,50 +1,74 @@
1
1
  /// <reference lib="webworker" />
2
+ /* eslint-disable no-restricted-globals */
3
+ import { uint32Escape } from "../../../../Math/tessellation/triangle-tessellation";
2
4
  const _workers = [];
3
5
  const _workerMap = new Map();
4
- let _maxWorkers = 4; // Default, updated in init
6
+ let _maxWorkers = 4;
5
7
  let _nextWorkerIndex = 0;
6
- // Configuration state to pass to new workers or re-broadcast
7
8
  let _pickableState;
9
+ let _arcState;
8
10
  let _variativeColorsOn;
9
- // Initialize workers
11
+ // NEW: barrier state for "wait for all outputs of the last dispatched batch"
12
+ let _batchInFlight = false;
13
+ let _batchPending = 0;
10
14
  function initWorkers() {
11
- _maxWorkers = Math.max(1, (navigator.hardwareConcurrency || 4) - 1);
12
- for (let i = 0; i < _maxWorkers; i++) {
15
+ _maxWorkers = Math.max(1, ((navigator.hardwareConcurrency - 2) || 4) - 1);
16
+ console.log(`TerrainPolygon: initializing ${_maxWorkers} workers.`);
17
+ for (let i = 0; i < _maxWorkers; i++)
13
18
  addWorker();
14
- }
15
19
  }
16
20
  function addWorker() {
21
+ // IMPORTANT: use the TS entry so the bundler can build the worker module.
17
22
  // @ts-ignore
18
- const worker = new Worker(new URL("./worker.js", import.meta.url), { type: 'module' });
23
+ const worker = new Worker(new URL("./worker.ts", import.meta.url), { type: "module" });
19
24
  const wrapper = {
20
25
  worker,
21
26
  inProgress: false,
22
27
  insertDeleteQueue: [],
23
28
  lastBBOXData: null,
24
29
  itemCount: 0,
25
- lastOutput: null
30
+ lastOutput: null,
26
31
  };
27
32
  worker.onmessage = (event) => {
28
33
  wrapper.inProgress = false;
29
34
  wrapper.lastOutput = event.data;
30
- mergeAndSendResults();
35
+ // Barrier: only merge/send after all workers dispatched for this batch have finished.
36
+ if (_batchInFlight) {
37
+ _batchPending = Math.max(0, _batchPending - 1);
38
+ if (_batchPending === 0) {
39
+ _batchInFlight = false;
40
+ mergeAndSendResults();
41
+ // Start next batch (if anything queued while we were waiting)
42
+ triggerAllWorkers();
43
+ }
44
+ return;
45
+ }
46
+ // Fallback (should rarely happen): if not in a batch, allow immediate draining.
31
47
  sendToSubWorker(wrapper);
32
48
  };
33
- // Initialize sub-worker with current global state
34
49
  worker.postMessage({
35
50
  pickableState: _pickableState,
36
51
  variativeColorsOn: _variativeColorsOn,
52
+ arcState: _arcState,
37
53
  insertDeleteQueue: [],
38
54
  bboxes: null,
39
55
  });
40
56
  _workers.push(wrapper);
41
57
  }
42
58
  function mergeAndSendResults() {
43
- let totalVec3s = 0;
44
- let totalIndices = 0;
45
- let totalLongLats = 0;
46
- let totalPickIndices = 0;
47
- let totalVariativeColors = 0;
59
+ // Match the working master-worker.js sentinel/header layout
60
+ const BASE_VEC3S = 9; // 3 vertices * 3
61
+ const BASE_INDICES = 3;
62
+ const BASE_LONGLATS = 6; // 3 vertices * 2
63
+ const BASE_PICKINDICES = 3;
64
+ const BASE_VARIATIVE = _variativeColorsOn ? 12 : 0; // 3 vertices * 4
65
+ const BASE_REAL_EDGE_ARC_INDICES = _arcState ? 1 : 0; // reserve header only when arc mode is enabled
66
+ let totalVec3s = BASE_VEC3S;
67
+ let totalIndices = BASE_INDICES;
68
+ let totalLongLats = BASE_LONGLATS;
69
+ let totalPickIndices = BASE_PICKINDICES;
70
+ let totalVariativeColors = BASE_VARIATIVE;
71
+ let totalRealEdgeArcIndices = BASE_REAL_EDGE_ARC_INDICES;
48
72
  const validOutputs = [];
49
73
  for (const w of _workers) {
50
74
  if (w.lastOutput) {
@@ -52,6 +76,9 @@ function mergeAndSendResults() {
52
76
  totalVec3s += w.lastOutput.vec3s.length;
53
77
  totalIndices += w.lastOutput.indices.length;
54
78
  totalLongLats += w.lastOutput.longLats.length;
79
+ if (_arcState && w.lastOutput.realEdgeArcIndices) {
80
+ totalRealEdgeArcIndices += w.lastOutput.realEdgeArcIndices.length;
81
+ }
55
82
  if (w.lastOutput.pickIndices)
56
83
  totalPickIndices += w.lastOutput.pickIndices.length;
57
84
  if (w.lastOutput.variativeColors)
@@ -64,21 +91,50 @@ function mergeAndSendResults() {
64
91
  vec3s: new Float32Array(totalVec3s),
65
92
  indices: new Uint32Array(totalIndices),
66
93
  longLats: new Float32Array(totalLongLats),
94
+ realEdgeArcIndices: _arcState && totalRealEdgeArcIndices > 0 ? new Uint32Array(totalRealEdgeArcIndices) : null,
67
95
  pickIndices: totalPickIndices > 0 ? new Float32Array(totalPickIndices) : null,
68
- variativeColors: totalVariativeColors > 0 ? new Float32Array(totalVariativeColors) : null
96
+ variativeColors: totalVariativeColors > 0 ? new Uint8Array(totalVariativeColors) : null,
69
97
  };
70
- let offsetVec3s = 0;
71
- let offsetIndices = 0;
72
- let offsetLongLats = 0;
73
- let offsetPickIndices = 0;
74
- let offsetVariativeColors = 0;
75
- let vertexOffset = 0;
98
+ // Sentinel/header (as in master-worker.js)
99
+ merged.vec3s[0] = NaN;
100
+ merged.vec3s[1] = NaN;
101
+ merged.vec3s[2] = NaN;
102
+ // Uint32Array cannot hold NaN; writing NaN becomes 0. Keep the header reserved anyway.
103
+ merged.indices[0] = 0;
104
+ merged.indices[1] = 0;
105
+ merged.indices[2] = 0;
106
+ merged.longLats[0] = NaN;
107
+ merged.longLats[1] = NaN;
108
+ if (_arcState && merged.realEdgeArcIndices) {
109
+ merged.realEdgeArcIndices[0] = 0; // header/sentinel
110
+ }
111
+ if (merged.variativeColors) {
112
+ // Sentinel/header (no-color marker)
113
+ merged.variativeColors[0] = 0;
114
+ merged.variativeColors[1] = 0;
115
+ merged.variativeColors[2] = 0;
116
+ merged.variativeColors[3] = 255;
117
+ }
118
+ let offsetVec3s = BASE_VEC3S;
119
+ let offsetIndices = BASE_INDICES;
120
+ let offsetLongLats = BASE_LONGLATS;
121
+ let offsetPickIndices = BASE_PICKINDICES;
122
+ let offsetVariativeColors = BASE_VARIATIVE;
123
+ let vertexOffset = 3; // reserve 3 vertices
124
+ let arcCounter = BASE_REAL_EDGE_ARC_INDICES;
76
125
  for (const out of validOutputs) {
77
126
  merged.vec3s.set(out.vec3s, offsetVec3s);
78
127
  offsetVec3s += out.vec3s.length;
79
128
  for (let i = 0; i < out.indices.length; i++) {
80
129
  merged.indices[offsetIndices + i] = out.indices[i] + vertexOffset;
81
130
  }
131
+ if (_arcState && merged.realEdgeArcIndices && out.realEdgeArcIndices) {
132
+ for (let i = 0; i < out.realEdgeArcIndices.length; i++) {
133
+ const realEdgeIndice = out.realEdgeArcIndices[i];
134
+ merged.realEdgeArcIndices[arcCounter++] =
135
+ realEdgeIndice === uint32Escape ? uint32Escape : realEdgeIndice + vertexOffset;
136
+ }
137
+ }
82
138
  offsetIndices += out.indices.length;
83
139
  vertexOffset += out.vec3s.length / 3;
84
140
  merged.longLats.set(out.longLats, offsetLongLats);
@@ -92,51 +148,59 @@ function mergeAndSendResults() {
92
148
  offsetVariativeColors += out.variativeColors.length;
93
149
  }
94
150
  }
95
- // Send merged result to Main Thread
96
151
  self.postMessage(merged, [
97
152
  merged.vec3s.buffer,
98
153
  merged.indices.buffer,
99
154
  merged.longLats.buffer,
100
155
  ...(merged.pickIndices ? [merged.pickIndices.buffer] : []),
101
- ...(merged.variativeColors ? [merged.variativeColors.buffer] : [])
156
+ ...(merged.variativeColors ? [merged.variativeColors.buffer] : []),
157
+ ...(merged.realEdgeArcIndices ? [merged.realEdgeArcIndices.buffer] : []),
102
158
  ]);
103
159
  }
104
160
  function sendToSubWorker(wrapper) {
105
161
  if (wrapper.inProgress)
106
- return;
162
+ return false;
107
163
  if (wrapper.insertDeleteQueue.length === 0 && wrapper.lastBBOXData === null)
108
- return;
164
+ return false;
109
165
  wrapper.inProgress = true;
110
166
  wrapper.worker.postMessage({
111
- pickableState: undefined, // State is set on init, only send updates if needed
167
+ pickableState: undefined,
112
168
  variativeColorsOn: undefined,
169
+ arcState: undefined,
113
170
  bboxes: wrapper.lastBBOXData,
114
171
  insertDeleteQueue: wrapper.insertDeleteQueue,
115
172
  });
116
173
  wrapper.lastBBOXData = null;
117
174
  wrapper.insertDeleteQueue = [];
175
+ return true;
118
176
  }
119
177
  function triggerAllWorkers() {
178
+ // If a batch is already running, do not start another one.
179
+ if (_batchInFlight)
180
+ return;
181
+ let dispatched = 0;
120
182
  for (const w of _workers) {
121
- sendToSubWorker(w);
183
+ if (sendToSubWorker(w))
184
+ dispatched++;
185
+ }
186
+ // Start barrier only if we actually dispatched work.
187
+ if (dispatched > 0) {
188
+ _batchInFlight = true;
189
+ _batchPending = dispatched;
122
190
  }
123
191
  }
124
- // Handle messages from Main Thread
125
192
  self.onmessage = (event) => {
126
- const { bboxes, insertDeleteQueue, pickableState, variativeColorsOn } = event.data;
127
- // Initialize if not already done
193
+ const { bboxes, insertDeleteQueue, pickableState, variativeColorsOn, arcState } = event.data;
128
194
  if (_workers.length === 0) {
129
195
  _pickableState = pickableState;
130
196
  _variativeColorsOn = variativeColorsOn;
197
+ _arcState = arcState;
131
198
  initWorkers();
132
199
  }
133
- // Handle BBOX updates
134
200
  if (bboxes) {
135
- for (const w of _workers) {
201
+ for (const w of _workers)
136
202
  w.lastBBOXData = bboxes;
137
- }
138
203
  }
139
- // Handle Insert/Delete
140
204
  if (insertDeleteQueue && insertDeleteQueue.length > 0) {
141
205
  if (insertDeleteQueue[0] === "__CLEAR_ALL_ITEMS__") {
142
206
  _workerMap.clear();
@@ -148,7 +212,7 @@ self.onmessage = (event) => {
148
212
  }
149
213
  else {
150
214
  for (const item of insertDeleteQueue) {
151
- if (typeof item === 'string') {
215
+ if (typeof item === "string") {
152
216
  // Delete
153
217
  const workerIdx = _workerMap.get(item);
154
218
  if (workerIdx !== undefined) {
@@ -158,7 +222,7 @@ self.onmessage = (event) => {
158
222
  }
159
223
  }
160
224
  else {
161
- // Insert
225
+ // Insert/Update: MUST enqueue the full polygon payload, not just the key
162
226
  let workerIdx = _workerMap.get(item.key);
163
227
  if (workerIdx === undefined) {
164
228
  workerIdx = _nextWorkerIndex;
@@ -166,12 +230,12 @@ self.onmessage = (event) => {
166
230
  _workers[workerIdx].itemCount++;
167
231
  _nextWorkerIndex = (_nextWorkerIndex + 1) % _workers.length;
168
232
  }
169
- _workers[workerIdx].insertDeleteQueue.push(item.key);
233
+ _workers[workerIdx].insertDeleteQueue.push(item);
170
234
  }
171
235
  }
172
236
  }
173
237
  }
174
- // Trigger all workers to process the new data
238
+ // This now starts a "batch" and waits for all dispatched workers to respond
239
+ // before mergeAndSendResults() is called.
175
240
  triggerAllWorkers();
176
241
  };
177
- export {};