@arenarium/maps 1.0.34 → 1.0.37
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/dist/index.js +83 -27400
- package/dist/style.css +1 -1
- package/package.json +19 -24
- package/dist/index.umd.cjs +0 -729
- package/node_modules/@workspace/shared/package.json +0 -6
- package/node_modules/@workspace/shared/src/constants.ts +0 -11
- package/node_modules/@workspace/shared/src/marker/blocks/blocks.ts +0 -129
- package/node_modules/@workspace/shared/src/marker/blocks/bounds.ts +0 -58
- package/node_modules/@workspace/shared/src/marker/blocks/thresholds.ts +0 -546
- package/node_modules/@workspace/shared/src/marker/position.ts +0 -44
- package/node_modules/@workspace/shared/src/marker/projection.ts +0 -16
- package/node_modules/@workspace/shared/src/marker/rectangle.ts +0 -49
- package/node_modules/@workspace/shared/src/types.ts +0 -29
- package/node_modules/@workspace/shared/tsconfig.json +0 -12
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
export const MAP_MARKERS_MAX_COUNT = 1024;
|
|
2
|
-
export const MAP_BASE_SIZE = 512;
|
|
3
|
-
export const MAP_MIN_ZOOM = 0;
|
|
4
|
-
export const MAP_MAX_ZOOM = 18;
|
|
5
|
-
export const MAP_VISIBLE_ZOOM_DEPTH = 3;
|
|
6
|
-
export const MAP_DISPLAYED_ZOOM_DEPTH = 0.5;
|
|
7
|
-
|
|
8
|
-
export const MARKER_DEFAULT_ANGLE = 270;
|
|
9
|
-
export const MARKER_PADDING = 8;
|
|
10
|
-
|
|
11
|
-
export const FEEDBACK_EMAIL = 'arenarium.dev@gmail.com';
|
|
@@ -1,129 +0,0 @@
|
|
|
1
|
-
import { getThresholds } from './thresholds.js';
|
|
2
|
-
import { getPoint } from '../projection.js';
|
|
3
|
-
import { type Types } from '../../types.js';
|
|
4
|
-
import { MAP_MIN_ZOOM, MAP_MAX_ZOOM, MARKER_PADDING } from '../../constants.js';
|
|
5
|
-
|
|
6
|
-
const MARKERS_PER_BLOCK_TARGET = 64;
|
|
7
|
-
|
|
8
|
-
function getBlocksZoomStep(markersLength: number, zoomStep: number): number {
|
|
9
|
-
// Adjust the zoom step based on the number of markers
|
|
10
|
-
// so that each block markers lenght is around the given size
|
|
11
|
-
// MAP_MAX_ZOOM - MAP_MIN_ZOOM shoud be a power of 2, eg 16
|
|
12
|
-
// zoomStep should be a power of 2
|
|
13
|
-
if (zoomStep == 1) return 1;
|
|
14
|
-
|
|
15
|
-
let blockLevels = (MAP_MAX_ZOOM - MAP_MIN_ZOOM) / zoomStep;
|
|
16
|
-
let blockCount = (1 / 3) * (Math.pow(4, blockLevels) - 1);
|
|
17
|
-
|
|
18
|
-
let markersPerBlock = Math.ceil(markersLength / blockCount);
|
|
19
|
-
if (markersPerBlock > MARKERS_PER_BLOCK_TARGET) return getBlocksZoomStep(markersLength, Math.round(zoomStep / 2));
|
|
20
|
-
|
|
21
|
-
return zoomStep;
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
export function getBlocks(popups: Types.Popup[]): Types.Block[] {
|
|
25
|
-
// Calculate the thresholds
|
|
26
|
-
const thresholdProjections = popups.map(m => getPoint(m.lat, m.lng));
|
|
27
|
-
const thresholdMarkers = popups.map((m, i) => ({
|
|
28
|
-
id: m.id,
|
|
29
|
-
x: thresholdProjections[i].x,
|
|
30
|
-
y: thresholdProjections[i].y,
|
|
31
|
-
width: m.width + 4 * MARKER_PADDING,
|
|
32
|
-
height: m.height + 4 * MARKER_PADDING,
|
|
33
|
-
rank: popups.length - m.index
|
|
34
|
-
}));
|
|
35
|
-
const thresholds = getThresholds(thresholdMarkers);
|
|
36
|
-
|
|
37
|
-
// Validate and load expansion results
|
|
38
|
-
const markers = popups.map(m => ({
|
|
39
|
-
id: m.id,
|
|
40
|
-
lat: m.lat,
|
|
41
|
-
lng: m.lng,
|
|
42
|
-
width: m.width,
|
|
43
|
-
height: m.height,
|
|
44
|
-
zet: NaN,
|
|
45
|
-
angs: []
|
|
46
|
-
}) as Types.Marker)
|
|
47
|
-
const markerMap = new Map(markers.map((p) => [p.id, p]));
|
|
48
|
-
|
|
49
|
-
for (const threshold of thresholds) {
|
|
50
|
-
for (const id of threshold.ids) {
|
|
51
|
-
if (!id) throw new Error('Marker id is not valid');
|
|
52
|
-
|
|
53
|
-
const marker = markerMap.get(id);
|
|
54
|
-
if (!marker) throw new Error('Marker not found');
|
|
55
|
-
|
|
56
|
-
if (isNaN(marker.zet)) {
|
|
57
|
-
marker.zet = threshold.zoom;
|
|
58
|
-
}
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
for (const angle of threshold.angles) {
|
|
62
|
-
if (!angle.id) throw new Error('Marker angle id is not valid');
|
|
63
|
-
if (angle.value == undefined || angle.value == null) throw new Error('Marker angle val is not valid');
|
|
64
|
-
|
|
65
|
-
const marker = markerMap.get(angle.id);
|
|
66
|
-
if (!marker) throw new Error('Marker not found');
|
|
67
|
-
|
|
68
|
-
// If the last angle value is different from the new angle value, add the new angle
|
|
69
|
-
// (ang[0] = threshold, ang[1] = value)
|
|
70
|
-
if (marker.angs.length == 0 || marker.angs[marker.angs.length - 1][1] != angle.value) {
|
|
71
|
-
marker.angs.push([threshold.zoom, angle.value]);
|
|
72
|
-
}
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
for (const marker of markers) {
|
|
77
|
-
if (isNaN(marker.zet)) throw new Error('Marker zet is NaN');
|
|
78
|
-
if (marker.angs.length == 0) throw new Error('Marker angs is empty');
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
// Calculate blocks
|
|
82
|
-
const blocks = new Array<Types.Block>();
|
|
83
|
-
|
|
84
|
-
const zoomMin = MAP_MIN_ZOOM;
|
|
85
|
-
const zoomStep = getBlocksZoomStep(markers.length, MAP_MAX_ZOOM - MAP_MIN_ZOOM);
|
|
86
|
-
|
|
87
|
-
const latMin = -90;
|
|
88
|
-
const latMax = 90;
|
|
89
|
-
const lngMin = -180;
|
|
90
|
-
const lngMax = 180;
|
|
91
|
-
|
|
92
|
-
for (const marker of markers) {
|
|
93
|
-
let block = blocks
|
|
94
|
-
.filter((b) => b.zs <= marker.zet && marker.zet <= b.ze)
|
|
95
|
-
.find((b) => b.sw.lat <= marker.lat && marker.lat <= b.ne.lat && b.sw.lng <= marker.lng && marker.lng <= b.ne.lng);
|
|
96
|
-
|
|
97
|
-
if (block === undefined) {
|
|
98
|
-
const zoomStart = zoomMin + Math.floor((marker.zet - zoomMin) / zoomStep) * zoomStep;
|
|
99
|
-
const zoomEnd = Math.floor(zoomStart + zoomStep);
|
|
100
|
-
|
|
101
|
-
const blockLevel = Math.floor((zoomStart - zoomMin) / zoomStep);
|
|
102
|
-
const blockSize = Math.pow(2, blockLevel);
|
|
103
|
-
const blockSizeLat = (latMax - latMin) / blockSize;
|
|
104
|
-
const blockSizeLng = (lngMax - lngMin) / blockSize;
|
|
105
|
-
|
|
106
|
-
const blockRowId = Math.floor(((marker.lat - latMin) / (latMax - latMin)) * blockSize);
|
|
107
|
-
const blockColId = Math.floor(((marker.lng - lngMin) / (lngMax - lngMin)) * blockSize);
|
|
108
|
-
|
|
109
|
-
const swLat = latMin + blockRowId * blockSizeLat;
|
|
110
|
-
const swLng = lngMin + blockColId * blockSizeLng;
|
|
111
|
-
const neLat = swLat + blockSizeLat;
|
|
112
|
-
const neLng = swLng + blockSizeLng;
|
|
113
|
-
|
|
114
|
-
block = {
|
|
115
|
-
id: `${blockLevel}_${blockRowId}_${blockColId}`,
|
|
116
|
-
sw: { lat: swLat, lng: swLng },
|
|
117
|
-
ne: { lat: neLat, lng: neLng },
|
|
118
|
-
zs: zoomStart,
|
|
119
|
-
ze: zoomEnd,
|
|
120
|
-
markers: []
|
|
121
|
-
};
|
|
122
|
-
blocks.push(block);
|
|
123
|
-
}
|
|
124
|
-
|
|
125
|
-
block.markers.push(marker);
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
return blocks;
|
|
129
|
-
}
|
|
@@ -1,58 +0,0 @@
|
|
|
1
|
-
import { getRectangleOffsets } from '../rectangle.js';
|
|
2
|
-
|
|
3
|
-
export interface Rectangle {
|
|
4
|
-
x: number;
|
|
5
|
-
y: number;
|
|
6
|
-
width: number;
|
|
7
|
-
height: number;
|
|
8
|
-
}
|
|
9
|
-
|
|
10
|
-
export interface Bounds {
|
|
11
|
-
// Anchor
|
|
12
|
-
x: number;
|
|
13
|
-
y: number;
|
|
14
|
-
// Distances from anchor
|
|
15
|
-
left: number;
|
|
16
|
-
right: number;
|
|
17
|
-
top: number;
|
|
18
|
-
bottom: number;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
export function areBoundsOverlaping(bounds1: Bounds, bounds2: Bounds): boolean {
|
|
22
|
-
if (bounds1.x - bounds1.left > bounds2.x + bounds2.right) return false;
|
|
23
|
-
if (bounds1.x + bounds1.right < bounds2.x - bounds2.left) return false;
|
|
24
|
-
if (bounds1.y - bounds1.top > bounds2.y + bounds2.bottom) return false;
|
|
25
|
-
if (bounds1.y + bounds1.bottom < bounds2.y - bounds2.top) return false;
|
|
26
|
-
return true;
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
export function getBoundsZoomWhenTouching(bounds1: Bounds, bounds2: Bounds): number {
|
|
30
|
-
let xDistance0 = Math.abs(bounds1.x - bounds2.x);
|
|
31
|
-
let xDistanceZ = bounds1.x < bounds2.x ? bounds1.right + bounds2.left : bounds1.left + bounds2.right;
|
|
32
|
-
let xRatio = xDistanceZ / xDistance0;
|
|
33
|
-
|
|
34
|
-
let yDistance0 = Math.abs(bounds1.y - bounds2.y);
|
|
35
|
-
let yDistanceZ = bounds1.y < bounds2.y ? bounds1.bottom + bounds2.top : bounds1.top + bounds2.bottom;
|
|
36
|
-
let yRatio = yDistanceZ / yDistance0;
|
|
37
|
-
|
|
38
|
-
let minRatio = Math.min(xRatio, yRatio);
|
|
39
|
-
let zoom = Math.log2(minRatio);
|
|
40
|
-
return zoom;
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
export function getBounds(rectangle: Rectangle, angle: number, scale: number): Bounds {
|
|
44
|
-
let { offsetX, offsetY } = getRectangleOffsets(rectangle.width, rectangle.height, angle);
|
|
45
|
-
let left = -offsetX;
|
|
46
|
-
let right = rectangle.width - left;
|
|
47
|
-
let top = -offsetY;
|
|
48
|
-
let bottom = rectangle.height - top;
|
|
49
|
-
|
|
50
|
-
return {
|
|
51
|
-
x: rectangle.x,
|
|
52
|
-
y: rectangle.y,
|
|
53
|
-
left: left / scale,
|
|
54
|
-
right: right / scale,
|
|
55
|
-
top: top / scale,
|
|
56
|
-
bottom: bottom / scale
|
|
57
|
-
};
|
|
58
|
-
}
|