@pirireis/webglobeplugins 0.8.6 → 0.8.7
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.
- package/bearing-line/plugin.js +51 -43
- package/circle-line-chain/plugin.js +52 -44
- package/compass-rose/compass-rose-padding-flat.js +3 -0
- package/compassrose/compassrose.js +1 -8
- package/heatwave/isobar/plugin.js +4 -1
- package/heatwave/isobar/quadtreecontours.js +0 -2
- package/heatwave/plugins/heatwaveglobeshell.js +2 -0
- package/package.json +1 -1
- package/partialrings/goals.md +2 -0
- package/partialrings/plugin.js +2 -1
- package/point-glow-line-to-earth/draw-subset-obj.js +27 -0
- package/point-glow-line-to-earth/keymethod.js +0 -0
- package/point-glow-line-to-earth/plugin.js +439 -0
- package/point-glow-line-to-earth/types.js +26 -0
- package/point-heat-map/index.js +0 -3
- package/point-heat-map/plugin-webworker.js +4 -9
- package/point-heat-map/point-to-heat-map-flow.js +0 -6
- package/point-tracks/plugin.js +4 -4
- package/programs/arrowfield/logic.js +6 -4
- package/programs/arrowfield/object.js +1 -1
- package/programs/float2legendwithratio/object.js +5 -4
- package/programs/globe-util/is-globe-moved.js +27 -0
- package/programs/globeshell/wiggle/logic.js +3 -7
- package/programs/globeshell/wiggle/object.js +1 -2
- package/programs/line-on-globe/circle-accurate-3d.js +16 -23
- package/programs/line-on-globe/circle-accurate-flat.js +21 -21
- package/programs/line-on-globe/lines-color-instanced-flat.js +6 -7
- package/programs/line-on-globe/naive-accurate-flexible.js +239 -0
- package/programs/line-on-globe/to-the-surface.js +129 -0
- package/programs/picking/pickable-renderer.js +216 -0
- package/programs/point-on-globe/element-globe-surface-glow.js +168 -0
- package/programs/point-on-globe/element-point-glow.js +184 -0
- package/programs/point-on-globe/square-pixel-point.js +2 -4
- package/programs/programcache.js +9 -0
- package/programs/rings/partial-ring/piece-of-pie.js +1 -1
- package/programs/totems/camerauniformblock.js +23 -2
- package/rangerings/plugin.js +9 -6
- package/shaders/fragment-toy/firework.js +55 -0
- package/shaders/fragment-toy/singularity.js +59 -0
- package/types.js +16 -0
- package/util/account/single-attribute-buffer-management/buffer-manager.js +1 -5
- package/util/account/util.js +17 -7
- package/util/check/typecheck.js +11 -0
- package/util/gl-util/buffer/integrate-buffer.js +74 -0
- package/util/gl-util/draw-options/client.js +59 -0
- package/util/gl-util/draw-options/methods.js +46 -0
- package/util/gl-util/draw-options/types.js +18 -0
- package/util/gl-util/uniform-block/manager.js +176 -0
- package/util/gl-util/uniform-block/roadmap.md +70 -0
- package/util/gl-util/uniform-block/shader.js +0 -0
- package/util/gl-util/uniform-block/types.js +7 -0
- package/util/jshelpers/equality.js +17 -0
- package/util/picking/picker-displayer.js +1 -1
- package/util/programs/shapesonglobe.js +17 -19
- package/util/shaderfunctions/geometrytransformations.js +27 -63
- package/bearing-line/roadmap.md +0 -15
- package/point-heat-map/plugin.js +0 -132
- package/programs/line-on-globe/naive-accurate.js +0 -221
- package/programs/line-on-globe/to-the-origin.js +0 -164
- package/util/jshelpers/timemethods.js +0 -19
- /package/{programs/point-on-globe/element-draw-glow.js → point-glow-line-to-earth/adaptors.js} +0 -0
|
File without changes
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
function arraysEqual(a, b) {
|
|
2
|
+
if (a === b) return true;
|
|
3
|
+
if (a == null || b == null) return false;
|
|
4
|
+
if (a.length !== b.length) return false;
|
|
5
|
+
|
|
6
|
+
// If you don't care about the order of the elements inside
|
|
7
|
+
// the array, you should sort both arrays here.
|
|
8
|
+
// Please note that calling sort on an array will modify that array.
|
|
9
|
+
// you might want to clone your array first.
|
|
10
|
+
|
|
11
|
+
for (var i = 0; i < a.length; ++i) {
|
|
12
|
+
if (a[i] !== b[i]) return false;
|
|
13
|
+
}
|
|
14
|
+
return true;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
export { arraysEqual };
|
|
@@ -31,7 +31,6 @@ class PickerDisplayer {
|
|
|
31
31
|
width = this.globe.api_ScrW();
|
|
32
32
|
height = this.globe.api_ScrH();
|
|
33
33
|
}
|
|
34
|
-
console.log("resize picker displayer", width, height);
|
|
35
34
|
const { gl, colorTexture, indexTexture } = this;
|
|
36
35
|
|
|
37
36
|
gl.deleteTexture(colorTexture);
|
|
@@ -97,6 +96,7 @@ class PickerDisplayer {
|
|
|
97
96
|
}
|
|
98
97
|
|
|
99
98
|
|
|
99
|
+
|
|
100
100
|
pickBbox(left, top, right, bottom, callback) {
|
|
101
101
|
const size = (right - left) * (bottom - top) * 4;
|
|
102
102
|
this._pick(size, left, top, right - left, bottom - top, callback);
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { createProgram } from "../webglobjectbuilders";
|
|
2
|
+
import { CameraUniformBlockString, CameraUniformBlockTotemCache } from "../../programs/totems/camerauniformblock";
|
|
2
3
|
import { shaderfunctions } from "..";
|
|
3
4
|
/** TODO:
|
|
4
5
|
* 3d icin calistir
|
|
@@ -51,19 +52,14 @@ export class ShapesOnGlobeProgram {
|
|
|
51
52
|
}
|
|
52
53
|
|
|
53
54
|
_createProgramWrapper() {
|
|
54
|
-
const gl = this
|
|
55
|
+
const { gl, globe } = this;
|
|
55
56
|
const vertexSource = `#version 300 es
|
|
56
57
|
precision highp float;
|
|
58
|
+
${CameraUniformBlockString}
|
|
57
59
|
|
|
58
60
|
in vec2 a_position;
|
|
59
61
|
in vec4 a_color;
|
|
60
62
|
|
|
61
|
-
uniform mat4 u_model_view_matrix;
|
|
62
|
-
uniform mat4 u_proj_matrix;
|
|
63
|
-
uniform vec3 u_transpos;
|
|
64
|
-
|
|
65
|
-
uniform vec2 u_mapWH;
|
|
66
|
-
uniform vec2 u_scrWH;
|
|
67
63
|
|
|
68
64
|
uniform bool u_is3D;
|
|
69
65
|
uniform float height;
|
|
@@ -77,14 +73,13 @@ export class ShapesOnGlobeProgram {
|
|
|
77
73
|
|
|
78
74
|
|
|
79
75
|
void main() {
|
|
80
|
-
// vec3 pos = u_bbox_matrix * vec3(a_position, height);
|
|
81
76
|
vec3 pos = vec3(a_position, height);
|
|
82
|
-
if(
|
|
77
|
+
if(is3D){
|
|
83
78
|
pos = pixelXYToCartesian3DPoint(pos);
|
|
84
|
-
gl_Position =
|
|
79
|
+
gl_Position = projection * view * vec4(pos - translate, 1.0);
|
|
85
80
|
} else {
|
|
86
|
-
vec2 xy = pixelXYToCartesian2DPoint(pos.xy,
|
|
87
|
-
gl_Position =
|
|
81
|
+
vec2 xy = pixelXYToCartesian2DPoint(pos.xy, translate.xy, mapWH, screenWH);
|
|
82
|
+
gl_Position = projection * vec4(xy.x, xy.y, 0.0, 1.0);
|
|
88
83
|
}
|
|
89
84
|
gl_PointSize = u_point_size;
|
|
90
85
|
v_color = a_color;
|
|
@@ -121,17 +116,18 @@ export class ShapesOnGlobeProgram {
|
|
|
121
116
|
gl.vertexAttribPointer(a_color, 4, gl.FLOAT, false, 6 * 4, 2 * 4);
|
|
122
117
|
gl.bindVertexArray(null);
|
|
123
118
|
|
|
119
|
+
const cm = CameraUniformBlockTotemCache.get(globe);
|
|
120
|
+
const bindingPoint = 0;
|
|
121
|
+
const cmIndex = gl.getUniformBlockIndex(program, "CameraUniformBlock");
|
|
122
|
+
gl.uniformBlockBinding(program, cmIndex, bindingPoint);
|
|
123
|
+
|
|
124
124
|
return {
|
|
125
125
|
program: program,
|
|
126
126
|
vao: vao,
|
|
127
|
-
u_model_view_matrix: gl.getUniformLocation(program, 'u_model_view_matrix'),
|
|
128
|
-
u_proj_matrix: gl.getUniformLocation(program, 'u_proj_matrix'),
|
|
129
|
-
u_transpos: gl.getUniformLocation(program, 'u_transpos'),
|
|
130
127
|
u_point_size: gl.getUniformLocation(program, 'u_point_size'),
|
|
131
|
-
u_mapWH: gl.getUniformLocation(program, 'u_mapWH'),
|
|
132
|
-
u_scrWH: gl.getUniformLocation(program, 'u_scrWH'),
|
|
133
|
-
u_is3D: gl.getUniformLocation(program, 'u_is3D'),
|
|
134
128
|
u_opacity: gl.getUniformLocation(program, 'u_opacity'),
|
|
129
|
+
bindCamera: () => cm.bind(bindingPoint),
|
|
130
|
+
unbindCamera: () => cm.unbind(bindingPoint)
|
|
135
131
|
};
|
|
136
132
|
}
|
|
137
133
|
|
|
@@ -149,6 +145,7 @@ export class ShapesOnGlobeProgram {
|
|
|
149
145
|
gl.uniformMatrix4fv(_programWrapper.u_proj_matrix, false, uProjectionMatrix);
|
|
150
146
|
gl.uniform3f(_programWrapper.u_transpos, uTranslate.x, uTranslate.y, uTranslate.z);
|
|
151
147
|
gl.bindVertexArray(_programWrapper.vao);
|
|
148
|
+
_programWrapper.bindCamera();
|
|
152
149
|
if (!_is3D) {
|
|
153
150
|
const mapWH = this.globe.api_GetCurrentWorldWH();
|
|
154
151
|
gl.uniform2f(_programWrapper.u_mapWH, mapWH.width, mapWH.height);
|
|
@@ -157,8 +154,9 @@ export class ShapesOnGlobeProgram {
|
|
|
157
154
|
|
|
158
155
|
for (const drawRange of drawRanges) {
|
|
159
156
|
gl.drawArrays(this._drawMode, drawRange[0], drawRange[1]);
|
|
160
|
-
gl.drawArrays(gl.POINTS, drawRange[0], 1);
|
|
157
|
+
// gl.drawArrays(gl.POINTS, drawRange[0], 1);
|
|
161
158
|
}
|
|
159
|
+
_programWrapper.unbindCamera();
|
|
162
160
|
|
|
163
161
|
gl.bindVertexArray(null);
|
|
164
162
|
if (deepTest) {
|
|
@@ -192,26 +192,6 @@ vec2 circleLimpFromLongLatRadCenterMercatorCompass(vec2 center, float radius, fl
|
|
|
192
192
|
} `;
|
|
193
193
|
|
|
194
194
|
|
|
195
|
-
// Function to interpolate between two Cartesian points using spherical interpolation (slerp)
|
|
196
|
-
export const slerp = `
|
|
197
|
-
vec3 slerp(vec3 A, vec3 B, float t) {
|
|
198
|
-
float cosTheta = dot(A, B);
|
|
199
|
-
float theta = acos(clamp(cosTheta, -1.0, 1.0)); // Angle between the points
|
|
200
|
-
|
|
201
|
-
float sinTheta = sin(theta);
|
|
202
|
-
|
|
203
|
-
// Avoid division by zero // many points falls in to this category
|
|
204
|
-
if (sinTheta < 0.00001) {
|
|
205
|
-
return mix(A, B, t); // Linear interpolation as fallback
|
|
206
|
-
}
|
|
207
|
-
|
|
208
|
-
float factorA = sin((1.0 - t) * theta) / sinTheta;
|
|
209
|
-
float factorB = sin(t * theta) / sinTheta;
|
|
210
|
-
|
|
211
|
-
return factorA * A + factorB * B;
|
|
212
|
-
}
|
|
213
|
-
`;
|
|
214
|
-
|
|
215
195
|
// Function to convert Cartesian coordinates back to spherical (latitude, longitude)
|
|
216
196
|
export const cartesianToSpherical = `
|
|
217
197
|
vec2 cartesianToSpherical(vec3 point) {
|
|
@@ -223,16 +203,6 @@ vec2 cartesianToSpherical(vec3 point) {
|
|
|
223
203
|
|
|
224
204
|
// Main function to calculate an intermediate point
|
|
225
205
|
|
|
226
|
-
export const interpolateGeographicPoint = slerp + cartesianToSpherical + longLatRadToCartesian3D + `
|
|
227
|
-
vec3 interpolateGeographicPoint(vec2 start, vec2 end, float t) {
|
|
228
|
-
vec3 pointA = longLatRadToCartesian3D(start);
|
|
229
|
-
vec3 pointB = longLatRadToCartesian3D(end);
|
|
230
|
-
vec3 interpolatedPoint = slerp(pointA, pointB, t);
|
|
231
|
-
return interpolatedPoint;
|
|
232
|
-
// return cartesianToSpherical(interpolatedPoint);
|
|
233
|
-
}
|
|
234
|
-
`;
|
|
235
|
-
|
|
236
206
|
|
|
237
207
|
|
|
238
208
|
export const angleBetweenTwoPointsRadian = `
|
|
@@ -253,35 +223,7 @@ float circleCircumferenceInterPolationOf2PointsRadian(vec2 center, vec2 target,
|
|
|
253
223
|
}
|
|
254
224
|
`
|
|
255
225
|
|
|
256
|
-
const circumferencePoints = `
|
|
257
|
-
vec2 circumferencePoints(vec2 center, vec2 target, vec2 target2, float phase) {
|
|
258
|
-
// Calculate vectors from center to target and target2
|
|
259
|
-
vec2 v1 = target - center;
|
|
260
|
-
vec2 v2 = target2 - center;
|
|
261
|
-
|
|
262
|
-
// Normalize the vectors to ensure they are on the unit circle
|
|
263
|
-
v1 = normalize(v1);
|
|
264
|
-
v2 = normalize(v2);
|
|
265
|
-
|
|
266
|
-
// Calculate the angle between the vectors
|
|
267
|
-
float angle1 = atan(v1.y, v1.x);
|
|
268
|
-
float angle2 = atan(v2.y, v2.x);
|
|
269
|
-
|
|
270
|
-
// Ensure the angles are continuous (handle wrap-around at 2π)
|
|
271
|
-
if (angle2 < angle1) {
|
|
272
|
-
angle2 += 2.0 * 3.14159265359; // Add 2π to angle2 if it is smaller
|
|
273
|
-
}
|
|
274
226
|
|
|
275
|
-
// Interpolate the angle based on the phase
|
|
276
|
-
float interpolatedAngle = mix(angle1, angle2, phase);
|
|
277
|
-
|
|
278
|
-
// Calculate the new point on the circle
|
|
279
|
-
vec2 result = vec2(cos(interpolatedAngle), sin(interpolatedAngle));
|
|
280
|
-
|
|
281
|
-
// Scale back to the original circle radius and shift to center
|
|
282
|
-
return center + length(target - center) * result;
|
|
283
|
-
}
|
|
284
|
-
`
|
|
285
227
|
|
|
286
228
|
|
|
287
229
|
export const realDistanceOnSphereR1 = `
|
|
@@ -294,22 +236,44 @@ float realDistanceOnSphereR1(vec2 longLat1, vec2 longLat2) {
|
|
|
294
236
|
}
|
|
295
237
|
`;
|
|
296
238
|
|
|
297
|
-
|
|
239
|
+
|
|
240
|
+
|
|
241
|
+
const pointsOnSphereBetween = `
|
|
242
|
+
vec3 pointsOnSphereBetween(vec3 a, vec3 b, float ratio) {
|
|
298
243
|
// Normalize the input points to ensure they are on the unit sphere
|
|
299
244
|
a = normalize(a);
|
|
300
245
|
b = normalize(b);
|
|
301
246
|
|
|
247
|
+
// Compute the dot product and clamp it to avoid numerical issues
|
|
248
|
+
float dotProduct = clamp(dot(a, b), -1.0, 1.0);
|
|
249
|
+
|
|
302
250
|
// Compute the angle between the points
|
|
303
|
-
float theta = acos(
|
|
251
|
+
float theta = acos(dotProduct);
|
|
252
|
+
|
|
253
|
+
// Handle the edge case where the points are nearly identical
|
|
254
|
+
if (theta < 0.0001) {
|
|
255
|
+
return normalize(mix(a, b, ratio)); // Linear interpolation as fallback
|
|
256
|
+
}
|
|
304
257
|
|
|
305
258
|
// Compute the interpolated point using spherical linear interpolation (slerp)
|
|
306
|
-
|
|
259
|
+
float sinTheta = sin(theta);
|
|
260
|
+
float factorA = sin((1.0 - ratio) * theta) / sinTheta;
|
|
261
|
+
float factorB = sin(ratio * theta) / sinTheta;
|
|
262
|
+
|
|
263
|
+
vec3 result = factorA * a + factorB * b;
|
|
307
264
|
|
|
308
265
|
// Return the normalized result to ensure it lies on the sphere
|
|
309
266
|
return normalize(result);
|
|
310
|
-
}
|
|
267
|
+
}`;
|
|
311
268
|
|
|
312
269
|
|
|
270
|
+
const slerp = `
|
|
271
|
+
${pointsOnSphereBetween}
|
|
272
|
+
vec3 slerp(vec3 A, vec3 B, float t) {
|
|
273
|
+
return pointsOnSphereBetween(A, B, t) * mix(length(A), length(B), t);
|
|
274
|
+
}
|
|
275
|
+
`
|
|
276
|
+
|
|
313
277
|
const circleLimpFromLongLatRadCenterCartesian3D_accurate = R + `
|
|
314
278
|
vec3 circleLimpFromLongLatRadCenterCartesian3D_accurate( vec3 geoW, float radius, float angle) {
|
|
315
279
|
vec3 normal = normalize(geoW);
|
|
@@ -357,7 +321,7 @@ vec2 circleLimpFromLongLatRadCenterMercatorRealDistanceNew_accurate(vec2 mercato
|
|
|
357
321
|
}`;
|
|
358
322
|
|
|
359
323
|
export {
|
|
360
|
-
|
|
324
|
+
slerp,
|
|
361
325
|
circleLimpFromLongLatRadCenterCartesian3D_accurate,
|
|
362
326
|
circleLimpFromLongLatRadCenterMercatorCompass_accurate,
|
|
363
327
|
circleLimpFromLongLatRadCenterMercatorRealDistanceNew_accurate
|
package/bearing-line/roadmap.md
DELETED
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
# Two problems:
|
|
2
|
-
lines are curved to to arrive perpendicular to the longitude lines
|
|
3
|
-
patrial rings are not fit to the lines nor the bearing angle
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
# AngledLine
|
|
8
|
-
|
|
9
|
-
Does not render
|
|
10
|
-
Check:
|
|
11
|
-
[-] VAO
|
|
12
|
-
[-] Attributes are loaded with data
|
|
13
|
-
Assign constants to attributes.
|
|
14
|
-
[x] Uniforms are loaded // program was not used before setting opacity
|
|
15
|
-
[x] Check geometry // Assigning a constant to the geometry made all edges of the line overlap and the line was not visible
|
package/point-heat-map/plugin.js
DELETED
|
@@ -1,132 +0,0 @@
|
|
|
1
|
-
import { PointHeatmapFlow } from "./point-to-heat-map-flow";
|
|
2
|
-
import { TimeTrackInterpolator } from "../util/interpolation/timetrack/timetrack-interpolator";
|
|
3
|
-
import { createTexture, getColorRampModed } from "../util";
|
|
4
|
-
// TODO: DEPRECATED
|
|
5
|
-
class PointHeatmapPlugin {
|
|
6
|
-
|
|
7
|
-
constructor(id, { opacity = 1.0, pointSize = 5.0 } = {}) {
|
|
8
|
-
this.id = id;
|
|
9
|
-
this.globe = null;
|
|
10
|
-
this.gl = null;
|
|
11
|
-
this.densityToLegendProgram = null;
|
|
12
|
-
this._time = null;
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
this._opacity = opacity;
|
|
16
|
-
this._pointSize = pointSize;
|
|
17
|
-
this._legendTexture = null;
|
|
18
|
-
this.timeTrackInterpolator = new TimeTrackInterpolator();
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
// globe interaction
|
|
22
|
-
|
|
23
|
-
init(globe, gl) {
|
|
24
|
-
this.globe = globe;
|
|
25
|
-
this.gl = gl;
|
|
26
|
-
this.flow = new PointHeatmapFlow(globe);
|
|
27
|
-
this.setGeometry();
|
|
28
|
-
this.resize();
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
setPointSize(pointSize) {
|
|
33
|
-
if (typeof pointSize !== 'number' || pointSize <= 0) {
|
|
34
|
-
throw new Error('Invalid pointSize');
|
|
35
|
-
}
|
|
36
|
-
this._pointSize = pointSize;
|
|
37
|
-
this.globe.DrawRender();
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
/**
|
|
42
|
-
* @param {Array<string>}
|
|
43
|
-
* @param {string} mode "interpolated" | "discrete"
|
|
44
|
-
*/
|
|
45
|
-
|
|
46
|
-
setColorRamp(values, thresholds, mode = "interpolated") {
|
|
47
|
-
const gl = this.gl
|
|
48
|
-
if (this.gl === null) {
|
|
49
|
-
throw new Error('Plugin not initialized');
|
|
50
|
-
};
|
|
51
|
-
const rampData = getColorRampModed(values, thresholds, mode);
|
|
52
|
-
const texture = createTexture(gl, gl.LINEAR, rampData, 256, 1);
|
|
53
|
-
if (this._legendTexture) {
|
|
54
|
-
this.gl.deleteTexture(this._legendTexture);
|
|
55
|
-
}
|
|
56
|
-
this._legendTexture = texture;
|
|
57
|
-
this.globe.DrawRender();
|
|
58
|
-
}
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
setTime(time) {
|
|
62
|
-
this._time = time;
|
|
63
|
-
const data = this.timeTrackInterpolator.interpolate(time);
|
|
64
|
-
if (data === null) {
|
|
65
|
-
return;
|
|
66
|
-
}
|
|
67
|
-
this.flow.setData(data);
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
setTimetracks(timeTracks) {
|
|
72
|
-
this.timeTrackInterpolator.setTimetracks(timeTracks);
|
|
73
|
-
if (this._time !== null) {
|
|
74
|
-
this.setTime(this._time);
|
|
75
|
-
}
|
|
76
|
-
this.globe.DrawRender();
|
|
77
|
-
}
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
setOpacity(opacity) {
|
|
81
|
-
if (typeof opacity !== 'number' || opacity < 0 || opacity > 1) {
|
|
82
|
-
throw new Error('Invalid opacity');
|
|
83
|
-
}
|
|
84
|
-
this._opacity = opacity;
|
|
85
|
-
this.globe.DrawRender();
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
setGeometry() {
|
|
91
|
-
const geometry = this.globe.api_GetCurrentGeometry();
|
|
92
|
-
this.timeTrackInterpolator.setGeometry(geometry);
|
|
93
|
-
if (this._time !== null) {
|
|
94
|
-
this.setTime(this._time);
|
|
95
|
-
}
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
draw3D() {
|
|
100
|
-
if (this.isReady()) {
|
|
101
|
-
this.flow.draw(this._legendTexture, this._pointSize, this._opacity);
|
|
102
|
-
}
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
resize() {
|
|
107
|
-
this.timeTrackInterpolator.setGeometry(this.globe.api_GetCurrentGeometry());
|
|
108
|
-
this.flow.resize();
|
|
109
|
-
if (this._time !== null) {
|
|
110
|
-
this.setTime(this._time);
|
|
111
|
-
}
|
|
112
|
-
}
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
isReady() {
|
|
116
|
-
return (this.gl !== null && this._legendTexture !== null);
|
|
117
|
-
}
|
|
118
|
-
|
|
119
|
-
free() {
|
|
120
|
-
if (this._isFreed) return;
|
|
121
|
-
this.gl.deleteTexture(this._legendTexture);
|
|
122
|
-
this.flow.free();
|
|
123
|
-
this.flow = null;
|
|
124
|
-
this.gl = null;
|
|
125
|
-
this._isFreed = true;
|
|
126
|
-
this.timeTrackInterpolator = null;
|
|
127
|
-
this._legendTexture = null;
|
|
128
|
-
}
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
export { PointHeatmapPlugin };
|
|
@@ -1,221 +0,0 @@
|
|
|
1
|
-
import { CameraUniformBlockString, CameraUniformBlockTotem } from "../totems";
|
|
2
|
-
import { pointsOnSphereBetween, POLE, R_3D, mercatorXYToGLPosition, cartesian3DToGLPosition } from "../../util/shaderfunctions/geometrytransformations";
|
|
3
|
-
import { createProgram } from "../../util";
|
|
4
|
-
import { noRegisterGlobeProgramCache, globeProgramCache } from "../programcache";
|
|
5
|
-
import { programCache } from "../rings/distancering/circleflatprogram";
|
|
6
|
-
|
|
7
|
-
const GLOBE_MIDPOINT_COUNT = 30;
|
|
8
|
-
|
|
9
|
-
const vertexShader = `#version 300 es
|
|
10
|
-
precision highp float;
|
|
11
|
-
${R_3D}
|
|
12
|
-
${CameraUniformBlockString}
|
|
13
|
-
${pointsOnSphereBetween}
|
|
14
|
-
${mercatorXYToGLPosition}
|
|
15
|
-
${cartesian3DToGLPosition}
|
|
16
|
-
|
|
17
|
-
in vec2 start_position;
|
|
18
|
-
in vec3 start_position3d;
|
|
19
|
-
in vec2 end_position;
|
|
20
|
-
in vec3 end_position3d;
|
|
21
|
-
in float dash_ratio;
|
|
22
|
-
in vec4 color;
|
|
23
|
-
in float dash_opacity;
|
|
24
|
-
out vec4 v_color;
|
|
25
|
-
out vec2 v_limp;
|
|
26
|
-
out float interpolation;
|
|
27
|
-
out float v_dash_ratio;
|
|
28
|
-
out float v_dash_opacity;
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
void main() {
|
|
32
|
-
vec2 longLat;
|
|
33
|
-
if (is3D) {
|
|
34
|
-
interpolation = float(gl_VertexID) / ${GLOBE_MIDPOINT_COUNT - 1}.0;
|
|
35
|
-
vec3 cartesian;
|
|
36
|
-
if ( length( start_position3d - end_position3d) < 4.4){
|
|
37
|
-
cartesian = mix( start_position3d, end_position3d, interpolation);
|
|
38
|
-
} else {
|
|
39
|
-
cartesian = pointsOnSphereBetween(start_position3d, end_position3d, interpolation) * length(end_position3d);
|
|
40
|
-
}
|
|
41
|
-
gl_Position = cartesian3DToGLPosition(cartesian);
|
|
42
|
-
v_limp = vec2(0.0, 0.0);
|
|
43
|
-
} else {
|
|
44
|
-
if ( distance( start_position, end_position) > 30000000.0) { return; }
|
|
45
|
-
interpolation = float(gl_VertexID);
|
|
46
|
-
if (gl_VertexID % 2 == 0) {
|
|
47
|
-
longLat = start_position;
|
|
48
|
-
} else {
|
|
49
|
-
longLat = end_position;
|
|
50
|
-
}
|
|
51
|
-
v_limp = longLat;
|
|
52
|
-
gl_Position = mercatorXYToGLPosition(longLat);
|
|
53
|
-
}
|
|
54
|
-
// if ( gl_VertexID % 2 == 0) {v_color = color;}
|
|
55
|
-
// else {v_color = vec4(0.0, 0.0, 0.0, 0.0);}
|
|
56
|
-
v_color = color;
|
|
57
|
-
v_dash_ratio = dash_ratio;
|
|
58
|
-
v_dash_opacity = dash_opacity;
|
|
59
|
-
}
|
|
60
|
-
`;
|
|
61
|
-
|
|
62
|
-
const fragmentShader = `#version 300 es
|
|
63
|
-
${POLE}
|
|
64
|
-
precision highp float;
|
|
65
|
-
uniform float opacity;
|
|
66
|
-
in vec4 v_color;
|
|
67
|
-
out vec4 color;
|
|
68
|
-
in float interpolation;
|
|
69
|
-
in float v_dash_ratio;
|
|
70
|
-
in vec2 v_limp;
|
|
71
|
-
in float v_dash_opacity;
|
|
72
|
-
void main() {
|
|
73
|
-
if (v_limp.x < -POLE || v_limp.x > POLE || v_limp.y < -POLE || v_limp.y > POLE) { discard; }
|
|
74
|
-
color = v_color;
|
|
75
|
-
color.a *= opacity;
|
|
76
|
-
if ( v_dash_ratio >= 1.0 ) { return; }
|
|
77
|
-
if (interpolation > 0.95) { return; }
|
|
78
|
-
if (fract(interpolation / (2.0 * v_dash_ratio)) < 0.5) { color.a *= v_dash_opacity; }
|
|
79
|
-
|
|
80
|
-
}
|
|
81
|
-
`;
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
class Logic {
|
|
85
|
-
|
|
86
|
-
constructor(globe) {
|
|
87
|
-
this.globe = globe;
|
|
88
|
-
this.gl = globe.gl;
|
|
89
|
-
this.program = createProgram(this.gl, vertexShader, fragmentShader);
|
|
90
|
-
this._lastOpacity = 1.0;
|
|
91
|
-
const { gl, program } = this;
|
|
92
|
-
{
|
|
93
|
-
// assign attribute locations
|
|
94
|
-
gl.bindAttribLocation(program, 0, "start_position");
|
|
95
|
-
gl.bindAttribLocation(program, 1, "start_position3d");
|
|
96
|
-
gl.bindAttribLocation(program, 2, "end_position");
|
|
97
|
-
gl.bindAttribLocation(program, 3, "end_position3d");
|
|
98
|
-
gl.bindAttribLocation(program, 4, "dash_ratio");
|
|
99
|
-
gl.bindAttribLocation(program, 5, "color");
|
|
100
|
-
gl.bindAttribLocation(program, 6, "dash_opacity");
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
{
|
|
104
|
-
this._opacityLocation = gl.getUniformLocation(program, "opacity");
|
|
105
|
-
const currentProgram = gl.getParameter(gl.CURRENT_PROGRAM);
|
|
106
|
-
gl.useProgram(program);
|
|
107
|
-
gl.uniform1f(this._opacityLocation, this._lastOpacity);
|
|
108
|
-
gl.useProgram(currentProgram);
|
|
109
|
-
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
this.cameraBlockBindingPoint = 0;
|
|
113
|
-
const cameraBlockIndex = this.gl.getUniformBlockIndex(this.program, "CameraUniformBlock");
|
|
114
|
-
this.cameraBlockTotem = globeProgramCache.getProgram(globe, CameraUniformBlockTotem);
|
|
115
|
-
gl.uniformBlockBinding(this.program, cameraBlockIndex, this.cameraBlockBindingPoint);
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
draw(vao, length, opacity) {
|
|
122
|
-
const { gl, program, globe, cameraBlockTotem, cameraBlockBindingPoint } = this;
|
|
123
|
-
gl.useProgram(program);
|
|
124
|
-
cameraBlockTotem.bind(cameraBlockBindingPoint);
|
|
125
|
-
gl.bindVertexArray(vao);
|
|
126
|
-
if (opacity !== this._lastOpacity) {
|
|
127
|
-
gl.uniform1f(this._opacityLocation, opacity);
|
|
128
|
-
this._lastOpacity = opacity;
|
|
129
|
-
}
|
|
130
|
-
const drawCount = globe.api_GetCurrentGeometry() === 0 ? GLOBE_MIDPOINT_COUNT : 2;
|
|
131
|
-
gl.drawArraysInstanced(gl.LINE_STRIP, 0, drawCount, length);
|
|
132
|
-
gl.bindVertexArray(null);
|
|
133
|
-
cameraBlockTotem.unbind(cameraBlockBindingPoint);
|
|
134
|
-
}
|
|
135
|
-
|
|
136
|
-
//
|
|
137
|
-
createVAO(
|
|
138
|
-
startPotisionBufferObj, startPotision3DBufferObj,
|
|
139
|
-
endPositionBufferObj, endPosition3DBufferObj,
|
|
140
|
-
dashRatioBufferObj,
|
|
141
|
-
dashOpacityBufferObj,
|
|
142
|
-
colorBufferObj) {
|
|
143
|
-
const { gl } = this;
|
|
144
|
-
const vao = gl.createVertexArray();
|
|
145
|
-
gl.bindVertexArray(vao);
|
|
146
|
-
{
|
|
147
|
-
const { buffer, stride = 0, offset = 0 } = startPotisionBufferObj;
|
|
148
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
|
|
149
|
-
gl.enableVertexAttribArray(0);
|
|
150
|
-
gl.vertexAttribPointer(0, 2, gl.FLOAT, false, stride, offset);
|
|
151
|
-
gl.vertexAttribDivisor(0, 1);
|
|
152
|
-
}
|
|
153
|
-
{
|
|
154
|
-
const { buffer, stride = 0, offset = 0 } = startPotision3DBufferObj;
|
|
155
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
|
|
156
|
-
gl.enableVertexAttribArray(1);
|
|
157
|
-
gl.vertexAttribPointer(1, 3, gl.FLOAT, false, stride, offset);
|
|
158
|
-
gl.vertexAttribDivisor(1, 1);
|
|
159
|
-
}
|
|
160
|
-
{
|
|
161
|
-
|
|
162
|
-
const { buffer, stride = 0, offset = 0 } = endPositionBufferObj;
|
|
163
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
|
|
164
|
-
gl.enableVertexAttribArray(2);
|
|
165
|
-
gl.vertexAttribPointer(2, 2, gl.FLOAT, false, stride, offset);
|
|
166
|
-
gl.vertexAttribDivisor(2, 1);
|
|
167
|
-
}
|
|
168
|
-
{
|
|
169
|
-
|
|
170
|
-
const { buffer, stride = 0, offset = 0 } = endPosition3DBufferObj;
|
|
171
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
|
|
172
|
-
gl.enableVertexAttribArray(3);
|
|
173
|
-
gl.vertexAttribPointer(3, 3, gl.FLOAT, false, stride, offset);
|
|
174
|
-
gl.vertexAttribDivisor(3, 1);
|
|
175
|
-
}
|
|
176
|
-
{
|
|
177
|
-
const { buffer, stride = 0, offset = 0 } = dashRatioBufferObj;
|
|
178
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
|
|
179
|
-
gl.enableVertexAttribArray(4);
|
|
180
|
-
gl.vertexAttribPointer(4, 1, gl.FLOAT, false, stride, offset);
|
|
181
|
-
gl.vertexAttribDivisor(4, 1);
|
|
182
|
-
}
|
|
183
|
-
|
|
184
|
-
{
|
|
185
|
-
const { buffer, stride = 0, offset = 0 } = colorBufferObj;
|
|
186
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
|
|
187
|
-
gl.enableVertexAttribArray(5);
|
|
188
|
-
gl.vertexAttribPointer(5, 4, gl.FLOAT, false, stride, offset);
|
|
189
|
-
gl.vertexAttribDivisor(5, 1);
|
|
190
|
-
}
|
|
191
|
-
|
|
192
|
-
{
|
|
193
|
-
const { buffer, stride = 0, offset = 0 } = dashOpacityBufferObj;
|
|
194
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, buffer);
|
|
195
|
-
gl.enableVertexAttribArray(6);
|
|
196
|
-
gl.vertexAttribPointer(6, 1, gl.FLOAT, false, stride, offset);
|
|
197
|
-
gl.vertexAttribDivisor(6, 1);
|
|
198
|
-
}
|
|
199
|
-
|
|
200
|
-
gl.bindVertexArray(null);
|
|
201
|
-
gl.bindBuffer(gl.ARRAY_BUFFER, null);
|
|
202
|
-
return vao;
|
|
203
|
-
|
|
204
|
-
}
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
free() {
|
|
208
|
-
if (this.isFreed) return;
|
|
209
|
-
programCache.releaseProgram(this.globe, CameraUniformBlockTotem);
|
|
210
|
-
this.gl.deleteProgram(this.program);
|
|
211
|
-
this.isFreed = true;
|
|
212
|
-
}
|
|
213
|
-
}
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
export const LineOnGlobeCache = Object.freeze({
|
|
218
|
-
get: (globe) => { return noRegisterGlobeProgramCache.getProgram(globe, Logic) },
|
|
219
|
-
release: (globe) => { return noRegisterGlobeProgramCache.releaseProgram(globe, Logic) }
|
|
220
|
-
});
|
|
221
|
-
|