@sindicum/libre-draw 0.1.1 → 0.2.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.
- package/dist/LibreDraw.d.ts +11 -1
- package/dist/core/ModeContext.d.ts +36 -0
- package/dist/core/ModeManager.d.ts +2 -4
- package/dist/index.d.ts +3 -2
- package/dist/input/MouseInput.d.ts +4 -2
- package/dist/input/TouchInput.d.ts +6 -0
- package/dist/libre-draw.cjs +1 -1
- package/dist/libre-draw.cjs.map +1 -1
- package/dist/libre-draw.js +950 -758
- package/dist/libre-draw.js.map +1 -1
- package/dist/modes/DrawMode.d.ts +7 -29
- package/dist/modes/IdleMode.d.ts +4 -0
- package/dist/modes/Mode.d.ts +9 -0
- package/dist/modes/PolygonDragger.d.ts +23 -0
- package/dist/modes/SelectMode.d.ts +15 -126
- package/dist/modes/SelectionManager.d.ts +19 -0
- package/dist/modes/VertexEditor.d.ts +28 -0
- package/dist/rendering/RenderManager.d.ts +11 -1
- package/dist/rendering/SourceManager.d.ts +4 -0
- package/dist/types/events.d.ts +3 -2
- package/dist/types/features.d.ts +3 -3
- package/dist/types/index.d.ts +3 -0
- package/dist/types/mode.d.ts +4 -0
- package/dist/types/options.d.ts +3 -0
- package/dist/types/style.d.ts +84 -0
- package/dist/utils/featureSnapshot.d.ts +21 -0
- package/dist/utils/geometry.d.ts +25 -0
- package/package.json +3 -5
package/dist/libre-draw.js
CHANGED
|
@@ -1,6 +1,44 @@
|
|
|
1
|
-
|
|
1
|
+
function J(s) {
|
|
2
|
+
if (Array.isArray(s))
|
|
3
|
+
return s.map((e) => J(e));
|
|
4
|
+
if (s !== null && typeof s == "object") {
|
|
5
|
+
const e = {};
|
|
6
|
+
for (const [t, r] of Object.entries(
|
|
7
|
+
s
|
|
8
|
+
))
|
|
9
|
+
e[t] = J(r);
|
|
10
|
+
return e;
|
|
11
|
+
}
|
|
12
|
+
return s;
|
|
13
|
+
}
|
|
14
|
+
function fe(s) {
|
|
15
|
+
return s.map(
|
|
16
|
+
(e) => e.map((t) => [t[0], t[1]])
|
|
17
|
+
);
|
|
18
|
+
}
|
|
19
|
+
function pe(s) {
|
|
20
|
+
return J(s);
|
|
21
|
+
}
|
|
22
|
+
function v(s) {
|
|
23
|
+
return {
|
|
24
|
+
id: s.id,
|
|
25
|
+
type: "Feature",
|
|
26
|
+
geometry: {
|
|
27
|
+
type: "Polygon",
|
|
28
|
+
coordinates: fe(s.geometry.coordinates)
|
|
29
|
+
},
|
|
30
|
+
properties: pe(s.properties)
|
|
31
|
+
};
|
|
32
|
+
}
|
|
33
|
+
function ye(s) {
|
|
34
|
+
return {
|
|
35
|
+
type: "FeatureCollection",
|
|
36
|
+
features: s.features.map((e) => v(e))
|
|
37
|
+
};
|
|
38
|
+
}
|
|
39
|
+
class me {
|
|
2
40
|
constructor(e) {
|
|
3
|
-
this.
|
|
41
|
+
this.type = "create", this.feature = v(e);
|
|
4
42
|
}
|
|
5
43
|
apply(e) {
|
|
6
44
|
e.add(this.feature);
|
|
@@ -9,9 +47,9 @@ class ue {
|
|
|
9
47
|
e.remove(this.feature.id);
|
|
10
48
|
}
|
|
11
49
|
}
|
|
12
|
-
class
|
|
13
|
-
constructor(e, t,
|
|
14
|
-
this.
|
|
50
|
+
class ae {
|
|
51
|
+
constructor(e, t, r) {
|
|
52
|
+
this.type = "update", this.id = e, this.oldFeature = v(t), this.newFeature = v(r);
|
|
15
53
|
}
|
|
16
54
|
apply(e) {
|
|
17
55
|
e.update(this.id, this.newFeature);
|
|
@@ -20,9 +58,9 @@ class $ {
|
|
|
20
58
|
e.update(this.id, this.oldFeature);
|
|
21
59
|
}
|
|
22
60
|
}
|
|
23
|
-
class
|
|
61
|
+
class le {
|
|
24
62
|
constructor(e) {
|
|
25
|
-
this.
|
|
63
|
+
this.type = "delete", this.feature = v(e);
|
|
26
64
|
}
|
|
27
65
|
apply(e) {
|
|
28
66
|
e.remove(this.feature.id);
|
|
@@ -31,7 +69,7 @@ class oe {
|
|
|
31
69
|
e.add(this.feature);
|
|
32
70
|
}
|
|
33
71
|
}
|
|
34
|
-
class
|
|
72
|
+
class ve {
|
|
35
73
|
constructor() {
|
|
36
74
|
this.listeners = /* @__PURE__ */ new Map();
|
|
37
75
|
}
|
|
@@ -41,8 +79,8 @@ class ge {
|
|
|
41
79
|
* @param listener - The callback to invoke when the event fires.
|
|
42
80
|
*/
|
|
43
81
|
on(e, t) {
|
|
44
|
-
let
|
|
45
|
-
|
|
82
|
+
let r = this.listeners.get(e);
|
|
83
|
+
r || (r = /* @__PURE__ */ new Set(), this.listeners.set(e, r)), r.add(t);
|
|
46
84
|
}
|
|
47
85
|
/**
|
|
48
86
|
* Remove a listener for a specific event type.
|
|
@@ -50,8 +88,8 @@ class ge {
|
|
|
50
88
|
* @param listener - The callback to remove.
|
|
51
89
|
*/
|
|
52
90
|
off(e, t) {
|
|
53
|
-
const
|
|
54
|
-
|
|
91
|
+
const r = this.listeners.get(e);
|
|
92
|
+
r && r.delete(t);
|
|
55
93
|
}
|
|
56
94
|
/**
|
|
57
95
|
* Emit an event, invoking all registered listeners.
|
|
@@ -59,10 +97,10 @@ class ge {
|
|
|
59
97
|
* @param payload - The event payload.
|
|
60
98
|
*/
|
|
61
99
|
emit(e, t) {
|
|
62
|
-
const
|
|
63
|
-
if (
|
|
64
|
-
for (const
|
|
65
|
-
|
|
100
|
+
const r = this.listeners.get(e);
|
|
101
|
+
if (r)
|
|
102
|
+
for (const n of r)
|
|
103
|
+
n(t);
|
|
66
104
|
}
|
|
67
105
|
/**
|
|
68
106
|
* Remove all listeners for all event types.
|
|
@@ -71,7 +109,7 @@ class ge {
|
|
|
71
109
|
this.listeners.clear();
|
|
72
110
|
}
|
|
73
111
|
}
|
|
74
|
-
class
|
|
112
|
+
class we {
|
|
75
113
|
constructor() {
|
|
76
114
|
this.features = /* @__PURE__ */ new Map();
|
|
77
115
|
}
|
|
@@ -82,8 +120,8 @@ class R {
|
|
|
82
120
|
* @returns The added feature (with ID assigned).
|
|
83
121
|
*/
|
|
84
122
|
add(e) {
|
|
85
|
-
const t = e.id || crypto.randomUUID(),
|
|
86
|
-
return this.features.set(t,
|
|
123
|
+
const t = e.id || crypto.randomUUID(), r = v({ ...e, id: t });
|
|
124
|
+
return this.features.set(t, r), v(r);
|
|
87
125
|
}
|
|
88
126
|
/**
|
|
89
127
|
* Update a feature in the store by ID.
|
|
@@ -91,7 +129,7 @@ class R {
|
|
|
91
129
|
* @param feature - The new feature data.
|
|
92
130
|
*/
|
|
93
131
|
update(e, t) {
|
|
94
|
-
this.features.has(e) && this.features.set(e, { ...t, id: e });
|
|
132
|
+
this.features.has(e) && this.features.set(e, v({ ...t, id: e }));
|
|
95
133
|
}
|
|
96
134
|
/**
|
|
97
135
|
* Remove a feature from the store by ID.
|
|
@@ -100,14 +138,18 @@ class R {
|
|
|
100
138
|
*/
|
|
101
139
|
remove(e) {
|
|
102
140
|
const t = this.features.get(e);
|
|
103
|
-
|
|
141
|
+
if (t)
|
|
142
|
+
return this.features.delete(e), v(t);
|
|
104
143
|
}
|
|
105
144
|
/**
|
|
106
145
|
* Get all features in the store.
|
|
107
146
|
* @returns An array of all features.
|
|
108
147
|
*/
|
|
109
148
|
getAll() {
|
|
110
|
-
return Array.from(
|
|
149
|
+
return Array.from(
|
|
150
|
+
this.features.values(),
|
|
151
|
+
(e) => v(e)
|
|
152
|
+
);
|
|
111
153
|
}
|
|
112
154
|
/**
|
|
113
155
|
* Get a feature by its ID.
|
|
@@ -115,7 +157,8 @@ class R {
|
|
|
115
157
|
* @returns The feature, or undefined if not found.
|
|
116
158
|
*/
|
|
117
159
|
getById(e) {
|
|
118
|
-
|
|
160
|
+
const t = this.features.get(e);
|
|
161
|
+
return t ? v(t) : void 0;
|
|
119
162
|
}
|
|
120
163
|
/**
|
|
121
164
|
* Remove all features from the store.
|
|
@@ -130,8 +173,8 @@ class R {
|
|
|
130
173
|
setAll(e) {
|
|
131
174
|
this.features.clear();
|
|
132
175
|
for (const t of e) {
|
|
133
|
-
const
|
|
134
|
-
this.features.set(
|
|
176
|
+
const r = t.id || crypto.randomUUID();
|
|
177
|
+
this.features.set(r, v({ ...t, id: r }));
|
|
135
178
|
}
|
|
136
179
|
}
|
|
137
180
|
/**
|
|
@@ -139,10 +182,9 @@ class R {
|
|
|
139
182
|
* @returns A GeoJSON FeatureCollection.
|
|
140
183
|
*/
|
|
141
184
|
toGeoJSON() {
|
|
142
|
-
return {
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
};
|
|
185
|
+
return ye({
|
|
186
|
+
features: Array.from(this.features.values())
|
|
187
|
+
});
|
|
146
188
|
}
|
|
147
189
|
/**
|
|
148
190
|
* Create a deep clone of a feature suitable for history snapshots.
|
|
@@ -150,20 +192,10 @@ class R {
|
|
|
150
192
|
* @returns A deep-cloned feature.
|
|
151
193
|
*/
|
|
152
194
|
static cloneFeature(e) {
|
|
153
|
-
return
|
|
154
|
-
id: e.id,
|
|
155
|
-
type: "Feature",
|
|
156
|
-
geometry: {
|
|
157
|
-
type: "Polygon",
|
|
158
|
-
coordinates: e.geometry.coordinates.map(
|
|
159
|
-
(t) => t.map((s) => [...s])
|
|
160
|
-
)
|
|
161
|
-
},
|
|
162
|
-
properties: { ...e.properties }
|
|
163
|
-
};
|
|
195
|
+
return v(e);
|
|
164
196
|
}
|
|
165
197
|
}
|
|
166
|
-
class
|
|
198
|
+
class Se {
|
|
167
199
|
/**
|
|
168
200
|
* Create a new HistoryManager.
|
|
169
201
|
* @param limit - Maximum number of actions to retain. Defaults to 100.
|
|
@@ -216,7 +248,7 @@ class fe {
|
|
|
216
248
|
this.undoStack = [], this.redoStack = [];
|
|
217
249
|
}
|
|
218
250
|
}
|
|
219
|
-
class
|
|
251
|
+
class be {
|
|
220
252
|
constructor() {
|
|
221
253
|
this.modes = /* @__PURE__ */ new Map(), this.currentModeName = "idle";
|
|
222
254
|
}
|
|
@@ -243,10 +275,10 @@ class pe {
|
|
|
243
275
|
setMode(e) {
|
|
244
276
|
if (e === this.currentModeName)
|
|
245
277
|
return;
|
|
246
|
-
const t = this.currentModeName,
|
|
247
|
-
|
|
248
|
-
const
|
|
249
|
-
|
|
278
|
+
const t = this.currentModeName, r = this.modes.get(this.currentModeName);
|
|
279
|
+
r && r.deactivate(), this.currentModeName = e;
|
|
280
|
+
const n = this.modes.get(e);
|
|
281
|
+
n && n.activate(), this.onModeChange && this.onModeChange(e, t);
|
|
250
282
|
}
|
|
251
283
|
/**
|
|
252
284
|
* Get the current mode name.
|
|
@@ -268,52 +300,52 @@ class E extends Error {
|
|
|
268
300
|
super(e), this.name = "LibreDrawError";
|
|
269
301
|
}
|
|
270
302
|
}
|
|
271
|
-
function
|
|
272
|
-
const
|
|
273
|
-
return Math.abs(
|
|
303
|
+
function j(s, e, t) {
|
|
304
|
+
const r = (e[1] - s[1]) * (t[0] - e[0]) - (e[0] - s[0]) * (t[1] - e[1]);
|
|
305
|
+
return Math.abs(r) < 1e-10 ? 0 : r > 0 ? 1 : 2;
|
|
274
306
|
}
|
|
275
|
-
function
|
|
276
|
-
return e[0] <= Math.max(
|
|
307
|
+
function W(s, e, t) {
|
|
308
|
+
return e[0] <= Math.max(s[0], t[0]) && e[0] >= Math.min(s[0], t[0]) && e[1] <= Math.max(s[1], t[1]) && e[1] >= Math.min(s[1], t[1]);
|
|
277
309
|
}
|
|
278
|
-
function
|
|
279
|
-
return Math.abs(
|
|
310
|
+
function G(s, e) {
|
|
311
|
+
return Math.abs(s[0] - e[0]) < 1e-10 && Math.abs(s[1] - e[1]) < 1e-10;
|
|
280
312
|
}
|
|
281
|
-
function
|
|
282
|
-
if (
|
|
313
|
+
function X(s, e, t, r) {
|
|
314
|
+
if (G(s, t) || G(s, r) || G(e, t) || G(e, r))
|
|
283
315
|
return !1;
|
|
284
|
-
const
|
|
285
|
-
return !!(
|
|
316
|
+
const n = j(s, e, t), i = j(s, e, r), o = j(t, r, s), a = j(t, r, e);
|
|
317
|
+
return !!(n !== i && o !== a || n === 0 && W(s, t, e) || i === 0 && W(s, r, e) || o === 0 && W(t, s, r) || a === 0 && W(t, e, r));
|
|
286
318
|
}
|
|
287
|
-
function
|
|
288
|
-
const e =
|
|
319
|
+
function he(s) {
|
|
320
|
+
const e = s.length - 1;
|
|
289
321
|
if (e < 3) return !1;
|
|
290
322
|
for (let t = 0; t < e; t++)
|
|
291
|
-
for (let
|
|
292
|
-
if (!(t === 0 &&
|
|
323
|
+
for (let r = t + 2; r < e; r++)
|
|
324
|
+
if (!(t === 0 && r === e - 1) && X(s[t], s[t + 1], s[r], s[r + 1]))
|
|
293
325
|
return !0;
|
|
294
326
|
return !1;
|
|
295
327
|
}
|
|
296
|
-
function
|
|
297
|
-
if (
|
|
298
|
-
const t =
|
|
299
|
-
for (let
|
|
300
|
-
if (
|
|
328
|
+
function Ee(s, e) {
|
|
329
|
+
if (s.length < 2) return !1;
|
|
330
|
+
const t = s[s.length - 1];
|
|
331
|
+
for (let r = 0; r < s.length - 2; r++)
|
|
332
|
+
if (X(t, e, s[r], s[r + 1]))
|
|
301
333
|
return !0;
|
|
302
334
|
return !1;
|
|
303
335
|
}
|
|
304
|
-
function
|
|
305
|
-
if (
|
|
306
|
-
const e =
|
|
307
|
-
for (let
|
|
308
|
-
if (
|
|
336
|
+
function Z(s) {
|
|
337
|
+
if (s.length < 3) return !1;
|
|
338
|
+
const e = s[0], t = s[s.length - 1];
|
|
339
|
+
for (let r = 1; r < s.length - 2; r++)
|
|
340
|
+
if (X(t, e, s[r], s[r + 1]))
|
|
309
341
|
return !0;
|
|
310
342
|
return !1;
|
|
311
343
|
}
|
|
312
|
-
function
|
|
313
|
-
return
|
|
344
|
+
function Ie(s, e) {
|
|
345
|
+
return s[0] === e[0] && s[1] === e[1];
|
|
314
346
|
}
|
|
315
|
-
function
|
|
316
|
-
const [e, t] =
|
|
347
|
+
function Me(s) {
|
|
348
|
+
const [e, t] = s;
|
|
317
349
|
if (typeof e != "number" || typeof t != "number")
|
|
318
350
|
throw new E(
|
|
319
351
|
`Invalid coordinate: expected [number, number], got [${typeof e}, ${typeof t}]`
|
|
@@ -327,34 +359,34 @@ function be(r) {
|
|
|
327
359
|
`Invalid latitude: ${t}. Must be between -90 and 90.`
|
|
328
360
|
);
|
|
329
361
|
}
|
|
330
|
-
function
|
|
331
|
-
if (!Array.isArray(
|
|
362
|
+
function xe(s) {
|
|
363
|
+
if (!Array.isArray(s))
|
|
332
364
|
throw new E("Ring must be an array of positions.");
|
|
333
|
-
if (
|
|
365
|
+
if (s.length < 4)
|
|
334
366
|
throw new E(
|
|
335
|
-
`Ring must have at least 4 positions (got ${
|
|
367
|
+
`Ring must have at least 4 positions (got ${s.length}). A valid polygon ring requires 3 unique vertices plus a closing vertex.`
|
|
336
368
|
);
|
|
337
|
-
const e =
|
|
338
|
-
if (!
|
|
369
|
+
const e = s[0], t = s[s.length - 1];
|
|
370
|
+
if (!Ie(e, t))
|
|
339
371
|
throw new E(
|
|
340
372
|
"Ring is not closed. The first and last positions must be identical."
|
|
341
373
|
);
|
|
342
|
-
for (const
|
|
343
|
-
if (!Array.isArray(
|
|
374
|
+
for (const r of s) {
|
|
375
|
+
if (!Array.isArray(r) || r.length < 2)
|
|
344
376
|
throw new E(
|
|
345
377
|
"Each position in a ring must be an array of at least 2 numbers."
|
|
346
378
|
);
|
|
347
|
-
|
|
379
|
+
Me(r);
|
|
348
380
|
}
|
|
349
|
-
if (
|
|
381
|
+
if (he(s))
|
|
350
382
|
throw new E(
|
|
351
383
|
"Ring has self-intersections. Polygon edges must not cross each other."
|
|
352
384
|
);
|
|
353
385
|
}
|
|
354
|
-
function
|
|
355
|
-
if (
|
|
386
|
+
function ce(s) {
|
|
387
|
+
if (s == null || typeof s != "object")
|
|
356
388
|
throw new E("Feature must be a non-null object.");
|
|
357
|
-
const e =
|
|
389
|
+
const e = s;
|
|
358
390
|
if (e.type !== "Feature")
|
|
359
391
|
throw new E(
|
|
360
392
|
`Feature.type must be "Feature", got "${String(e.type)}".`
|
|
@@ -370,40 +402,57 @@ function le(r) {
|
|
|
370
402
|
throw new E(
|
|
371
403
|
"Feature.geometry.coordinates must be an array."
|
|
372
404
|
);
|
|
373
|
-
const
|
|
374
|
-
if (
|
|
405
|
+
const r = t.coordinates;
|
|
406
|
+
if (r.length === 0)
|
|
375
407
|
throw new E(
|
|
376
408
|
"Polygon must have at least one ring (outer ring)."
|
|
377
409
|
);
|
|
378
|
-
for (const
|
|
379
|
-
|
|
380
|
-
|
|
410
|
+
for (const a of r)
|
|
411
|
+
xe(a);
|
|
412
|
+
const n = typeof e.id == "string" ? e.id : "", i = e.properties, o = i != null && typeof i == "object" && !Array.isArray(i) ? J(i) : {};
|
|
413
|
+
return {
|
|
414
|
+
id: n,
|
|
415
|
+
type: "Feature",
|
|
416
|
+
geometry: {
|
|
417
|
+
type: "Polygon",
|
|
418
|
+
coordinates: r.map(
|
|
419
|
+
(a) => a.map((h) => [h[0], h[1]])
|
|
420
|
+
)
|
|
421
|
+
},
|
|
422
|
+
properties: o
|
|
423
|
+
};
|
|
381
424
|
}
|
|
382
|
-
function
|
|
383
|
-
if (
|
|
425
|
+
function Pe(s) {
|
|
426
|
+
if (s == null || typeof s != "object")
|
|
384
427
|
throw new E("GeoJSON must be a non-null object.");
|
|
385
|
-
const e =
|
|
428
|
+
const e = s;
|
|
386
429
|
if (e.type !== "FeatureCollection")
|
|
387
430
|
throw new E(
|
|
388
431
|
`GeoJSON.type must be "FeatureCollection", got "${String(e.type)}".`
|
|
389
432
|
);
|
|
390
433
|
if (!Array.isArray(e.features))
|
|
391
434
|
throw new E("GeoJSON.features must be an array.");
|
|
392
|
-
const t =
|
|
393
|
-
for (let
|
|
435
|
+
const t = s, r = [];
|
|
436
|
+
for (let n = 0; n < t.features.length; n++)
|
|
394
437
|
try {
|
|
395
|
-
|
|
396
|
-
} catch (
|
|
397
|
-
throw
|
|
398
|
-
`Invalid feature at index ${
|
|
399
|
-
) :
|
|
438
|
+
r.push(ce(t.features[n]));
|
|
439
|
+
} catch (i) {
|
|
440
|
+
throw i instanceof E ? new E(
|
|
441
|
+
`Invalid feature at index ${n}: ${i.message}`
|
|
442
|
+
) : i;
|
|
400
443
|
}
|
|
401
444
|
return {
|
|
402
445
|
type: "FeatureCollection",
|
|
403
|
-
features:
|
|
446
|
+
features: r
|
|
404
447
|
};
|
|
405
448
|
}
|
|
406
|
-
class
|
|
449
|
+
class Ce {
|
|
450
|
+
mapInteractions() {
|
|
451
|
+
return {
|
|
452
|
+
dragPan: !0,
|
|
453
|
+
doubleClickZoom: !0
|
|
454
|
+
};
|
|
455
|
+
}
|
|
407
456
|
activate() {
|
|
408
457
|
}
|
|
409
458
|
deactivate() {
|
|
@@ -421,32 +470,38 @@ class Ie {
|
|
|
421
470
|
onKeyDown(e, t) {
|
|
422
471
|
}
|
|
423
472
|
}
|
|
424
|
-
const
|
|
425
|
-
class
|
|
473
|
+
const De = 10, $ = 3;
|
|
474
|
+
class Fe {
|
|
426
475
|
constructor(e) {
|
|
427
|
-
this.vertices = [], this.isActive = !1, this.
|
|
476
|
+
this.vertices = [], this.isActive = !1, this.context = e;
|
|
477
|
+
}
|
|
478
|
+
mapInteractions() {
|
|
479
|
+
return {
|
|
480
|
+
dragPan: !1,
|
|
481
|
+
doubleClickZoom: !1
|
|
482
|
+
};
|
|
428
483
|
}
|
|
429
484
|
activate() {
|
|
430
485
|
this.isActive = !0, this.vertices = [];
|
|
431
486
|
}
|
|
432
487
|
deactivate() {
|
|
433
|
-
this.isActive = !1, this.vertices = [], this.
|
|
488
|
+
this.isActive = !1, this.vertices = [], this.context.render.clearPreview();
|
|
434
489
|
}
|
|
435
490
|
onPointerDown(e) {
|
|
436
491
|
if (!this.isActive) return;
|
|
437
492
|
const t = [e.lngLat.lng, e.lngLat.lat];
|
|
438
|
-
if (this.vertices.length >=
|
|
439
|
-
const
|
|
440
|
-
lng:
|
|
441
|
-
lat:
|
|
442
|
-
}),
|
|
443
|
-
if (Math.sqrt(
|
|
444
|
-
if (
|
|
493
|
+
if (this.vertices.length >= $) {
|
|
494
|
+
const r = this.vertices[0], n = this.context.getScreenPoint({
|
|
495
|
+
lng: r[0],
|
|
496
|
+
lat: r[1]
|
|
497
|
+
}), i = e.point.x - n.x, o = e.point.y - n.y;
|
|
498
|
+
if (Math.sqrt(i * i + o * o) <= De) {
|
|
499
|
+
if (Z(this.vertices)) return;
|
|
445
500
|
this.finalizePolygon();
|
|
446
501
|
return;
|
|
447
502
|
}
|
|
448
503
|
}
|
|
449
|
-
|
|
504
|
+
Ee(this.vertices, t) || (this.vertices.push(t), this.updatePreview(e));
|
|
450
505
|
}
|
|
451
506
|
onPointerMove(e) {
|
|
452
507
|
!this.isActive || this.vertices.length === 0 || this.updatePreview(e);
|
|
@@ -454,10 +509,10 @@ class Se {
|
|
|
454
509
|
onPointerUp(e) {
|
|
455
510
|
}
|
|
456
511
|
onDoubleClick(e) {
|
|
457
|
-
this.isActive && (this.vertices.length >
|
|
512
|
+
this.isActive && (this.vertices.length > $ && this.vertices.pop(), this.vertices.length >= $ && (Z(this.vertices) || this.finalizePolygon()), e.originalEvent.preventDefault(), e.originalEvent.stopPropagation());
|
|
458
513
|
}
|
|
459
514
|
onLongPress(e) {
|
|
460
|
-
this.isActive && this.vertices.length > 0 && (this.vertices.pop(), this.vertices.length === 0 ? this.
|
|
515
|
+
this.isActive && this.vertices.length > 0 && (this.vertices.pop(), this.vertices.length === 0 ? this.context.render.clearPreview() : this.context.render.renderPreview(this.buildPreviewCoordinates()));
|
|
461
516
|
}
|
|
462
517
|
onKeyDown(e, t) {
|
|
463
518
|
this.isActive && e === "Escape" && this.cancelDrawing();
|
|
@@ -474,14 +529,14 @@ class Se {
|
|
|
474
529
|
* Update the preview rendering with the current cursor position.
|
|
475
530
|
*/
|
|
476
531
|
updatePreview(e) {
|
|
477
|
-
const t = [e.lngLat.lng, e.lngLat.lat],
|
|
478
|
-
this.
|
|
532
|
+
const t = [e.lngLat.lng, e.lngLat.lat], r = this.buildPreviewCoordinates(t);
|
|
533
|
+
this.context.render.renderPreview(r);
|
|
479
534
|
}
|
|
480
535
|
/**
|
|
481
536
|
* Finalize the polygon: create the feature, push to history, emit event.
|
|
482
537
|
*/
|
|
483
538
|
finalizePolygon() {
|
|
484
|
-
if (this.vertices.length <
|
|
539
|
+
if (this.vertices.length < $) return;
|
|
485
540
|
const e = [
|
|
486
541
|
...this.vertices,
|
|
487
542
|
[...this.vertices[0]]
|
|
@@ -493,500 +548,526 @@ class Se {
|
|
|
493
548
|
coordinates: [e]
|
|
494
549
|
},
|
|
495
550
|
properties: {}
|
|
496
|
-
},
|
|
497
|
-
this.
|
|
551
|
+
}, r = this.context.store.add(t), n = new me(r);
|
|
552
|
+
this.context.history.push(n), this.context.events.emit("create", { feature: v(r) }), this.context.render.renderFeatures(), this.vertices = [], this.context.render.clearPreview();
|
|
498
553
|
}
|
|
499
554
|
/**
|
|
500
555
|
* Cancel the current drawing operation.
|
|
501
556
|
*/
|
|
502
557
|
cancelDrawing() {
|
|
503
|
-
this.vertices = [], this.
|
|
558
|
+
this.vertices = [], this.context.render.clearPreview();
|
|
559
|
+
}
|
|
560
|
+
}
|
|
561
|
+
class Te {
|
|
562
|
+
constructor(e, t) {
|
|
563
|
+
this.selectedIds = /* @__PURE__ */ new Set(), this.context = e, this.onSelectionChange = t;
|
|
564
|
+
}
|
|
565
|
+
getSelectedIds() {
|
|
566
|
+
return Array.from(this.selectedIds);
|
|
567
|
+
}
|
|
568
|
+
getFirstSelectedId() {
|
|
569
|
+
return this.selectedIds.values().next().value;
|
|
570
|
+
}
|
|
571
|
+
hasSelection() {
|
|
572
|
+
return this.selectedIds.size > 0;
|
|
573
|
+
}
|
|
574
|
+
has(e) {
|
|
575
|
+
return this.selectedIds.has(e);
|
|
504
576
|
}
|
|
577
|
+
selectOnly(e) {
|
|
578
|
+
this.selectedIds.clear(), this.selectedIds.add(e);
|
|
579
|
+
}
|
|
580
|
+
remove(e) {
|
|
581
|
+
this.selectedIds.delete(e);
|
|
582
|
+
}
|
|
583
|
+
clear() {
|
|
584
|
+
this.selectedIds.clear();
|
|
585
|
+
}
|
|
586
|
+
clearAndNotify() {
|
|
587
|
+
return this.hasSelection() ? (this.clear(), this.notify(), !0) : !1;
|
|
588
|
+
}
|
|
589
|
+
notify() {
|
|
590
|
+
const e = this.getSelectedIds();
|
|
591
|
+
this.context.render.setSelectedIds(e), this.context.events.emit("selectionchange", { selectedIds: e }), this.onSelectionChange && this.onSelectionChange(e);
|
|
592
|
+
}
|
|
593
|
+
}
|
|
594
|
+
function z(s) {
|
|
595
|
+
const e = s.geometry.coordinates[0];
|
|
596
|
+
return e.slice(0, e.length - 1);
|
|
505
597
|
}
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
let
|
|
509
|
-
|
|
598
|
+
function Q(s) {
|
|
599
|
+
const e = [];
|
|
600
|
+
for (let t = 0; t < s.length; t++) {
|
|
601
|
+
const r = (t + 1) % s.length;
|
|
602
|
+
e.push([
|
|
603
|
+
(s[t][0] + s[r][0]) / 2,
|
|
604
|
+
(s[t][1] + s[r][1]) / 2
|
|
605
|
+
]);
|
|
606
|
+
}
|
|
607
|
+
return e;
|
|
608
|
+
}
|
|
609
|
+
function Le(s, e, t) {
|
|
610
|
+
const r = [...s.geometry.coordinates[0]];
|
|
611
|
+
return r[e] = t, e === 0 && (r[r.length - 1] = t), e === r.length - 1 && (r[0] = t), {
|
|
612
|
+
...s,
|
|
613
|
+
geometry: {
|
|
614
|
+
type: "Polygon",
|
|
615
|
+
coordinates: [r]
|
|
616
|
+
}
|
|
617
|
+
};
|
|
618
|
+
}
|
|
619
|
+
function Ae(s, e, t) {
|
|
620
|
+
const r = s.geometry.coordinates[0].map(
|
|
621
|
+
(n) => [n[0] + e, n[1] + t]
|
|
622
|
+
);
|
|
623
|
+
return {
|
|
624
|
+
...s,
|
|
625
|
+
geometry: {
|
|
626
|
+
type: "Polygon",
|
|
627
|
+
coordinates: [r]
|
|
628
|
+
}
|
|
629
|
+
};
|
|
630
|
+
}
|
|
631
|
+
function ke(s, e, t) {
|
|
632
|
+
const r = [...s.geometry.coordinates[0]];
|
|
633
|
+
return r.splice(e, 0, t), {
|
|
634
|
+
...s,
|
|
635
|
+
geometry: {
|
|
636
|
+
type: "Polygon",
|
|
637
|
+
coordinates: [r]
|
|
638
|
+
}
|
|
639
|
+
};
|
|
640
|
+
}
|
|
641
|
+
function Ve(s, e) {
|
|
642
|
+
const r = z(s).filter((i, o) => o !== e), n = [...r, [...r[0]]];
|
|
643
|
+
return {
|
|
644
|
+
...s,
|
|
645
|
+
geometry: {
|
|
646
|
+
type: "Polygon",
|
|
647
|
+
coordinates: [n]
|
|
648
|
+
}
|
|
649
|
+
};
|
|
650
|
+
}
|
|
651
|
+
const ee = 10, Re = 24, _e = 3;
|
|
652
|
+
class Ne {
|
|
653
|
+
constructor(e) {
|
|
654
|
+
this.dragging = !1, this.dragVertexIndex = -1, this.dragStartFeature = null, this.highlightedVertexIndex = -1, this.context = e;
|
|
655
|
+
}
|
|
656
|
+
isDragging() {
|
|
657
|
+
return this.dragging;
|
|
658
|
+
}
|
|
659
|
+
getDragStartFeature() {
|
|
660
|
+
return this.dragStartFeature;
|
|
661
|
+
}
|
|
662
|
+
resetInteractionState() {
|
|
663
|
+
this.endDrag(), this.highlightedVertexIndex = -1;
|
|
664
|
+
}
|
|
665
|
+
clearHighlight() {
|
|
666
|
+
this.highlightedVertexIndex = -1;
|
|
667
|
+
}
|
|
668
|
+
tryStartVertexDragOrInsert(e, t, r) {
|
|
669
|
+
const n = z(e), i = this.getThreshold(r), o = this.findNearestVertex(n, r.point, i);
|
|
670
|
+
if (o >= 0)
|
|
671
|
+
return this.startDrag(e, o), !0;
|
|
672
|
+
const a = Q(n), h = this.findNearestPoint(a, r.point, i);
|
|
673
|
+
if (h >= 0) {
|
|
674
|
+
const d = v(e), u = ke(e, h + 1, a[h]);
|
|
675
|
+
return this.context.store.update(t, u), this.renderHandles(u), this.startDrag(u, h + 1, d), !0;
|
|
676
|
+
}
|
|
677
|
+
return !1;
|
|
678
|
+
}
|
|
679
|
+
handleDragMove(e, t) {
|
|
680
|
+
if (!this.dragging) return !1;
|
|
681
|
+
const r = this.context.store.getById(e);
|
|
682
|
+
if (!r) return !0;
|
|
683
|
+
const n = [t.lngLat.lng, t.lngLat.lat], i = Le(r, this.dragVertexIndex, n);
|
|
684
|
+
return he(i.geometry.coordinates[0]) || (this.context.store.update(e, i), this.context.render.renderFeatures(), this.renderHandles(i)), !0;
|
|
685
|
+
}
|
|
686
|
+
updateHighlightIfNeeded(e, t) {
|
|
687
|
+
const r = z(e), n = this.getThreshold(t), i = this.findNearestVertex(r, t.point, n);
|
|
688
|
+
i !== this.highlightedVertexIndex && (this.highlightedVertexIndex = i, this.renderHandles(e));
|
|
689
|
+
}
|
|
690
|
+
deleteVertexAtPointer(e, t, r) {
|
|
691
|
+
const n = z(t), i = this.getThreshold(r), o = this.findNearestVertex(n, r.point, i);
|
|
692
|
+
if (o < 0 || n.length <= _e)
|
|
693
|
+
return !1;
|
|
694
|
+
const a = v(t), h = Ve(t, o);
|
|
695
|
+
this.context.store.update(e, h);
|
|
696
|
+
const d = new ae(
|
|
697
|
+
e,
|
|
698
|
+
a,
|
|
699
|
+
v(h)
|
|
700
|
+
);
|
|
701
|
+
return this.context.history.push(d), this.context.events.emit("update", {
|
|
702
|
+
feature: v(h),
|
|
703
|
+
oldFeature: v(a)
|
|
704
|
+
}), this.context.render.renderFeatures(), this.renderHandles(h), !0;
|
|
705
|
+
}
|
|
706
|
+
renderHandles(e) {
|
|
707
|
+
const t = z(e), r = Q(t);
|
|
708
|
+
this.context.render.renderVertices(
|
|
709
|
+
t,
|
|
710
|
+
r,
|
|
711
|
+
this.highlightedVertexIndex >= 0 ? this.highlightedVertexIndex : void 0
|
|
712
|
+
);
|
|
713
|
+
}
|
|
714
|
+
endDrag() {
|
|
715
|
+
this.dragging && this.context.setDragPan(!0), this.dragging = !1, this.dragVertexIndex = -1, this.dragStartFeature = null;
|
|
716
|
+
}
|
|
717
|
+
startDrag(e, t, r = v(e)) {
|
|
718
|
+
this.dragging = !0, this.dragVertexIndex = t, this.dragStartFeature = r, this.context.setDragPan(!1);
|
|
719
|
+
}
|
|
720
|
+
getThreshold(e) {
|
|
721
|
+
return e.inputType === "touch" ? Re : ee;
|
|
722
|
+
}
|
|
723
|
+
findNearestVertex(e, t, r) {
|
|
724
|
+
return this.findNearestPoint(e, t, r);
|
|
725
|
+
}
|
|
726
|
+
findNearestPoint(e, t, r = ee) {
|
|
727
|
+
let n = 1 / 0, i = -1;
|
|
728
|
+
for (let o = 0; o < e.length; o++) {
|
|
729
|
+
const a = this.context.getScreenPoint({
|
|
730
|
+
lng: e[o][0],
|
|
731
|
+
lat: e[o][1]
|
|
732
|
+
}), h = t.x - a.x, d = t.y - a.y, u = Math.sqrt(h * h + d * d);
|
|
733
|
+
u <= r && u < n && (n = u, i = o);
|
|
734
|
+
}
|
|
735
|
+
return i;
|
|
736
|
+
}
|
|
737
|
+
}
|
|
738
|
+
class Be {
|
|
739
|
+
constructor(e, t) {
|
|
740
|
+
this.dragging = !1, this.dragStartFeature = null, this.dragStartLngLat = null, this.context = e, this.onFeatureMoved = t;
|
|
741
|
+
}
|
|
742
|
+
isDragging() {
|
|
743
|
+
return this.dragging;
|
|
744
|
+
}
|
|
745
|
+
getDragStartFeature() {
|
|
746
|
+
return this.dragStartFeature;
|
|
747
|
+
}
|
|
748
|
+
startDrag(e, t) {
|
|
749
|
+
this.dragging = !0, this.dragStartFeature = v(e), this.dragStartLngLat = t, this.context.setDragPan(!1);
|
|
750
|
+
}
|
|
751
|
+
handleDragMove(e, t) {
|
|
752
|
+
if (!this.dragging) return !1;
|
|
753
|
+
if (!this.dragStartFeature || !this.dragStartLngLat) return !0;
|
|
754
|
+
const r = t.lngLat.lng - this.dragStartLngLat.lng, n = t.lngLat.lat - this.dragStartLngLat.lat, i = Ae(this.dragStartFeature, r, n);
|
|
755
|
+
return this.context.store.update(e, i), this.context.render.renderFeatures(), this.onFeatureMoved(i), !0;
|
|
756
|
+
}
|
|
757
|
+
endDrag() {
|
|
758
|
+
this.dragging && this.context.setDragPan(!0), this.dragging = !1, this.dragStartFeature = null, this.dragStartLngLat = null;
|
|
759
|
+
}
|
|
760
|
+
resetInteractionState() {
|
|
761
|
+
this.endDrag();
|
|
762
|
+
}
|
|
763
|
+
}
|
|
764
|
+
const _ = 11102230246251565e-32, D = 134217729, Ue = (3 + 8 * _) * _;
|
|
765
|
+
function Y(s, e, t, r, n) {
|
|
766
|
+
let i, o, a, h, d = e[0], u = r[0], l = 0, c = 0;
|
|
767
|
+
u > d == u > -d ? (i = d, d = e[++l]) : (i = u, u = r[++c]);
|
|
510
768
|
let g = 0;
|
|
511
|
-
if (
|
|
512
|
-
for (u > d == u > -d ? (o = d +
|
|
513
|
-
u > d == u > -d ? (o =
|
|
514
|
-
for (;
|
|
515
|
-
o =
|
|
769
|
+
if (l < s && c < t)
|
|
770
|
+
for (u > d == u > -d ? (o = d + i, a = i - (o - d), d = e[++l]) : (o = u + i, a = i - (o - u), u = r[++c]), i = o, a !== 0 && (n[g++] = a); l < s && c < t; )
|
|
771
|
+
u > d == u > -d ? (o = i + d, h = o - i, a = i - (o - h) + (d - h), d = e[++l]) : (o = i + u, h = o - i, a = i - (o - h) + (u - h), u = r[++c]), i = o, a !== 0 && (n[g++] = a);
|
|
772
|
+
for (; l < s; )
|
|
773
|
+
o = i + d, h = o - i, a = i - (o - h) + (d - h), d = e[++l], i = o, a !== 0 && (n[g++] = a);
|
|
516
774
|
for (; c < t; )
|
|
517
|
-
o =
|
|
518
|
-
return (
|
|
775
|
+
o = i + u, h = o - i, a = i - (o - h) + (u - h), u = r[++c], i = o, a !== 0 && (n[g++] = a);
|
|
776
|
+
return (i !== 0 || g === 0) && (n[g++] = i), g;
|
|
519
777
|
}
|
|
520
|
-
function
|
|
778
|
+
function Oe(s, e) {
|
|
521
779
|
let t = e[0];
|
|
522
|
-
for (let
|
|
780
|
+
for (let r = 1; r < s; r++) t += e[r];
|
|
523
781
|
return t;
|
|
524
782
|
}
|
|
525
|
-
function H(
|
|
526
|
-
return new Float64Array(
|
|
783
|
+
function H(s) {
|
|
784
|
+
return new Float64Array(s);
|
|
527
785
|
}
|
|
528
|
-
const
|
|
529
|
-
function
|
|
530
|
-
let
|
|
531
|
-
const L =
|
|
532
|
-
I = L *
|
|
533
|
-
let
|
|
534
|
-
if (
|
|
535
|
-
I =
|
|
536
|
-
const
|
|
537
|
-
I = L * u, c =
|
|
538
|
-
const
|
|
539
|
-
I =
|
|
540
|
-
const
|
|
541
|
-
return
|
|
786
|
+
const ze = (3 + 16 * _) * _, He = (2 + 12 * _) * _, je = (9 + 64 * _) * _ * _, B = H(4), te = H(8), re = H(12), se = H(16), F = H(4);
|
|
787
|
+
function We(s, e, t, r, n, i, o) {
|
|
788
|
+
let a, h, d, u, l, c, g, m, p, y, f, w, M, I, x, P, T, C;
|
|
789
|
+
const L = s - n, A = t - n, k = e - i, V = r - i;
|
|
790
|
+
I = L * V, c = D * L, g = c - (c - L), m = L - g, c = D * V, p = c - (c - V), y = V - p, x = m * y - (I - g * p - m * p - g * y), P = k * A, c = D * k, g = c - (c - k), m = k - g, c = D * A, p = c - (c - A), y = A - p, T = m * y - (P - g * p - m * p - g * y), f = x - T, l = x - f, B[0] = x - (f + l) + (l - T), w = I + f, l = w - I, M = I - (w - l) + (f - l), f = M - P, l = M - f, B[1] = M - (f + l) + (l - P), C = w + f, l = C - w, B[2] = w - (C - l) + (f - l), B[3] = C;
|
|
791
|
+
let R = Oe(4, B), U = He * o;
|
|
792
|
+
if (R >= U || -R >= U || (l = s - L, a = s - (L + l) + (l - n), l = t - A, d = t - (A + l) + (l - n), l = e - k, h = e - (k + l) + (l - i), l = r - V, u = r - (V + l) + (l - i), a === 0 && h === 0 && d === 0 && u === 0) || (U = je * o + Ue * Math.abs(R), R += L * u + V * a - (k * d + A * h), R >= U || -R >= U)) return R;
|
|
793
|
+
I = a * V, c = D * a, g = c - (c - a), m = a - g, c = D * V, p = c - (c - V), y = V - p, x = m * y - (I - g * p - m * p - g * y), P = h * A, c = D * h, g = c - (c - h), m = h - g, c = D * A, p = c - (c - A), y = A - p, T = m * y - (P - g * p - m * p - g * y), f = x - T, l = x - f, F[0] = x - (f + l) + (l - T), w = I + f, l = w - I, M = I - (w - l) + (f - l), f = M - P, l = M - f, F[1] = M - (f + l) + (l - P), C = w + f, l = C - w, F[2] = w - (C - l) + (f - l), F[3] = C;
|
|
794
|
+
const de = Y(4, B, 4, F, te);
|
|
795
|
+
I = L * u, c = D * L, g = c - (c - L), m = L - g, c = D * u, p = c - (c - u), y = u - p, x = m * y - (I - g * p - m * p - g * y), P = k * d, c = D * k, g = c - (c - k), m = k - g, c = D * d, p = c - (c - d), y = d - p, T = m * y - (P - g * p - m * p - g * y), f = x - T, l = x - f, F[0] = x - (f + l) + (l - T), w = I + f, l = w - I, M = I - (w - l) + (f - l), f = M - P, l = M - f, F[1] = M - (f + l) + (l - P), C = w + f, l = C - w, F[2] = w - (C - l) + (f - l), F[3] = C;
|
|
796
|
+
const ue = Y(de, te, 4, F, re);
|
|
797
|
+
I = a * u, c = D * a, g = c - (c - a), m = a - g, c = D * u, p = c - (c - u), y = u - p, x = m * y - (I - g * p - m * p - g * y), P = h * d, c = D * h, g = c - (c - h), m = h - g, c = D * d, p = c - (c - d), y = d - p, T = m * y - (P - g * p - m * p - g * y), f = x - T, l = x - f, F[0] = x - (f + l) + (l - T), w = I + f, l = w - I, M = I - (w - l) + (f - l), f = M - P, l = M - f, F[1] = M - (f + l) + (l - P), C = w + f, l = C - w, F[2] = w - (C - l) + (f - l), F[3] = C;
|
|
798
|
+
const ge = Y(ue, re, 4, F, se);
|
|
799
|
+
return se[ge - 1];
|
|
542
800
|
}
|
|
543
|
-
function
|
|
544
|
-
const o = (e -
|
|
545
|
-
return Math.abs(h) >=
|
|
801
|
+
function Ge(s, e, t, r, n, i) {
|
|
802
|
+
const o = (e - i) * (t - n), a = (s - n) * (r - i), h = o - a, d = Math.abs(o + a);
|
|
803
|
+
return Math.abs(h) >= ze * d ? h : -We(s, e, t, r, n, i, d);
|
|
546
804
|
}
|
|
547
|
-
function
|
|
548
|
-
var t,
|
|
549
|
-
for (t = 0; t <
|
|
550
|
-
|
|
551
|
-
var p = e[t],
|
|
552
|
-
if (u = p[0], u[0] !== p[
|
|
805
|
+
function $e(s, e) {
|
|
806
|
+
var t, r, n = 0, i, o, a, h, d, u, l, c = s[0], g = s[1], m = e.length;
|
|
807
|
+
for (t = 0; t < m; t++) {
|
|
808
|
+
r = 0;
|
|
809
|
+
var p = e[t], y = p.length - 1;
|
|
810
|
+
if (u = p[0], u[0] !== p[y][0] && u[1] !== p[y][1])
|
|
553
811
|
throw new Error("First and last coordinates in a ring must be the same");
|
|
554
|
-
for (o = u[0] - c,
|
|
555
|
-
if (
|
|
812
|
+
for (o = u[0] - c, a = u[1] - g, r; r < y; r++) {
|
|
813
|
+
if (l = p[r + 1], h = l[0] - c, d = l[1] - g, a === 0 && d === 0) {
|
|
556
814
|
if (h <= 0 && o >= 0 || o <= 0 && h >= 0)
|
|
557
815
|
return 0;
|
|
558
|
-
} else if (d >= 0 &&
|
|
559
|
-
if (
|
|
816
|
+
} else if (d >= 0 && a <= 0 || d <= 0 && a >= 0) {
|
|
817
|
+
if (i = Ge(o, h, a, d, 0, 0), i === 0)
|
|
560
818
|
return 0;
|
|
561
|
-
(
|
|
819
|
+
(i > 0 && d > 0 && a <= 0 || i < 0 && d <= 0 && a > 0) && n++;
|
|
562
820
|
}
|
|
563
|
-
u =
|
|
821
|
+
u = l, a = d, o = h;
|
|
564
822
|
}
|
|
565
823
|
}
|
|
566
|
-
return
|
|
824
|
+
return n % 2 !== 0;
|
|
567
825
|
}
|
|
568
|
-
function
|
|
569
|
-
const
|
|
570
|
-
return (t.id === 0 || t.id) && (
|
|
826
|
+
function Je(s, e, t = {}) {
|
|
827
|
+
const r = { type: "Feature" };
|
|
828
|
+
return (t.id === 0 || t.id) && (r.id = t.id), t.bbox && (r.bbox = t.bbox), r.properties = {}, r.geometry = s, r;
|
|
571
829
|
}
|
|
572
|
-
function
|
|
573
|
-
if (!
|
|
830
|
+
function ie(s, e, t = {}) {
|
|
831
|
+
if (!s)
|
|
574
832
|
throw new Error("coordinates is required");
|
|
575
|
-
if (!Array.isArray(
|
|
833
|
+
if (!Array.isArray(s))
|
|
576
834
|
throw new Error("coordinates must be an Array");
|
|
577
|
-
if (
|
|
835
|
+
if (s.length < 2)
|
|
578
836
|
throw new Error("coordinates must be at least 2 numbers long");
|
|
579
|
-
if (!
|
|
837
|
+
if (!ne(s[0]) || !ne(s[1]))
|
|
580
838
|
throw new Error("coordinates must contain numbers");
|
|
581
|
-
return
|
|
839
|
+
return Je({
|
|
582
840
|
type: "Point",
|
|
583
|
-
coordinates:
|
|
841
|
+
coordinates: s
|
|
584
842
|
}, e, t);
|
|
585
843
|
}
|
|
586
|
-
function
|
|
587
|
-
return !isNaN(
|
|
844
|
+
function ne(s) {
|
|
845
|
+
return !isNaN(s) && s !== null && !Array.isArray(s);
|
|
588
846
|
}
|
|
589
|
-
function
|
|
590
|
-
if (!
|
|
847
|
+
function Ke(s) {
|
|
848
|
+
if (!s)
|
|
591
849
|
throw new Error("coord is required");
|
|
592
|
-
if (!Array.isArray(
|
|
593
|
-
if (
|
|
594
|
-
return [...
|
|
595
|
-
if (
|
|
596
|
-
return [...
|
|
597
|
-
}
|
|
598
|
-
if (Array.isArray(
|
|
599
|
-
return [...
|
|
850
|
+
if (!Array.isArray(s)) {
|
|
851
|
+
if (s.type === "Feature" && s.geometry !== null && s.geometry.type === "Point")
|
|
852
|
+
return [...s.geometry.coordinates];
|
|
853
|
+
if (s.type === "Point")
|
|
854
|
+
return [...s.coordinates];
|
|
855
|
+
}
|
|
856
|
+
if (Array.isArray(s) && s.length >= 2 && !Array.isArray(s[0]) && !Array.isArray(s[1]))
|
|
857
|
+
return [...s];
|
|
600
858
|
throw new Error("coord must be GeoJSON Point or an Array of numbers");
|
|
601
859
|
}
|
|
602
|
-
function
|
|
603
|
-
return
|
|
860
|
+
function Ye(s) {
|
|
861
|
+
return s.type === "Feature" ? s.geometry : s;
|
|
604
862
|
}
|
|
605
|
-
function
|
|
606
|
-
if (!
|
|
863
|
+
function qe(s, e, t = {}) {
|
|
864
|
+
if (!s)
|
|
607
865
|
throw new Error("point is required");
|
|
608
866
|
if (!e)
|
|
609
867
|
throw new Error("polygon is required");
|
|
610
|
-
const
|
|
611
|
-
let
|
|
612
|
-
if (o &&
|
|
868
|
+
const r = Ke(s), n = Ye(e), i = n.type, o = e.bbox;
|
|
869
|
+
let a = n.coordinates;
|
|
870
|
+
if (o && Xe(r, o) === !1)
|
|
613
871
|
return !1;
|
|
614
|
-
|
|
872
|
+
i === "Polygon" && (a = [a]);
|
|
615
873
|
let h = !1;
|
|
616
|
-
for (var d = 0; d <
|
|
617
|
-
const u =
|
|
874
|
+
for (var d = 0; d < a.length; ++d) {
|
|
875
|
+
const u = $e(r, a[d]);
|
|
618
876
|
if (u === 0) return !t.ignoreBoundary;
|
|
619
877
|
u && (h = !0);
|
|
620
878
|
}
|
|
621
879
|
return h;
|
|
622
880
|
}
|
|
623
|
-
function
|
|
624
|
-
return e[0] <=
|
|
881
|
+
function Xe(s, e) {
|
|
882
|
+
return e[0] <= s[0] && e[1] <= s[1] && e[2] >= s[0] && e[3] >= s[1];
|
|
625
883
|
}
|
|
626
|
-
var
|
|
627
|
-
|
|
628
|
-
class Oe {
|
|
884
|
+
var oe = qe;
|
|
885
|
+
class Ze {
|
|
629
886
|
constructor(e, t) {
|
|
630
|
-
this.
|
|
887
|
+
this.isActive = !1, this.context = e, this.selection = new Te(e, t), this.vertexEditor = new Ne(e), this.polygonDragger = new Be(e, (r) => {
|
|
888
|
+
this.vertexEditor.renderHandles(r);
|
|
889
|
+
});
|
|
890
|
+
}
|
|
891
|
+
mapInteractions() {
|
|
892
|
+
return {
|
|
893
|
+
dragPan: !0,
|
|
894
|
+
doubleClickZoom: !1
|
|
895
|
+
};
|
|
631
896
|
}
|
|
632
897
|
activate() {
|
|
633
898
|
this.isActive = !0;
|
|
634
899
|
}
|
|
635
900
|
deactivate() {
|
|
636
|
-
this.isActive = !1, this.
|
|
901
|
+
this.isActive = !1, this.forceClearSelectionState();
|
|
637
902
|
}
|
|
638
903
|
/**
|
|
639
904
|
* Get the currently selected feature IDs.
|
|
640
905
|
*/
|
|
641
906
|
getSelectedIds() {
|
|
642
|
-
return
|
|
907
|
+
return this.selection.getSelectedIds();
|
|
643
908
|
}
|
|
644
909
|
/**
|
|
645
910
|
* Programmatically select a feature by ID.
|
|
646
|
-
*
|
|
647
|
-
* Replaces any existing selection. Renders vertex handles and
|
|
648
|
-
* emits a selectionchange event. Cancels any in-progress drag.
|
|
649
|
-
*
|
|
650
|
-
* @param id - The feature ID to select.
|
|
651
|
-
* @returns `true` if the feature was found and selected, `false` otherwise.
|
|
652
911
|
*/
|
|
653
912
|
selectFeature(e) {
|
|
654
913
|
if (!this.isActive) return !1;
|
|
655
|
-
const t = this.
|
|
656
|
-
return t ? (this.
|
|
914
|
+
const t = this.context.store.getById(e);
|
|
915
|
+
return t ? (this.vertexEditor.resetInteractionState(), this.polygonDragger.resetInteractionState(), this.selection.selectOnly(e), this.vertexEditor.renderHandles(t), this.selection.notify(), this.context.render.renderFeatures(), !0) : !1;
|
|
657
916
|
}
|
|
658
917
|
/**
|
|
659
918
|
* Programmatically clear the current selection.
|
|
660
|
-
*
|
|
661
|
-
* Removes vertex handles and emits a selectionchange event.
|
|
662
|
-
* No-op if nothing is selected or mode is not active.
|
|
919
|
+
* Public API keeps the active-mode guard.
|
|
663
920
|
*/
|
|
664
921
|
clearSelection() {
|
|
665
|
-
this.isActive && this.
|
|
922
|
+
this.isActive && this.selection.hasSelection() && (this.forceClearSelectionState(), this.context.render.renderFeatures());
|
|
666
923
|
}
|
|
667
924
|
onPointerDown(e) {
|
|
668
925
|
if (!this.isActive) return;
|
|
669
|
-
const t = this.getFirstSelectedId();
|
|
926
|
+
const t = this.selection.getFirstSelectedId();
|
|
670
927
|
if (t) {
|
|
671
|
-
const o = this.
|
|
928
|
+
const o = this.context.store.getById(t);
|
|
672
929
|
if (o) {
|
|
673
|
-
|
|
674
|
-
l,
|
|
675
|
-
e.point,
|
|
676
|
-
h
|
|
677
|
-
);
|
|
678
|
-
if (d >= 0) {
|
|
679
|
-
this.startDrag(o, d);
|
|
680
|
-
return;
|
|
681
|
-
}
|
|
682
|
-
const u = this.computeMidpoints(l), a = this.findNearestPoint(u, e.point, h);
|
|
683
|
-
if (a >= 0) {
|
|
684
|
-
const g = R.cloneFeature(o), y = this.insertVertex(o, a + 1, u[a]);
|
|
685
|
-
this.callbacks.updateFeatureInStore(t, y), this.showVertexHandles(y), this.startDrag(y, a + 1), this.dragStartFeature = g;
|
|
930
|
+
if (this.vertexEditor.tryStartVertexDragOrInsert(o, t, e))
|
|
686
931
|
return;
|
|
687
|
-
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
this.startPolygonDrag(o, e.lngLat);
|
|
932
|
+
const a = ie([e.lngLat.lng, e.lngLat.lat]);
|
|
933
|
+
if (oe(a, o.geometry)) {
|
|
934
|
+
this.polygonDragger.startDrag(o, e.lngLat);
|
|
691
935
|
return;
|
|
692
936
|
}
|
|
693
937
|
}
|
|
694
938
|
}
|
|
695
|
-
this.
|
|
696
|
-
const
|
|
697
|
-
let
|
|
698
|
-
for (let o =
|
|
699
|
-
const
|
|
700
|
-
if (
|
|
701
|
-
|
|
939
|
+
this.vertexEditor.clearHighlight();
|
|
940
|
+
const r = ie([e.lngLat.lng, e.lngLat.lat]), n = this.context.store.getAll();
|
|
941
|
+
let i;
|
|
942
|
+
for (let o = n.length - 1; o >= 0; o--) {
|
|
943
|
+
const a = n[o];
|
|
944
|
+
if (oe(r, a.geometry)) {
|
|
945
|
+
i = a;
|
|
702
946
|
break;
|
|
703
947
|
}
|
|
704
948
|
}
|
|
705
|
-
|
|
949
|
+
i ? this.selection.has(i.id) ? (this.selection.remove(i.id), this.context.render.clearVertices()) : (this.selection.selectOnly(i.id), this.vertexEditor.renderHandles(i)) : (this.selection.clear(), this.context.render.clearVertices()), this.selection.notify(), this.context.render.renderFeatures();
|
|
706
950
|
}
|
|
707
951
|
onPointerMove(e) {
|
|
708
952
|
if (!this.isActive) return;
|
|
709
|
-
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
if (!h) return;
|
|
714
|
-
const d = [e.lngLat.lng, e.lngLat.lat], u = this.moveVertex(h, this.dragVertexIndex, d);
|
|
715
|
-
if (ae(u.geometry.coordinates[0]))
|
|
716
|
-
return;
|
|
717
|
-
this.callbacks.updateFeatureInStore(l, u), this.callbacks.renderFeatures(), this.showVertexHandles(u);
|
|
718
|
-
return;
|
|
719
|
-
}
|
|
720
|
-
if (this.draggingPolygon) {
|
|
721
|
-
const l = this.getFirstSelectedId();
|
|
722
|
-
if (!l || !this.dragStartFeature || !this.dragPolygonStartLngLat) return;
|
|
723
|
-
const h = e.lngLat.lng - this.dragPolygonStartLngLat.lng, d = e.lngLat.lat - this.dragPolygonStartLngLat.lat, u = this.movePolygon(this.dragStartFeature, h, d);
|
|
724
|
-
this.callbacks.updateFeatureInStore(l, u), this.callbacks.renderFeatures(), this.showVertexHandles(u);
|
|
725
|
-
return;
|
|
726
|
-
}
|
|
727
|
-
const t = this.getFirstSelectedId();
|
|
728
|
-
if (!t) return;
|
|
729
|
-
const s = this.callbacks.getFeatureById(t);
|
|
730
|
-
if (!s) return;
|
|
731
|
-
const i = this.getVertices(s), n = this.getThreshold(e), o = this.findNearestVertex(i, e.point, n);
|
|
732
|
-
o !== this.highlightedVertexIndex && (this.highlightedVertexIndex = o, this.showVertexHandles(s));
|
|
953
|
+
const t = this.selection.getFirstSelectedId();
|
|
954
|
+
if (!t || this.vertexEditor.handleDragMove(t, e) || this.polygonDragger.handleDragMove(t, e)) return;
|
|
955
|
+
const r = this.context.store.getById(t);
|
|
956
|
+
r && this.vertexEditor.updateHighlightIfNeeded(r, e);
|
|
733
957
|
}
|
|
734
958
|
onPointerUp(e) {
|
|
735
|
-
if (!this.isActive
|
|
736
|
-
const t = this.
|
|
737
|
-
if (!t
|
|
738
|
-
|
|
959
|
+
if (!this.isActive) return;
|
|
960
|
+
const t = this.vertexEditor.isDragging(), r = this.polygonDragger.isDragging();
|
|
961
|
+
if (!t && !r) return;
|
|
962
|
+
const n = this.selection.getFirstSelectedId();
|
|
963
|
+
if (!n) {
|
|
964
|
+
this.vertexEditor.endDrag(), this.polygonDragger.endDrag();
|
|
739
965
|
return;
|
|
740
966
|
}
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
t,
|
|
745
|
-
this.dragStartFeature,
|
|
746
|
-
R.cloneFeature(s)
|
|
747
|
-
);
|
|
748
|
-
this.callbacks.pushToHistory(i), this.callbacks.emitEvent("update", {
|
|
749
|
-
feature: s,
|
|
750
|
-
oldFeature: this.dragStartFeature
|
|
751
|
-
});
|
|
967
|
+
if (t) {
|
|
968
|
+
this.commitDragUpdate(n, this.vertexEditor.getDragStartFeature()), this.vertexEditor.endDrag();
|
|
969
|
+
return;
|
|
752
970
|
}
|
|
753
|
-
this.
|
|
971
|
+
r && (this.commitDragUpdate(
|
|
972
|
+
n,
|
|
973
|
+
this.polygonDragger.getDragStartFeature()
|
|
974
|
+
), this.polygonDragger.endDrag());
|
|
754
975
|
}
|
|
755
976
|
onDoubleClick(e) {
|
|
756
977
|
if (!this.isActive) return;
|
|
757
|
-
const t = this.getFirstSelectedId();
|
|
978
|
+
const t = this.selection.getFirstSelectedId();
|
|
758
979
|
if (!t) return;
|
|
759
|
-
const
|
|
760
|
-
|
|
761
|
-
const i = this.getVertices(s), n = this.getThreshold(e), o = this.findNearestVertex(i, e.point, n);
|
|
762
|
-
if (o >= 0 && i.length > ne) {
|
|
763
|
-
const l = R.cloneFeature(s), h = this.removeVertex(s, o);
|
|
764
|
-
this.callbacks.updateFeatureInStore(t, h);
|
|
765
|
-
const d = new $(t, l, R.cloneFeature(h));
|
|
766
|
-
this.callbacks.pushToHistory(d), this.callbacks.emitEvent("update", {
|
|
767
|
-
feature: h,
|
|
768
|
-
oldFeature: l
|
|
769
|
-
}), this.callbacks.renderFeatures(), this.showVertexHandles(h), e.originalEvent.preventDefault(), e.originalEvent.stopPropagation();
|
|
770
|
-
}
|
|
980
|
+
const r = this.context.store.getById(t);
|
|
981
|
+
r && this.vertexEditor.deleteVertexAtPointer(t, r, e) && (e.originalEvent.preventDefault(), e.originalEvent.stopPropagation());
|
|
771
982
|
}
|
|
772
983
|
onLongPress(e) {
|
|
773
984
|
if (!this.isActive) return;
|
|
774
|
-
const t = this.getFirstSelectedId();
|
|
775
|
-
if (!t)
|
|
776
|
-
|
|
777
|
-
|
|
778
|
-
if (!s) return;
|
|
779
|
-
const i = this.getVertices(s), n = this.getThreshold(e), o = this.findNearestVertex(i, e.point, n);
|
|
780
|
-
if (o >= 0 && i.length > ne) {
|
|
781
|
-
const l = R.cloneFeature(s), h = this.removeVertex(s, o);
|
|
782
|
-
this.callbacks.updateFeatureInStore(t, h);
|
|
783
|
-
const d = new $(t, l, R.cloneFeature(h));
|
|
784
|
-
this.callbacks.pushToHistory(d), this.callbacks.emitEvent("update", {
|
|
785
|
-
feature: h,
|
|
786
|
-
oldFeature: l
|
|
787
|
-
}), this.callbacks.renderFeatures(), this.showVertexHandles(h);
|
|
788
|
-
}
|
|
985
|
+
const t = this.selection.getFirstSelectedId();
|
|
986
|
+
if (!t) return;
|
|
987
|
+
const r = this.context.store.getById(t);
|
|
988
|
+
r && this.vertexEditor.deleteVertexAtPointer(t, r, e);
|
|
789
989
|
}
|
|
790
990
|
onKeyDown(e, t) {
|
|
791
991
|
this.isActive && (e === "Delete" || e === "Backspace") && this.deleteSelected();
|
|
792
992
|
}
|
|
793
993
|
/**
|
|
794
|
-
*
|
|
795
|
-
*/
|
|
796
|
-
getThreshold(e) {
|
|
797
|
-
return e.inputType === "touch" ? Ne : re;
|
|
798
|
-
}
|
|
799
|
-
/**
|
|
800
|
-
* Get the unique vertices (excluding closing point) of a polygon.
|
|
801
|
-
*/
|
|
802
|
-
getVertices(e) {
|
|
803
|
-
const t = e.geometry.coordinates[0];
|
|
804
|
-
return t.slice(0, t.length - 1);
|
|
805
|
-
}
|
|
806
|
-
/**
|
|
807
|
-
* Find the nearest vertex within the hit threshold.
|
|
808
|
-
* @returns The vertex index, or -1 if none is close enough.
|
|
809
|
-
*/
|
|
810
|
-
findNearestVertex(e, t, s) {
|
|
811
|
-
return this.findNearestPoint(e, t, s);
|
|
812
|
-
}
|
|
813
|
-
/**
|
|
814
|
-
* Find the nearest point (vertex or midpoint) within the hit threshold.
|
|
815
|
-
* @returns The index, or -1 if none is close enough.
|
|
816
|
-
*/
|
|
817
|
-
findNearestPoint(e, t, s = re) {
|
|
818
|
-
let i = 1 / 0, n = -1;
|
|
819
|
-
for (let o = 0; o < e.length; o++) {
|
|
820
|
-
const l = this.callbacks.getScreenPoint({
|
|
821
|
-
lng: e[o][0],
|
|
822
|
-
lat: e[o][1]
|
|
823
|
-
}), h = t.x - l.x, d = t.y - l.y, u = Math.sqrt(h * h + d * d);
|
|
824
|
-
u <= s && u < i && (i = u, n = o);
|
|
825
|
-
}
|
|
826
|
-
return n;
|
|
827
|
-
}
|
|
828
|
-
/**
|
|
829
|
-
* Compute midpoints for each edge of the polygon.
|
|
830
|
-
*/
|
|
831
|
-
computeMidpoints(e) {
|
|
832
|
-
const t = [];
|
|
833
|
-
for (let s = 0; s < e.length; s++) {
|
|
834
|
-
const i = (s + 1) % e.length;
|
|
835
|
-
t.push([
|
|
836
|
-
(e[s][0] + e[i][0]) / 2,
|
|
837
|
-
(e[s][1] + e[i][1]) / 2
|
|
838
|
-
]);
|
|
839
|
-
}
|
|
840
|
-
return t;
|
|
841
|
-
}
|
|
842
|
-
/**
|
|
843
|
-
* Start a vertex drag operation.
|
|
844
|
-
*/
|
|
845
|
-
startDrag(e, t) {
|
|
846
|
-
this.dragging = !0, this.dragVertexIndex = t, this.dragStartFeature = R.cloneFeature(e), this.callbacks.setDragPan(!1);
|
|
847
|
-
}
|
|
848
|
-
/**
|
|
849
|
-
* Start a polygon drag (whole-polygon move) operation.
|
|
850
|
-
*/
|
|
851
|
-
startPolygonDrag(e, t) {
|
|
852
|
-
this.draggingPolygon = !0, this.dragPolygonStartLngLat = t, this.dragStartFeature = R.cloneFeature(e), this.callbacks.setDragPan(!1);
|
|
853
|
-
}
|
|
854
|
-
/**
|
|
855
|
-
* End a drag operation and restore map interactions.
|
|
856
|
-
*/
|
|
857
|
-
endDrag() {
|
|
858
|
-
(this.dragging || this.draggingPolygon) && this.callbacks.setDragPan(!0), this.dragging = !1, this.dragVertexIndex = -1, this.dragStartFeature = null, this.draggingPolygon = !1, this.dragPolygonStartLngLat = null, this.highlightedVertexIndex = -1;
|
|
859
|
-
}
|
|
860
|
-
/**
|
|
861
|
-
* Create a new feature with a vertex moved to a new position.
|
|
862
|
-
*/
|
|
863
|
-
moveVertex(e, t, s) {
|
|
864
|
-
const i = [...e.geometry.coordinates[0]];
|
|
865
|
-
return i[t] = s, t === 0 && (i[i.length - 1] = s), t === i.length - 1 && (i[0] = s), {
|
|
866
|
-
...e,
|
|
867
|
-
geometry: {
|
|
868
|
-
type: "Polygon",
|
|
869
|
-
coordinates: [i]
|
|
870
|
-
}
|
|
871
|
-
};
|
|
872
|
-
}
|
|
873
|
-
/**
|
|
874
|
-
* Create a new feature with all vertices translated by the given delta.
|
|
875
|
-
*/
|
|
876
|
-
movePolygon(e, t, s) {
|
|
877
|
-
const i = e.geometry.coordinates[0].map(
|
|
878
|
-
(n) => [n[0] + t, n[1] + s]
|
|
879
|
-
);
|
|
880
|
-
return {
|
|
881
|
-
...e,
|
|
882
|
-
geometry: {
|
|
883
|
-
type: "Polygon",
|
|
884
|
-
coordinates: [i]
|
|
885
|
-
}
|
|
886
|
-
};
|
|
887
|
-
}
|
|
888
|
-
/**
|
|
889
|
-
* Create a new feature with a vertex inserted at the given index.
|
|
890
|
-
*/
|
|
891
|
-
insertVertex(e, t, s) {
|
|
892
|
-
const i = [...e.geometry.coordinates[0]];
|
|
893
|
-
return i.splice(t, 0, s), {
|
|
894
|
-
...e,
|
|
895
|
-
geometry: {
|
|
896
|
-
type: "Polygon",
|
|
897
|
-
coordinates: [i]
|
|
898
|
-
}
|
|
899
|
-
};
|
|
900
|
-
}
|
|
901
|
-
/**
|
|
902
|
-
* Create a new feature with a vertex removed at the given index.
|
|
903
|
-
*/
|
|
904
|
-
removeVertex(e, t) {
|
|
905
|
-
const i = this.getVertices(e).filter((o, l) => l !== t), n = [...i, [...i[0]]];
|
|
906
|
-
return {
|
|
907
|
-
...e,
|
|
908
|
-
geometry: {
|
|
909
|
-
type: "Polygon",
|
|
910
|
-
coordinates: [n]
|
|
911
|
-
}
|
|
912
|
-
};
|
|
913
|
-
}
|
|
914
|
-
/**
|
|
915
|
-
* Refresh vertex/midpoint handles for the currently selected feature.
|
|
916
|
-
* Call this after external geometry changes (e.g. undo/redo).
|
|
994
|
+
* Refresh vertex/midpoint handles after external geometry changes.
|
|
917
995
|
*/
|
|
918
996
|
refreshVertexHandles() {
|
|
919
997
|
if (!this.isActive) return;
|
|
920
|
-
const e = this.getFirstSelectedId();
|
|
998
|
+
const e = this.selection.getFirstSelectedId();
|
|
921
999
|
if (!e) return;
|
|
922
|
-
const t = this.
|
|
923
|
-
t ? this.
|
|
1000
|
+
const t = this.context.store.getById(e);
|
|
1001
|
+
t ? this.vertexEditor.renderHandles(t) : (this.selection.remove(e), this.context.render.clearVertices(), this.selection.notify());
|
|
924
1002
|
}
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
this.
|
|
931
|
-
|
|
1003
|
+
forceClearSelectionState() {
|
|
1004
|
+
this.vertexEditor.resetInteractionState(), this.polygonDragger.resetInteractionState(), this.selection.clearAndNotify() && this.context.render.clearVertices();
|
|
1005
|
+
}
|
|
1006
|
+
commitDragUpdate(e, t) {
|
|
1007
|
+
if (!t) return;
|
|
1008
|
+
const r = this.context.store.getById(e);
|
|
1009
|
+
if (!r || !this.hasGeometryChanged(t, r))
|
|
1010
|
+
return;
|
|
1011
|
+
const n = new ae(
|
|
1012
|
+
e,
|
|
932
1013
|
t,
|
|
933
|
-
|
|
934
|
-
this.highlightedVertexIndex >= 0 ? this.highlightedVertexIndex : void 0
|
|
1014
|
+
v(r)
|
|
935
1015
|
);
|
|
1016
|
+
this.context.history.push(n), this.context.events.emit("update", {
|
|
1017
|
+
feature: v(r),
|
|
1018
|
+
oldFeature: v(t)
|
|
1019
|
+
});
|
|
936
1020
|
}
|
|
937
|
-
/**
|
|
938
|
-
* Get the first selected feature ID.
|
|
939
|
-
*/
|
|
940
|
-
getFirstSelectedId() {
|
|
941
|
-
return this.selectedIds.values().next().value;
|
|
942
|
-
}
|
|
943
|
-
/**
|
|
944
|
-
* Delete all currently selected features.
|
|
945
|
-
*/
|
|
946
1021
|
deleteSelected() {
|
|
947
|
-
if (this.
|
|
948
|
-
const e =
|
|
1022
|
+
if (!this.selection.hasSelection()) return;
|
|
1023
|
+
const e = this.selection.getSelectedIds();
|
|
949
1024
|
for (const t of e) {
|
|
950
|
-
const
|
|
951
|
-
if (
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
}
|
|
1025
|
+
const r = this.context.store.getById(t);
|
|
1026
|
+
if (!r) continue;
|
|
1027
|
+
this.context.store.remove(t);
|
|
1028
|
+
const n = new le(r);
|
|
1029
|
+
this.context.history.push(n), this.context.events.emit("delete", { feature: v(r) });
|
|
956
1030
|
}
|
|
957
|
-
this.
|
|
958
|
-
}
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
1031
|
+
this.selection.clear(), this.context.render.clearVertices(), this.selection.notify(), this.context.render.renderFeatures();
|
|
1032
|
+
}
|
|
1033
|
+
hasGeometryChanged(e, t) {
|
|
1034
|
+
const r = e.geometry.coordinates, n = t.geometry.coordinates;
|
|
1035
|
+
if (r.length !== n.length) return !0;
|
|
1036
|
+
for (let i = 0; i < r.length; i++) {
|
|
1037
|
+
const o = r[i], a = n[i];
|
|
1038
|
+
if (o.length !== a.length) return !0;
|
|
1039
|
+
for (let h = 0; h < o.length; h++)
|
|
1040
|
+
if (o[h][0] !== a[h][0] || o[h][1] !== a[h][1])
|
|
1041
|
+
return !0;
|
|
1042
|
+
}
|
|
1043
|
+
return !1;
|
|
965
1044
|
}
|
|
966
1045
|
}
|
|
967
|
-
class
|
|
1046
|
+
class Qe {
|
|
968
1047
|
constructor(e, t) {
|
|
969
|
-
this.handleMouseDown = (
|
|
970
|
-
this.callbacks.onPointerDown(this.normalize(
|
|
971
|
-
}, this.
|
|
972
|
-
this.callbacks.onPointerMove(this.normalize(
|
|
973
|
-
}, this.
|
|
974
|
-
this.callbacks.
|
|
975
|
-
}, this.
|
|
976
|
-
this.callbacks.
|
|
1048
|
+
this.isPointerDown = !1, this.handleMouseDown = (r) => {
|
|
1049
|
+
this.isPointerDown = !0, this.callbacks.onPointerDown(this.normalize(r));
|
|
1050
|
+
}, this.handleMouseMoveCanvas = (r) => {
|
|
1051
|
+
this.isPointerDown || this.callbacks.onPointerMove(this.normalize(r));
|
|
1052
|
+
}, this.handleMouseMoveWindow = (r) => {
|
|
1053
|
+
this.isPointerDown && this.callbacks.onPointerMove(this.normalize(r));
|
|
1054
|
+
}, this.handleMouseUpWindow = (r) => {
|
|
1055
|
+
this.isPointerDown && (this.isPointerDown = !1, this.callbacks.onPointerUp(this.normalize(r)));
|
|
1056
|
+
}, this.handleDblClick = (r) => {
|
|
1057
|
+
this.callbacks.onDoubleClick(this.normalize(r));
|
|
977
1058
|
}, this.map = e, this.callbacks = t, this.canvas = e.getCanvasContainer();
|
|
978
1059
|
}
|
|
979
1060
|
/**
|
|
980
1061
|
* Start listening for mouse events on the map canvas.
|
|
981
1062
|
*/
|
|
982
1063
|
enable() {
|
|
983
|
-
this.canvas.addEventListener("mousedown", this.handleMouseDown), this.canvas.addEventListener("mousemove", this.
|
|
1064
|
+
this.canvas.addEventListener("mousedown", this.handleMouseDown), this.canvas.addEventListener("mousemove", this.handleMouseMoveCanvas), window.addEventListener("mousemove", this.handleMouseMoveWindow), window.addEventListener("mouseup", this.handleMouseUpWindow), this.canvas.addEventListener("dblclick", this.handleDblClick);
|
|
984
1065
|
}
|
|
985
1066
|
/**
|
|
986
1067
|
* Stop listening for mouse events.
|
|
987
1068
|
*/
|
|
988
1069
|
disable() {
|
|
989
|
-
this.canvas.removeEventListener("mousedown", this.handleMouseDown), this.canvas.removeEventListener("mousemove", this.
|
|
1070
|
+
this.canvas.removeEventListener("mousedown", this.handleMouseDown), this.canvas.removeEventListener("mousemove", this.handleMouseMoveCanvas), window.removeEventListener("mousemove", this.handleMouseMoveWindow), window.removeEventListener("mouseup", this.handleMouseUpWindow), this.canvas.removeEventListener("dblclick", this.handleDblClick), this.isPointerDown = !1;
|
|
990
1071
|
}
|
|
991
1072
|
/**
|
|
992
1073
|
* Destroy the mouse input handler and remove all listeners.
|
|
@@ -998,47 +1079,60 @@ class Ue {
|
|
|
998
1079
|
* Convert a raw MouseEvent into a NormalizedInputEvent.
|
|
999
1080
|
*/
|
|
1000
1081
|
normalize(e) {
|
|
1001
|
-
const t = this.canvas.getBoundingClientRect(),
|
|
1082
|
+
const t = this.canvas.getBoundingClientRect(), r = e.clientX - t.left, n = e.clientY - t.top, i = this.map.unproject([r, n]);
|
|
1002
1083
|
return {
|
|
1003
|
-
lngLat: { lng:
|
|
1004
|
-
point: { x:
|
|
1084
|
+
lngLat: { lng: i.lng, lat: i.lat },
|
|
1085
|
+
point: { x: r, y: n },
|
|
1005
1086
|
originalEvent: e,
|
|
1006
1087
|
inputType: "mouse"
|
|
1007
1088
|
};
|
|
1008
1089
|
}
|
|
1009
1090
|
}
|
|
1010
|
-
const
|
|
1011
|
-
class
|
|
1091
|
+
const et = 300, tt = 500, rt = 15;
|
|
1092
|
+
class st {
|
|
1012
1093
|
constructor(e, t) {
|
|
1013
|
-
this.lastTapTime = 0, this.longPressTimer = null, this.touchStartPos = null, this.isPinching = !1, this.handleTouchStart = (
|
|
1014
|
-
if (
|
|
1015
|
-
|
|
1094
|
+
this.lastTapTime = 0, this.longPressTimer = null, this.touchStartPos = null, this.isPinching = !1, this.longPressFired = !1, this.handleTouchStart = (r) => {
|
|
1095
|
+
if (r.touches.length >= 2) {
|
|
1096
|
+
const i = this.normalize(r);
|
|
1097
|
+
this.isPinching = !0, this.cancelLongPress(), this.endPointerIfActive(i), this.longPressFired = !1;
|
|
1016
1098
|
return;
|
|
1017
1099
|
}
|
|
1018
1100
|
this.isPinching = !1;
|
|
1019
|
-
const
|
|
1020
|
-
this.touchStartPos = { x:
|
|
1021
|
-
this.touchStartPos
|
|
1022
|
-
},
|
|
1023
|
-
}, this.handleTouchMove = (
|
|
1024
|
-
if (
|
|
1101
|
+
const n = this.normalize(r);
|
|
1102
|
+
this.touchStartPos = { x: n.point.x, y: n.point.y }, this.longPressFired = !1, this.cancelLongPress(), this.longPressTimer = setTimeout(() => {
|
|
1103
|
+
!this.touchStartPos || this.isPinching || (this.endPointerIfActive(n), this.longPressFired = !0, this.callbacks.onLongPress(n));
|
|
1104
|
+
}, tt), this.callbacks.onPointerDown(n);
|
|
1105
|
+
}, this.handleTouchMove = (r) => {
|
|
1106
|
+
if (r.touches.length >= 2) {
|
|
1107
|
+
const i = this.normalize(r);
|
|
1108
|
+
this.isPinching = !0, this.endPointerIfActive(i), this.cancelLongPress();
|
|
1109
|
+
return;
|
|
1110
|
+
}
|
|
1111
|
+
if (this.isPinching) {
|
|
1025
1112
|
this.cancelLongPress();
|
|
1026
1113
|
return;
|
|
1027
1114
|
}
|
|
1028
|
-
const
|
|
1115
|
+
const n = this.normalize(r);
|
|
1029
1116
|
if (this.touchStartPos) {
|
|
1030
|
-
const
|
|
1031
|
-
Math.sqrt(
|
|
1117
|
+
const i = n.point.x - this.touchStartPos.x, o = n.point.y - this.touchStartPos.y;
|
|
1118
|
+
Math.sqrt(i * i + o * o) > rt && this.cancelLongPress();
|
|
1032
1119
|
}
|
|
1033
|
-
this.callbacks.onPointerMove(
|
|
1034
|
-
}, this.handleTouchEnd = (
|
|
1035
|
-
if (this.cancelLongPress(),
|
|
1036
|
-
|
|
1120
|
+
this.callbacks.onPointerMove(n);
|
|
1121
|
+
}, this.handleTouchEnd = (r) => {
|
|
1122
|
+
if (this.cancelLongPress(), r.changedTouches.length === 0) return;
|
|
1123
|
+
const n = this.normalizeChangedTouch(r);
|
|
1124
|
+
if (this.endPointerIfActive(n), this.isPinching) {
|
|
1125
|
+
r.touches.length === 0 && (this.isPinching = !1), this.longPressFired = !1;
|
|
1037
1126
|
return;
|
|
1038
1127
|
}
|
|
1039
|
-
if (
|
|
1040
|
-
|
|
1041
|
-
|
|
1128
|
+
if (this.longPressFired) {
|
|
1129
|
+
this.longPressFired = !1, this.lastTapTime = 0;
|
|
1130
|
+
return;
|
|
1131
|
+
}
|
|
1132
|
+
const i = Date.now();
|
|
1133
|
+
i - this.lastTapTime < et ? (this.callbacks.onDoubleClick(n), this.lastTapTime = 0) : this.lastTapTime = i;
|
|
1134
|
+
}, this.handleTouchCancel = (r) => {
|
|
1135
|
+
this.cancelLongPress(), r.changedTouches.length > 0 && this.endPointerIfActive(this.normalizeChangedTouch(r)), this.touchStartPos = null, this.isPinching = !1, this.longPressFired = !1, this.lastTapTime = 0;
|
|
1042
1136
|
}, this.map = e, this.callbacks = t, this.canvas = e.getCanvasContainer();
|
|
1043
1137
|
}
|
|
1044
1138
|
/**
|
|
@@ -1049,13 +1143,13 @@ class je {
|
|
|
1049
1143
|
passive: !1
|
|
1050
1144
|
}), this.canvas.addEventListener("touchmove", this.handleTouchMove, {
|
|
1051
1145
|
passive: !1
|
|
1052
|
-
}), this.canvas.addEventListener("touchend", this.handleTouchEnd);
|
|
1146
|
+
}), this.canvas.addEventListener("touchend", this.handleTouchEnd), this.canvas.addEventListener("touchcancel", this.handleTouchCancel);
|
|
1053
1147
|
}
|
|
1054
1148
|
/**
|
|
1055
1149
|
* Stop listening for touch events.
|
|
1056
1150
|
*/
|
|
1057
1151
|
disable() {
|
|
1058
|
-
this.canvas.removeEventListener("touchstart", this.handleTouchStart), this.canvas.removeEventListener("touchmove", this.handleTouchMove), this.canvas.removeEventListener("touchend", this.handleTouchEnd), this.cancelLongPress();
|
|
1152
|
+
this.canvas.removeEventListener("touchstart", this.handleTouchStart), this.canvas.removeEventListener("touchmove", this.handleTouchMove), this.canvas.removeEventListener("touchend", this.handleTouchEnd), this.canvas.removeEventListener("touchcancel", this.handleTouchCancel), this.cancelLongPress(), this.touchStartPos = null, this.isPinching = !1, this.longPressFired = !1, this.lastTapTime = 0;
|
|
1059
1153
|
}
|
|
1060
1154
|
/**
|
|
1061
1155
|
* Destroy the touch input handler and remove all listeners.
|
|
@@ -1069,14 +1163,20 @@ class je {
|
|
|
1069
1163
|
cancelLongPress() {
|
|
1070
1164
|
this.longPressTimer !== null && (clearTimeout(this.longPressTimer), this.longPressTimer = null);
|
|
1071
1165
|
}
|
|
1166
|
+
/**
|
|
1167
|
+
* End the current pointer interaction if active.
|
|
1168
|
+
*/
|
|
1169
|
+
endPointerIfActive(e) {
|
|
1170
|
+
this.touchStartPos && (this.callbacks.onPointerUp(e), this.touchStartPos = null);
|
|
1171
|
+
}
|
|
1072
1172
|
/**
|
|
1073
1173
|
* Convert a TouchEvent into a NormalizedInputEvent using the first touch.
|
|
1074
1174
|
*/
|
|
1075
1175
|
normalize(e) {
|
|
1076
|
-
const t = e.touches[0],
|
|
1176
|
+
const t = e.touches[0], r = this.canvas.getBoundingClientRect(), n = t.clientX - r.left, i = t.clientY - r.top, o = this.map.unproject([n, i]);
|
|
1077
1177
|
return {
|
|
1078
1178
|
lngLat: { lng: o.lng, lat: o.lat },
|
|
1079
|
-
point: { x:
|
|
1179
|
+
point: { x: n, y: i },
|
|
1080
1180
|
originalEvent: e,
|
|
1081
1181
|
inputType: "touch"
|
|
1082
1182
|
};
|
|
@@ -1086,10 +1186,10 @@ class je {
|
|
|
1086
1186
|
* (for touchend events where touches array is empty).
|
|
1087
1187
|
*/
|
|
1088
1188
|
normalizeChangedTouch(e) {
|
|
1089
|
-
const t = e.changedTouches[0],
|
|
1189
|
+
const t = e.changedTouches[0], r = this.canvas.getBoundingClientRect(), n = t.clientX - r.left, i = t.clientY - r.top, o = this.map.unproject([n, i]);
|
|
1090
1190
|
return {
|
|
1091
1191
|
lngLat: { lng: o.lng, lat: o.lat },
|
|
1092
|
-
point: { x:
|
|
1192
|
+
point: { x: n, y: i },
|
|
1093
1193
|
originalEvent: e,
|
|
1094
1194
|
inputType: "touch"
|
|
1095
1195
|
};
|
|
@@ -1125,36 +1225,36 @@ K.RELEVANT_KEYS = /* @__PURE__ */ new Set([
|
|
|
1125
1225
|
"Delete",
|
|
1126
1226
|
"Backspace"
|
|
1127
1227
|
]);
|
|
1128
|
-
let
|
|
1129
|
-
class
|
|
1228
|
+
let q = K;
|
|
1229
|
+
class it {
|
|
1130
1230
|
constructor(e, t) {
|
|
1131
1231
|
this.getActiveMode = t;
|
|
1132
|
-
const
|
|
1133
|
-
onPointerDown: (
|
|
1134
|
-
var
|
|
1135
|
-
(
|
|
1232
|
+
const r = {
|
|
1233
|
+
onPointerDown: (n) => {
|
|
1234
|
+
var i;
|
|
1235
|
+
(i = this.getActiveMode()) == null || i.onPointerDown(n);
|
|
1136
1236
|
},
|
|
1137
|
-
onPointerMove: (
|
|
1138
|
-
var
|
|
1139
|
-
(
|
|
1237
|
+
onPointerMove: (n) => {
|
|
1238
|
+
var i;
|
|
1239
|
+
(i = this.getActiveMode()) == null || i.onPointerMove(n);
|
|
1140
1240
|
},
|
|
1141
|
-
onPointerUp: (
|
|
1142
|
-
var
|
|
1143
|
-
(
|
|
1241
|
+
onPointerUp: (n) => {
|
|
1242
|
+
var i;
|
|
1243
|
+
(i = this.getActiveMode()) == null || i.onPointerUp(n);
|
|
1144
1244
|
},
|
|
1145
|
-
onDoubleClick: (
|
|
1146
|
-
var
|
|
1147
|
-
(
|
|
1245
|
+
onDoubleClick: (n) => {
|
|
1246
|
+
var i;
|
|
1247
|
+
(i = this.getActiveMode()) == null || i.onDoubleClick(n);
|
|
1148
1248
|
},
|
|
1149
|
-
onLongPress: (
|
|
1150
|
-
var
|
|
1151
|
-
(
|
|
1249
|
+
onLongPress: (n) => {
|
|
1250
|
+
var i;
|
|
1251
|
+
(i = this.getActiveMode()) == null || i.onLongPress(n);
|
|
1152
1252
|
}
|
|
1153
1253
|
};
|
|
1154
|
-
this.mouseInput = new
|
|
1155
|
-
onKeyDown: (
|
|
1254
|
+
this.mouseInput = new Qe(e, r), this.touchInput = new st(e, r), this.keyboardInput = new q({
|
|
1255
|
+
onKeyDown: (n, i) => {
|
|
1156
1256
|
var o;
|
|
1157
|
-
(o = this.getActiveMode()) == null || o.onKeyDown(
|
|
1257
|
+
(o = this.getActiveMode()) == null || o.onKeyDown(n, i);
|
|
1158
1258
|
}
|
|
1159
1259
|
});
|
|
1160
1260
|
}
|
|
@@ -1177,32 +1277,38 @@ class Xe {
|
|
|
1177
1277
|
this.mouseInput.destroy(), this.touchInput.destroy(), this.keyboardInput.destroy();
|
|
1178
1278
|
}
|
|
1179
1279
|
}
|
|
1180
|
-
const
|
|
1280
|
+
const b = {
|
|
1181
1281
|
FEATURES: "libre-draw-features",
|
|
1182
1282
|
PREVIEW: "libre-draw-preview",
|
|
1183
1283
|
EDIT_VERTICES: "libre-draw-edit-vertices"
|
|
1184
|
-
},
|
|
1284
|
+
}, O = {
|
|
1185
1285
|
type: "FeatureCollection",
|
|
1186
1286
|
features: []
|
|
1187
1287
|
};
|
|
1188
|
-
class
|
|
1288
|
+
class nt {
|
|
1189
1289
|
constructor(e) {
|
|
1190
1290
|
this.initialized = !1, this.map = e;
|
|
1191
1291
|
}
|
|
1292
|
+
/**
|
|
1293
|
+
* Whether all required GeoJSON sources exist on the current style.
|
|
1294
|
+
*/
|
|
1295
|
+
hasAllSources() {
|
|
1296
|
+
return !!(this.map.getSource(b.FEATURES) && this.map.getSource(b.PREVIEW) && this.map.getSource(b.EDIT_VERTICES));
|
|
1297
|
+
}
|
|
1192
1298
|
/**
|
|
1193
1299
|
* Initialize the GeoJSON sources on the map.
|
|
1194
1300
|
* Should be called after the map style has loaded.
|
|
1195
1301
|
*/
|
|
1196
1302
|
initialize() {
|
|
1197
|
-
this.initialized || (this.map.getSource(
|
|
1303
|
+
this.initialized && this.hasAllSources() || (this.map.getSource(b.FEATURES) || this.map.addSource(b.FEATURES, {
|
|
1198
1304
|
type: "geojson",
|
|
1199
|
-
data:
|
|
1200
|
-
}), this.map.getSource(
|
|
1305
|
+
data: O
|
|
1306
|
+
}), this.map.getSource(b.PREVIEW) || this.map.addSource(b.PREVIEW, {
|
|
1201
1307
|
type: "geojson",
|
|
1202
|
-
data:
|
|
1203
|
-
}), this.map.getSource(
|
|
1308
|
+
data: O
|
|
1309
|
+
}), this.map.getSource(b.EDIT_VERTICES) || this.map.addSource(b.EDIT_VERTICES, {
|
|
1204
1310
|
type: "geojson",
|
|
1205
|
-
data:
|
|
1311
|
+
data: O
|
|
1206
1312
|
}), this.initialized = !0);
|
|
1207
1313
|
}
|
|
1208
1314
|
/**
|
|
@@ -1210,7 +1316,7 @@ class We {
|
|
|
1210
1316
|
* @param data - A GeoJSON FeatureCollection.
|
|
1211
1317
|
*/
|
|
1212
1318
|
updateFeatures(e) {
|
|
1213
|
-
const t = this.map.getSource(
|
|
1319
|
+
const t = this.map.getSource(b.FEATURES);
|
|
1214
1320
|
t && t.setData(e);
|
|
1215
1321
|
}
|
|
1216
1322
|
/**
|
|
@@ -1218,36 +1324,106 @@ class We {
|
|
|
1218
1324
|
* @param data - A GeoJSON FeatureCollection.
|
|
1219
1325
|
*/
|
|
1220
1326
|
updatePreview(e) {
|
|
1221
|
-
const t = this.map.getSource(
|
|
1327
|
+
const t = this.map.getSource(b.PREVIEW);
|
|
1222
1328
|
t && t.setData(e);
|
|
1223
1329
|
}
|
|
1224
1330
|
/**
|
|
1225
1331
|
* Clear the preview source.
|
|
1226
1332
|
*/
|
|
1227
1333
|
clearPreview() {
|
|
1228
|
-
this.updatePreview(
|
|
1334
|
+
this.updatePreview(O);
|
|
1229
1335
|
}
|
|
1230
1336
|
/**
|
|
1231
1337
|
* Update the edit vertices source with new GeoJSON data.
|
|
1232
1338
|
* @param data - A GeoJSON FeatureCollection of Point features.
|
|
1233
1339
|
*/
|
|
1234
1340
|
updateEditVertices(e) {
|
|
1235
|
-
const t = this.map.getSource(
|
|
1341
|
+
const t = this.map.getSource(b.EDIT_VERTICES);
|
|
1236
1342
|
t && t.setData(e);
|
|
1237
1343
|
}
|
|
1238
1344
|
/**
|
|
1239
1345
|
* Clear the edit vertices source.
|
|
1240
1346
|
*/
|
|
1241
1347
|
clearEditVertices() {
|
|
1242
|
-
this.updateEditVertices(
|
|
1348
|
+
this.updateEditVertices(O);
|
|
1243
1349
|
}
|
|
1244
1350
|
/**
|
|
1245
1351
|
* Remove all sources from the map.
|
|
1246
1352
|
*/
|
|
1247
1353
|
destroy() {
|
|
1248
|
-
this.map.getSource(
|
|
1354
|
+
this.map.getSource(b.FEATURES) && this.map.removeSource(b.FEATURES), this.map.getSource(b.PREVIEW) && this.map.removeSource(b.PREVIEW), this.map.getSource(b.EDIT_VERTICES) && this.map.removeSource(b.EDIT_VERTICES), this.initialized = !1;
|
|
1249
1355
|
}
|
|
1250
1356
|
}
|
|
1357
|
+
const N = {
|
|
1358
|
+
fill: {
|
|
1359
|
+
color: "#3bb2d0",
|
|
1360
|
+
opacity: 0.2,
|
|
1361
|
+
selectedColor: "#fbb03b",
|
|
1362
|
+
selectedOpacity: 0.4
|
|
1363
|
+
},
|
|
1364
|
+
outline: {
|
|
1365
|
+
color: "#3bb2d0",
|
|
1366
|
+
width: 2,
|
|
1367
|
+
selectedColor: "#fbb03b"
|
|
1368
|
+
},
|
|
1369
|
+
vertex: {
|
|
1370
|
+
color: "#ffffff",
|
|
1371
|
+
strokeColor: "#3bb2d0",
|
|
1372
|
+
strokeWidth: 2,
|
|
1373
|
+
radius: 4
|
|
1374
|
+
},
|
|
1375
|
+
preview: {
|
|
1376
|
+
color: "#3bb2d0",
|
|
1377
|
+
width: 2,
|
|
1378
|
+
dasharray: [2, 2]
|
|
1379
|
+
},
|
|
1380
|
+
editVertex: {
|
|
1381
|
+
color: "#ffffff",
|
|
1382
|
+
strokeColor: "#3bb2d0",
|
|
1383
|
+
strokeWidth: 2,
|
|
1384
|
+
radius: 5,
|
|
1385
|
+
highlightedColor: "#ff4444",
|
|
1386
|
+
highlightedStrokeColor: "#cc0000",
|
|
1387
|
+
highlightedRadius: 7
|
|
1388
|
+
},
|
|
1389
|
+
midpoint: {
|
|
1390
|
+
color: "#3bb2d0",
|
|
1391
|
+
opacity: 0.5,
|
|
1392
|
+
radius: 3
|
|
1393
|
+
}
|
|
1394
|
+
};
|
|
1395
|
+
function ot(s) {
|
|
1396
|
+
var e;
|
|
1397
|
+
return {
|
|
1398
|
+
fill: {
|
|
1399
|
+
...N.fill,
|
|
1400
|
+
...s == null ? void 0 : s.fill
|
|
1401
|
+
},
|
|
1402
|
+
outline: {
|
|
1403
|
+
...N.outline,
|
|
1404
|
+
...s == null ? void 0 : s.outline
|
|
1405
|
+
},
|
|
1406
|
+
vertex: {
|
|
1407
|
+
...N.vertex,
|
|
1408
|
+
...s == null ? void 0 : s.vertex
|
|
1409
|
+
},
|
|
1410
|
+
preview: {
|
|
1411
|
+
...N.preview,
|
|
1412
|
+
...s == null ? void 0 : s.preview,
|
|
1413
|
+
dasharray: [
|
|
1414
|
+
...((e = s == null ? void 0 : s.preview) == null ? void 0 : e.dasharray) ?? N.preview.dasharray
|
|
1415
|
+
]
|
|
1416
|
+
},
|
|
1417
|
+
editVertex: {
|
|
1418
|
+
...N.editVertex,
|
|
1419
|
+
...s == null ? void 0 : s.editVertex
|
|
1420
|
+
},
|
|
1421
|
+
midpoint: {
|
|
1422
|
+
...N.midpoint,
|
|
1423
|
+
...s == null ? void 0 : s.midpoint
|
|
1424
|
+
}
|
|
1425
|
+
};
|
|
1426
|
+
}
|
|
1251
1427
|
const S = {
|
|
1252
1428
|
FILL: "libre-draw-fill",
|
|
1253
1429
|
OUTLINE: "libre-draw-outline",
|
|
@@ -1255,124 +1431,116 @@ const S = {
|
|
|
1255
1431
|
PREVIEW: "libre-draw-preview",
|
|
1256
1432
|
EDIT_VERTICES: "libre-draw-edit-vertices",
|
|
1257
1433
|
EDIT_MIDPOINTS: "libre-draw-edit-midpoints"
|
|
1258
|
-
}, w = {
|
|
1259
|
-
FILL: "#3bb2d0",
|
|
1260
|
-
FILL_OPACITY: 0.2,
|
|
1261
|
-
FILL_SELECTED: "#fbb03b",
|
|
1262
|
-
FILL_SELECTED_OPACITY: 0.4,
|
|
1263
|
-
OUTLINE: "#3bb2d0",
|
|
1264
|
-
OUTLINE_WIDTH: 2,
|
|
1265
|
-
OUTLINE_SELECTED: "#fbb03b",
|
|
1266
|
-
VERTEX_COLOR: "#ffffff",
|
|
1267
|
-
VERTEX_STROKE: "#3bb2d0",
|
|
1268
|
-
VERTEX_RADIUS: 4,
|
|
1269
|
-
PREVIEW_OUTLINE: "#3bb2d0",
|
|
1270
|
-
PREVIEW_OUTLINE_DASH: [2, 2],
|
|
1271
|
-
EDIT_VERTEX_COLOR: "#ffffff",
|
|
1272
|
-
EDIT_VERTEX_STROKE: "#3bb2d0",
|
|
1273
|
-
EDIT_VERTEX_RADIUS: 5,
|
|
1274
|
-
EDIT_VERTEX_STROKE_WIDTH: 2,
|
|
1275
|
-
MIDPOINT_COLOR: "#3bb2d0",
|
|
1276
|
-
MIDPOINT_OPACITY: 0.5,
|
|
1277
|
-
MIDPOINT_RADIUS: 3
|
|
1278
1434
|
};
|
|
1279
|
-
class
|
|
1280
|
-
constructor(e, t) {
|
|
1281
|
-
this.selectedIds = /* @__PURE__ */ new Set(), this.pendingRender = !1, this.pendingFeatures = null, this.initialized = !1, this.map = e, this.sourceManager = t;
|
|
1435
|
+
class at {
|
|
1436
|
+
constructor(e, t, r) {
|
|
1437
|
+
this.selectedIds = /* @__PURE__ */ new Set(), this.pendingRender = !1, this.pendingFeatures = null, this.initialized = !1, this.map = e, this.sourceManager = t, this.style = ot(r);
|
|
1438
|
+
}
|
|
1439
|
+
/**
|
|
1440
|
+
* Whether render layers and sources are ready on the current style.
|
|
1441
|
+
*/
|
|
1442
|
+
isReadyForCurrentStyle() {
|
|
1443
|
+
return this.sourceManager.hasAllSources() && this.hasAllLayers();
|
|
1282
1444
|
}
|
|
1283
1445
|
/**
|
|
1284
1446
|
* Initialize rendering layers on the map.
|
|
1285
1447
|
* Should be called after the map style and sources are ready.
|
|
1286
1448
|
*/
|
|
1287
1449
|
initialize() {
|
|
1288
|
-
this.initialized
|
|
1289
|
-
|
|
1290
|
-
|
|
1291
|
-
|
|
1292
|
-
paint: {
|
|
1293
|
-
"fill-color": [
|
|
1294
|
-
"case",
|
|
1295
|
-
["boolean", ["get", "_selected"], !1],
|
|
1296
|
-
w.FILL_SELECTED,
|
|
1297
|
-
w.FILL
|
|
1298
|
-
],
|
|
1299
|
-
"fill-opacity": [
|
|
1300
|
-
"case",
|
|
1301
|
-
["boolean", ["get", "_selected"], !1],
|
|
1302
|
-
w.FILL_SELECTED_OPACITY,
|
|
1303
|
-
w.FILL_OPACITY
|
|
1304
|
-
]
|
|
1305
|
-
}
|
|
1306
|
-
}), this.map.getLayer(S.OUTLINE) || this.map.addLayer({
|
|
1307
|
-
id: S.OUTLINE,
|
|
1308
|
-
type: "line",
|
|
1309
|
-
source: v.FEATURES,
|
|
1310
|
-
paint: {
|
|
1311
|
-
"line-color": [
|
|
1312
|
-
"case",
|
|
1313
|
-
["boolean", ["get", "_selected"], !1],
|
|
1314
|
-
w.OUTLINE_SELECTED,
|
|
1315
|
-
w.OUTLINE
|
|
1316
|
-
],
|
|
1317
|
-
"line-width": w.OUTLINE_WIDTH
|
|
1318
|
-
}
|
|
1319
|
-
}), this.map.getLayer(S.VERTICES) || this.map.addLayer({
|
|
1320
|
-
id: S.VERTICES,
|
|
1321
|
-
type: "circle",
|
|
1322
|
-
source: v.FEATURES,
|
|
1323
|
-
filter: ["==", "$type", "Point"],
|
|
1324
|
-
paint: {
|
|
1325
|
-
"circle-radius": w.VERTEX_RADIUS,
|
|
1326
|
-
"circle-color": w.VERTEX_COLOR,
|
|
1327
|
-
"circle-stroke-color": w.VERTEX_STROKE,
|
|
1328
|
-
"circle-stroke-width": 2
|
|
1329
|
-
}
|
|
1330
|
-
}), this.map.getLayer(S.PREVIEW) || this.map.addLayer({
|
|
1331
|
-
id: S.PREVIEW,
|
|
1332
|
-
type: "line",
|
|
1333
|
-
source: v.PREVIEW,
|
|
1334
|
-
paint: {
|
|
1335
|
-
"line-color": w.PREVIEW_OUTLINE,
|
|
1336
|
-
"line-width": 2,
|
|
1337
|
-
"line-dasharray": w.PREVIEW_OUTLINE_DASH
|
|
1338
|
-
}
|
|
1339
|
-
}), this.map.getLayer(S.EDIT_MIDPOINTS) || this.map.addLayer({
|
|
1340
|
-
id: S.EDIT_MIDPOINTS,
|
|
1341
|
-
type: "circle",
|
|
1342
|
-
source: v.EDIT_VERTICES,
|
|
1343
|
-
filter: ["==", ["get", "_type"], "midpoint"],
|
|
1344
|
-
paint: {
|
|
1345
|
-
"circle-radius": w.MIDPOINT_RADIUS,
|
|
1346
|
-
"circle-color": w.MIDPOINT_COLOR,
|
|
1347
|
-
"circle-opacity": w.MIDPOINT_OPACITY
|
|
1348
|
-
}
|
|
1349
|
-
}), this.map.getLayer(S.EDIT_VERTICES) || this.map.addLayer({
|
|
1350
|
-
id: S.EDIT_VERTICES,
|
|
1351
|
-
type: "circle",
|
|
1352
|
-
source: v.EDIT_VERTICES,
|
|
1353
|
-
filter: ["==", ["get", "_type"], "vertex"],
|
|
1354
|
-
paint: {
|
|
1355
|
-
"circle-radius": [
|
|
1356
|
-
"case",
|
|
1357
|
-
["boolean", ["get", "_highlighted"], !1],
|
|
1358
|
-
7,
|
|
1359
|
-
w.EDIT_VERTEX_RADIUS
|
|
1360
|
-
],
|
|
1361
|
-
"circle-color": [
|
|
1362
|
-
"case",
|
|
1363
|
-
["boolean", ["get", "_highlighted"], !1],
|
|
1364
|
-
"#ff4444",
|
|
1365
|
-
w.EDIT_VERTEX_COLOR
|
|
1366
|
-
],
|
|
1367
|
-
"circle-stroke-color": [
|
|
1368
|
-
"case",
|
|
1369
|
-
["boolean", ["get", "_highlighted"], !1],
|
|
1370
|
-
"#cc0000",
|
|
1371
|
-
w.EDIT_VERTEX_STROKE
|
|
1372
|
-
],
|
|
1373
|
-
"circle-stroke-width": w.EDIT_VERTEX_STROKE_WIDTH
|
|
1450
|
+
if (!(this.initialized && this.isReadyForCurrentStyle())) {
|
|
1451
|
+
if (this.sourceManager.initialize(), this.hasAllLayers()) {
|
|
1452
|
+
this.initialized = !0;
|
|
1453
|
+
return;
|
|
1374
1454
|
}
|
|
1375
|
-
|
|
1455
|
+
this.map.getLayer(S.FILL) || this.map.addLayer({
|
|
1456
|
+
id: S.FILL,
|
|
1457
|
+
type: "fill",
|
|
1458
|
+
source: b.FEATURES,
|
|
1459
|
+
paint: {
|
|
1460
|
+
"fill-color": [
|
|
1461
|
+
"case",
|
|
1462
|
+
["boolean", ["get", "_selected"], !1],
|
|
1463
|
+
this.style.fill.selectedColor,
|
|
1464
|
+
this.style.fill.color
|
|
1465
|
+
],
|
|
1466
|
+
"fill-opacity": [
|
|
1467
|
+
"case",
|
|
1468
|
+
["boolean", ["get", "_selected"], !1],
|
|
1469
|
+
this.style.fill.selectedOpacity,
|
|
1470
|
+
this.style.fill.opacity
|
|
1471
|
+
]
|
|
1472
|
+
}
|
|
1473
|
+
}), this.map.getLayer(S.OUTLINE) || this.map.addLayer({
|
|
1474
|
+
id: S.OUTLINE,
|
|
1475
|
+
type: "line",
|
|
1476
|
+
source: b.FEATURES,
|
|
1477
|
+
paint: {
|
|
1478
|
+
"line-color": [
|
|
1479
|
+
"case",
|
|
1480
|
+
["boolean", ["get", "_selected"], !1],
|
|
1481
|
+
this.style.outline.selectedColor,
|
|
1482
|
+
this.style.outline.color
|
|
1483
|
+
],
|
|
1484
|
+
"line-width": this.style.outline.width
|
|
1485
|
+
}
|
|
1486
|
+
}), this.map.getLayer(S.VERTICES) || this.map.addLayer({
|
|
1487
|
+
id: S.VERTICES,
|
|
1488
|
+
type: "circle",
|
|
1489
|
+
source: b.FEATURES,
|
|
1490
|
+
filter: ["==", "$type", "Point"],
|
|
1491
|
+
paint: {
|
|
1492
|
+
"circle-radius": this.style.vertex.radius,
|
|
1493
|
+
"circle-color": this.style.vertex.color,
|
|
1494
|
+
"circle-stroke-color": this.style.vertex.strokeColor,
|
|
1495
|
+
"circle-stroke-width": this.style.vertex.strokeWidth
|
|
1496
|
+
}
|
|
1497
|
+
}), this.map.getLayer(S.PREVIEW) || this.map.addLayer({
|
|
1498
|
+
id: S.PREVIEW,
|
|
1499
|
+
type: "line",
|
|
1500
|
+
source: b.PREVIEW,
|
|
1501
|
+
paint: {
|
|
1502
|
+
"line-color": this.style.preview.color,
|
|
1503
|
+
"line-width": this.style.preview.width,
|
|
1504
|
+
"line-dasharray": this.style.preview.dasharray
|
|
1505
|
+
}
|
|
1506
|
+
}), this.map.getLayer(S.EDIT_MIDPOINTS) || this.map.addLayer({
|
|
1507
|
+
id: S.EDIT_MIDPOINTS,
|
|
1508
|
+
type: "circle",
|
|
1509
|
+
source: b.EDIT_VERTICES,
|
|
1510
|
+
filter: ["==", ["get", "_type"], "midpoint"],
|
|
1511
|
+
paint: {
|
|
1512
|
+
"circle-radius": this.style.midpoint.radius,
|
|
1513
|
+
"circle-color": this.style.midpoint.color,
|
|
1514
|
+
"circle-opacity": this.style.midpoint.opacity
|
|
1515
|
+
}
|
|
1516
|
+
}), this.map.getLayer(S.EDIT_VERTICES) || this.map.addLayer({
|
|
1517
|
+
id: S.EDIT_VERTICES,
|
|
1518
|
+
type: "circle",
|
|
1519
|
+
source: b.EDIT_VERTICES,
|
|
1520
|
+
filter: ["==", ["get", "_type"], "vertex"],
|
|
1521
|
+
paint: {
|
|
1522
|
+
"circle-radius": [
|
|
1523
|
+
"case",
|
|
1524
|
+
["boolean", ["get", "_highlighted"], !1],
|
|
1525
|
+
this.style.editVertex.highlightedRadius,
|
|
1526
|
+
this.style.editVertex.radius
|
|
1527
|
+
],
|
|
1528
|
+
"circle-color": [
|
|
1529
|
+
"case",
|
|
1530
|
+
["boolean", ["get", "_highlighted"], !1],
|
|
1531
|
+
this.style.editVertex.highlightedColor,
|
|
1532
|
+
this.style.editVertex.color
|
|
1533
|
+
],
|
|
1534
|
+
"circle-stroke-color": [
|
|
1535
|
+
"case",
|
|
1536
|
+
["boolean", ["get", "_highlighted"], !1],
|
|
1537
|
+
this.style.editVertex.highlightedStrokeColor,
|
|
1538
|
+
this.style.editVertex.strokeColor
|
|
1539
|
+
],
|
|
1540
|
+
"circle-stroke-width": this.style.editVertex.strokeWidth
|
|
1541
|
+
}
|
|
1542
|
+
}), this.initialized = !0;
|
|
1543
|
+
}
|
|
1376
1544
|
}
|
|
1377
1545
|
/**
|
|
1378
1546
|
* Render features to the map. Uses requestAnimationFrame
|
|
@@ -1394,8 +1562,8 @@ class Ke {
|
|
|
1394
1562
|
return;
|
|
1395
1563
|
}
|
|
1396
1564
|
const t = e.map(
|
|
1397
|
-
(
|
|
1398
|
-
),
|
|
1565
|
+
(n) => [n[0], n[1]]
|
|
1566
|
+
), r = {
|
|
1399
1567
|
type: "FeatureCollection",
|
|
1400
1568
|
features: [
|
|
1401
1569
|
{
|
|
@@ -1408,7 +1576,7 @@ class Ke {
|
|
|
1408
1576
|
}
|
|
1409
1577
|
]
|
|
1410
1578
|
};
|
|
1411
|
-
this.sourceManager.updatePreview(
|
|
1579
|
+
this.sourceManager.updatePreview(r);
|
|
1412
1580
|
}
|
|
1413
1581
|
/**
|
|
1414
1582
|
* Clear the drawing preview.
|
|
@@ -1422,28 +1590,28 @@ class Ke {
|
|
|
1422
1590
|
* @param midpoints - The edge midpoint positions.
|
|
1423
1591
|
* @param highlightIndex - Optional index of the vertex to highlight.
|
|
1424
1592
|
*/
|
|
1425
|
-
renderVertices(e, t,
|
|
1426
|
-
const
|
|
1427
|
-
for (let
|
|
1428
|
-
const o = e[
|
|
1429
|
-
|
|
1593
|
+
renderVertices(e, t, r) {
|
|
1594
|
+
const n = [];
|
|
1595
|
+
for (let i = 0; i < e.length; i++) {
|
|
1596
|
+
const o = e[i];
|
|
1597
|
+
n.push({
|
|
1430
1598
|
type: "Feature",
|
|
1431
1599
|
properties: {
|
|
1432
1600
|
_type: "vertex",
|
|
1433
|
-
_highlighted:
|
|
1601
|
+
_highlighted: i === r
|
|
1434
1602
|
},
|
|
1435
1603
|
geometry: { type: "Point", coordinates: [o[0], o[1]] }
|
|
1436
1604
|
});
|
|
1437
1605
|
}
|
|
1438
|
-
for (const
|
|
1439
|
-
|
|
1606
|
+
for (const i of t)
|
|
1607
|
+
n.push({
|
|
1440
1608
|
type: "Feature",
|
|
1441
1609
|
properties: { _type: "midpoint" },
|
|
1442
|
-
geometry: { type: "Point", coordinates: [
|
|
1610
|
+
geometry: { type: "Point", coordinates: [i[0], i[1]] }
|
|
1443
1611
|
});
|
|
1444
1612
|
this.sourceManager.updateEditVertices({
|
|
1445
1613
|
type: "FeatureCollection",
|
|
1446
|
-
features:
|
|
1614
|
+
features: n
|
|
1447
1615
|
});
|
|
1448
1616
|
}
|
|
1449
1617
|
/**
|
|
@@ -1484,22 +1652,28 @@ class Ke {
|
|
|
1484
1652
|
const t = {
|
|
1485
1653
|
type: "FeatureCollection",
|
|
1486
1654
|
features: this.pendingFeatures.map(
|
|
1487
|
-
(
|
|
1655
|
+
(r) => ({
|
|
1488
1656
|
type: "Feature",
|
|
1489
|
-
id:
|
|
1657
|
+
id: r.id,
|
|
1490
1658
|
properties: {
|
|
1491
|
-
...
|
|
1492
|
-
_id:
|
|
1493
|
-
_selected: this.selectedIds.has(
|
|
1659
|
+
...r.properties,
|
|
1660
|
+
_id: r.id,
|
|
1661
|
+
_selected: this.selectedIds.has(r.id)
|
|
1494
1662
|
},
|
|
1495
|
-
geometry:
|
|
1663
|
+
geometry: r.geometry
|
|
1496
1664
|
})
|
|
1497
1665
|
)
|
|
1498
1666
|
};
|
|
1499
1667
|
this.sourceManager.updateFeatures(t), this.pendingFeatures = null;
|
|
1500
1668
|
}
|
|
1669
|
+
/**
|
|
1670
|
+
* Whether all draw layers exist on the current style.
|
|
1671
|
+
*/
|
|
1672
|
+
hasAllLayers() {
|
|
1673
|
+
return !!(this.map.getLayer(S.FILL) && this.map.getLayer(S.OUTLINE) && this.map.getLayer(S.VERTICES) && this.map.getLayer(S.PREVIEW) && this.map.getLayer(S.EDIT_MIDPOINTS) && this.map.getLayer(S.EDIT_VERTICES));
|
|
1674
|
+
}
|
|
1501
1675
|
}
|
|
1502
|
-
class
|
|
1676
|
+
class lt {
|
|
1503
1677
|
constructor(e) {
|
|
1504
1678
|
this.options = e, this.element = document.createElement("button"), this.element.type = "button", this.element.title = e.title, this.element.setAttribute("aria-label", e.title), this.element.dataset.libreDrawButton = e.id, this.applyStyles(), this.iconContainer = document.createElement("span"), this.iconContainer.style.display = "flex", this.iconContainer.style.alignItems = "center", this.iconContainer.style.justifyContent = "center", this.setIcon(e.icon), this.element.appendChild(this.iconContainer), this.element.addEventListener("click", (t) => {
|
|
1505
1679
|
t.preventDefault(), t.stopPropagation(), this.element.disabled || e.onClick();
|
|
@@ -1535,11 +1709,11 @@ class $e {
|
|
|
1535
1709
|
* Set the icon SVG content using DOM parsing (no innerHTML).
|
|
1536
1710
|
*/
|
|
1537
1711
|
setIcon(e) {
|
|
1538
|
-
const
|
|
1712
|
+
const n = new DOMParser().parseFromString(e, "image/svg+xml").documentElement;
|
|
1539
1713
|
for (; this.iconContainer.firstChild; )
|
|
1540
1714
|
this.iconContainer.removeChild(this.iconContainer.firstChild);
|
|
1541
1715
|
this.iconContainer.appendChild(
|
|
1542
|
-
document.importNode(
|
|
1716
|
+
document.importNode(n, !0)
|
|
1543
1717
|
);
|
|
1544
1718
|
}
|
|
1545
1719
|
/**
|
|
@@ -1550,24 +1724,24 @@ class $e {
|
|
|
1550
1724
|
e.display = "flex", e.alignItems = "center", e.justifyContent = "center", e.width = "44px", e.height = "44px", e.padding = "0", e.margin = "0", e.border = "1px solid #ddd", e.borderRadius = "4px", e.backgroundColor = "#ffffff", e.color = "#333333", e.cursor = "pointer", e.outline = "none", e.transition = "background-color 0.15s, color 0.15s", e.boxSizing = "border-box";
|
|
1551
1725
|
}
|
|
1552
1726
|
}
|
|
1553
|
-
const
|
|
1727
|
+
const ht = '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="18" height="18" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M12 2l8.5 6.2-3.2 9.8H6.7L3.5 8.2z"/></svg>', ct = '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="18" height="18" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M3 3l7.07 16.97 2.51-7.39 7.39-2.51L3 3z"/><path d="M13 13l6 6"/></svg>', dt = '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="18" height="18" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="3 6 5 6 21 6"/><path d="M19 6v14a2 2 0 01-2 2H7a2 2 0 01-2-2V6m3 0V4a2 2 0 012-2h4a2 2 0 012 2v2"/><line x1="10" y1="11" x2="10" y2="17"/><line x1="14" y1="11" x2="14" y2="17"/></svg>', ut = '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="18" height="18" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="9 14 4 9 9 4"/><path d="M20 20v-7a4 4 0 00-4-4H4"/></svg>', gt = '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="18" height="18" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="15 14 20 9 15 4"/><path d="M4 20v-7a4 4 0 014-4h12"/></svg>', ft = {
|
|
1554
1728
|
draw: !0,
|
|
1555
1729
|
select: !0,
|
|
1556
1730
|
delete: !0,
|
|
1557
1731
|
undo: !0,
|
|
1558
1732
|
redo: !0
|
|
1559
1733
|
};
|
|
1560
|
-
class
|
|
1561
|
-
constructor(e, t,
|
|
1562
|
-
this.buttons = /* @__PURE__ */ new Map(), this.map = e, this.callbacks = t, this.options =
|
|
1734
|
+
class pt {
|
|
1735
|
+
constructor(e, t, r = {}) {
|
|
1736
|
+
this.buttons = /* @__PURE__ */ new Map(), this.map = e, this.callbacks = t, this.options = r, this.container = document.createElement("div"), this.container.className = "libre-draw-toolbar", this.applyContainerStyles(), this.createButtons(), this.mount();
|
|
1563
1737
|
}
|
|
1564
1738
|
/**
|
|
1565
1739
|
* Update the active mode displayed in the toolbar.
|
|
1566
1740
|
* @param mode - The active mode name ('idle', 'draw', 'select').
|
|
1567
1741
|
*/
|
|
1568
1742
|
setActiveMode(e) {
|
|
1569
|
-
const t = this.buttons.get("draw"),
|
|
1570
|
-
t && t.setActive(e === "draw"),
|
|
1743
|
+
const t = this.buttons.get("draw"), r = this.buttons.get("select");
|
|
1744
|
+
t && t.setActive(e === "draw"), r && r.setActive(e === "select");
|
|
1571
1745
|
}
|
|
1572
1746
|
/**
|
|
1573
1747
|
* Update the undo/redo button states.
|
|
@@ -1575,8 +1749,8 @@ class et {
|
|
|
1575
1749
|
* @param canRedo - Whether redo is available.
|
|
1576
1750
|
*/
|
|
1577
1751
|
setHistoryState(e, t) {
|
|
1578
|
-
const
|
|
1579
|
-
|
|
1752
|
+
const r = this.buttons.get("undo"), n = this.buttons.get("redo");
|
|
1753
|
+
r && r.setDisabled(!e), n && n.setDisabled(!t);
|
|
1580
1754
|
}
|
|
1581
1755
|
/**
|
|
1582
1756
|
* Remove the toolbar from the map and clean up.
|
|
@@ -1591,36 +1765,36 @@ class et {
|
|
|
1591
1765
|
*/
|
|
1592
1766
|
createButtons() {
|
|
1593
1767
|
const e = {
|
|
1594
|
-
...
|
|
1768
|
+
...ft,
|
|
1595
1769
|
...this.options.controls
|
|
1596
1770
|
};
|
|
1597
|
-
e.draw && this.addButton("draw",
|
|
1771
|
+
e.draw && this.addButton("draw", ht, "Draw polygon", () => {
|
|
1598
1772
|
this.callbacks.onDrawClick();
|
|
1599
|
-
}, !0), e.select && this.addButton("select",
|
|
1773
|
+
}, !0), e.select && this.addButton("select", ct, "Select feature", () => {
|
|
1600
1774
|
this.callbacks.onSelectClick();
|
|
1601
|
-
}, !0), e.delete && this.addButton("delete",
|
|
1775
|
+
}, !0), e.delete && this.addButton("delete", dt, "Delete selected", () => {
|
|
1602
1776
|
this.callbacks.onDeleteClick();
|
|
1603
|
-
}), e.undo && this.addButton("undo",
|
|
1777
|
+
}), e.undo && this.addButton("undo", ut, "Undo", () => {
|
|
1604
1778
|
this.callbacks.onUndoClick();
|
|
1605
|
-
}), e.redo && this.addButton("redo",
|
|
1779
|
+
}), e.redo && this.addButton("redo", gt, "Redo", () => {
|
|
1606
1780
|
this.callbacks.onRedoClick();
|
|
1607
1781
|
});
|
|
1608
1782
|
}
|
|
1609
1783
|
/**
|
|
1610
1784
|
* Create a button and add it to the toolbar.
|
|
1611
1785
|
*/
|
|
1612
|
-
addButton(e, t,
|
|
1613
|
-
const o = new
|
|
1786
|
+
addButton(e, t, r, n, i) {
|
|
1787
|
+
const o = new lt({ id: e, icon: t, title: r, onClick: n, isToggle: i });
|
|
1614
1788
|
this.buttons.set(e, o), this.container.appendChild(o.getElement());
|
|
1615
1789
|
}
|
|
1616
1790
|
/**
|
|
1617
1791
|
* Mount the toolbar container to the map's control container.
|
|
1618
1792
|
*/
|
|
1619
1793
|
mount() {
|
|
1620
|
-
const e = this.options.position || "top-right", t = this.map.getContainer(),
|
|
1794
|
+
const e = this.options.position || "top-right", t = this.map.getContainer(), r = t.querySelector(
|
|
1621
1795
|
`.maplibregl-ctrl-${e}`
|
|
1622
1796
|
);
|
|
1623
|
-
|
|
1797
|
+
r ? r.appendChild(this.container) : t.appendChild(this.container);
|
|
1624
1798
|
}
|
|
1625
1799
|
/**
|
|
1626
1800
|
* Apply CSS styles to the toolbar container.
|
|
@@ -1630,7 +1804,7 @@ class et {
|
|
|
1630
1804
|
e.display = "flex", e.flexDirection = "column", e.gap = "4px", e.padding = "4px", e.backgroundColor = "rgba(255, 255, 255, 0.9)", e.borderRadius = "4px", e.boxShadow = "0 1px 4px rgba(0, 0, 0, 0.3)", e.zIndex = "1", e.pointerEvents = "auto";
|
|
1631
1805
|
}
|
|
1632
1806
|
}
|
|
1633
|
-
class
|
|
1807
|
+
class yt {
|
|
1634
1808
|
/**
|
|
1635
1809
|
* Create a new LibreDraw instance attached to a MapLibre GL JS map.
|
|
1636
1810
|
*
|
|
@@ -1652,55 +1826,59 @@ class tt {
|
|
|
1652
1826
|
* ```
|
|
1653
1827
|
*/
|
|
1654
1828
|
constructor(e, t = {}) {
|
|
1655
|
-
this.toolbar = null, this.destroyed = !1, this.
|
|
1656
|
-
|
|
1657
|
-
|
|
1658
|
-
|
|
1659
|
-
|
|
1829
|
+
this.toolbar = null, this.destroyed = !1, this.inputEnabled = !1, this.handleStyleData = () => {
|
|
1830
|
+
this.destroyed || !this.map.isStyleLoaded() || this.renderManager.isReadyForCurrentStyle() || (this.renderManager.initialize(), this.renderAllFeatures(), this.modeManager.getMode() === "select" ? this.selectMode.refreshVertexHandles() : this.renderManager.clearVertices());
|
|
1831
|
+
}, this.map = e, this.eventBus = new ve(), this.featureStore = new we(), this.historyManager = new Se(t.historyLimit ?? 100), this.modeManager = new be(), this.sourceManager = new nt(e), this.renderManager = new at(
|
|
1832
|
+
e,
|
|
1833
|
+
this.sourceManager,
|
|
1834
|
+
t.style
|
|
1835
|
+
);
|
|
1836
|
+
const r = {
|
|
1837
|
+
store: {
|
|
1838
|
+
add: (o) => this.featureStore.add(o),
|
|
1839
|
+
update: (o, a) => this.featureStore.update(o, a),
|
|
1840
|
+
remove: (o) => this.featureStore.remove(o),
|
|
1841
|
+
getById: (o) => this.featureStore.getById(o),
|
|
1842
|
+
getAll: () => this.featureStore.getAll()
|
|
1660
1843
|
},
|
|
1661
|
-
|
|
1662
|
-
|
|
1663
|
-
|
|
1664
|
-
|
|
1665
|
-
|
|
1666
|
-
|
|
1667
|
-
|
|
1668
|
-
}
|
|
1669
|
-
|
|
1670
|
-
if (this.selectMode = new Oe(
|
|
1671
|
-
{
|
|
1672
|
-
removeFeatureFromStore: (i) => this.featureStore.remove(i),
|
|
1673
|
-
pushToHistory: (i) => {
|
|
1674
|
-
this.historyManager.push(i), this.updateToolbarHistoryState();
|
|
1675
|
-
},
|
|
1676
|
-
emitEvent: (i, n) => this.eventBus.emit(i, n),
|
|
1844
|
+
history: {
|
|
1845
|
+
push: (o) => {
|
|
1846
|
+
this.historyManager.push(o), this.updateToolbarHistoryState();
|
|
1847
|
+
}
|
|
1848
|
+
},
|
|
1849
|
+
events: {
|
|
1850
|
+
emit: (o, a) => this.eventBus.emit(o, a)
|
|
1851
|
+
},
|
|
1852
|
+
render: {
|
|
1677
1853
|
renderFeatures: () => this.renderAllFeatures(),
|
|
1678
|
-
|
|
1679
|
-
|
|
1680
|
-
|
|
1681
|
-
const n = e.project([i.lng, i.lat]);
|
|
1682
|
-
return { x: n.x, y: n.y };
|
|
1683
|
-
},
|
|
1684
|
-
updateFeatureInStore: (i, n) => this.featureStore.update(i, n),
|
|
1685
|
-
renderVertices: (i, n, o, l) => this.renderManager.renderVertices(n, o, l),
|
|
1854
|
+
renderPreview: (o) => this.renderManager.renderPreview(o),
|
|
1855
|
+
clearPreview: () => this.renderManager.clearPreview(),
|
|
1856
|
+
renderVertices: (o, a, h) => this.renderManager.renderVertices(o, a, h),
|
|
1686
1857
|
clearVertices: () => this.renderManager.clearVertices(),
|
|
1687
|
-
|
|
1688
|
-
i ? e.dragPan.enable() : e.dragPan.disable();
|
|
1689
|
-
}
|
|
1858
|
+
setSelectedIds: (o) => this.renderManager.setSelectedIds(o)
|
|
1690
1859
|
},
|
|
1691
|
-
(
|
|
1692
|
-
|
|
1860
|
+
getScreenPoint: (o) => {
|
|
1861
|
+
const a = e.project([o.lng, o.lat]);
|
|
1862
|
+
return { x: a.x, y: a.y };
|
|
1863
|
+
},
|
|
1864
|
+
setDragPan: (o) => {
|
|
1865
|
+
o ? e.dragPan.enable() : e.dragPan.disable();
|
|
1693
1866
|
}
|
|
1694
|
-
|
|
1695
|
-
|
|
1696
|
-
|
|
1867
|
+
}, n = new Fe(r);
|
|
1868
|
+
this.selectMode = new Ze(r), this.modeManager.registerMode("idle", new Ce()), this.modeManager.registerMode("draw", n), this.modeManager.registerMode("select", this.selectMode), this.modeManager.setOnModeChange((o, a) => {
|
|
1869
|
+
this.eventBus.emit("modechange", { mode: o, previousMode: a }), this.toolbar && this.toolbar.setActiveMode(o);
|
|
1870
|
+
const h = this.modeManager.getCurrentMode();
|
|
1871
|
+
h && this.applyMapInteractions(h.mapInteractions());
|
|
1872
|
+
});
|
|
1873
|
+
const i = this.modeManager.getCurrentMode();
|
|
1874
|
+
if (i && this.applyMapInteractions(i.mapInteractions()), this.inputHandler = new it(
|
|
1697
1875
|
e,
|
|
1698
1876
|
() => this.modeManager.getCurrentMode()
|
|
1699
1877
|
), t.toolbar !== !1 && t.toolbar !== void 0) {
|
|
1700
|
-
const
|
|
1701
|
-
this.createToolbar(
|
|
1878
|
+
const o = typeof t.toolbar == "object" ? t.toolbar : {};
|
|
1879
|
+
this.createToolbar(o);
|
|
1702
1880
|
}
|
|
1703
|
-
e.isStyleLoaded() ? this.initialize() : e.once("load", () => {
|
|
1881
|
+
e.on("styledata", this.handleStyleData), e.isStyleLoaded() ? this.initialize() : e.once("load", () => {
|
|
1704
1882
|
this.initialize();
|
|
1705
1883
|
});
|
|
1706
1884
|
}
|
|
@@ -1811,8 +1989,8 @@ class tt {
|
|
|
1811
1989
|
*/
|
|
1812
1990
|
setFeatures(e) {
|
|
1813
1991
|
this.assertNotDestroyed();
|
|
1814
|
-
const t =
|
|
1815
|
-
this.featureStore.setAll(t.features), this.historyManager.clear(), this.renderAllFeatures(), this.updateToolbarHistoryState();
|
|
1992
|
+
const t = Pe(e);
|
|
1993
|
+
this.featureStore.setAll(t.features), this.resetSelectionState(), this.historyManager.clear(), this.renderAllFeatures(), this.updateToolbarHistoryState();
|
|
1816
1994
|
}
|
|
1817
1995
|
/**
|
|
1818
1996
|
* Add features to the store from an array of GeoJSON Feature objects.
|
|
@@ -1840,8 +2018,8 @@ class tt {
|
|
|
1840
2018
|
addFeatures(e) {
|
|
1841
2019
|
this.assertNotDestroyed();
|
|
1842
2020
|
for (const t of e) {
|
|
1843
|
-
const
|
|
1844
|
-
this.featureStore.add(
|
|
2021
|
+
const r = ce(t);
|
|
2022
|
+
this.featureStore.add(r);
|
|
1845
2023
|
}
|
|
1846
2024
|
this.renderAllFeatures();
|
|
1847
2025
|
}
|
|
@@ -1910,8 +2088,8 @@ class tt {
|
|
|
1910
2088
|
const t = this.featureStore.getById(e);
|
|
1911
2089
|
if (!t) return;
|
|
1912
2090
|
this.selectMode.getSelectedIds().includes(e) && this.selectMode.clearSelection(), this.featureStore.remove(e);
|
|
1913
|
-
const
|
|
1914
|
-
return this.historyManager.push(
|
|
2091
|
+
const n = new le(t);
|
|
2092
|
+
return this.historyManager.push(n), this.eventBus.emit("delete", { feature: v(t) }), this.renderAllFeatures(), this.updateToolbarHistoryState(), t;
|
|
1915
2093
|
}
|
|
1916
2094
|
/**
|
|
1917
2095
|
* Programmatically select a feature by its ID.
|
|
@@ -2057,13 +2235,13 @@ class tt {
|
|
|
2057
2235
|
* ```
|
|
2058
2236
|
*/
|
|
2059
2237
|
destroy() {
|
|
2060
|
-
this.destroyed || (this.destroyed = !0, this.modeManager.setMode("idle"), this.inputHandler.destroy(), this.renderManager.destroy(), this.eventBus.removeAllListeners(), this.historyManager.clear(), this.featureStore.clear(), this.toolbar && (this.toolbar.destroy(), this.toolbar = null));
|
|
2238
|
+
this.destroyed || (this.destroyed = !0, this.map.off("styledata", this.handleStyleData), this.modeManager.setMode("idle"), this.inputHandler.destroy(), this.renderManager.destroy(), this.eventBus.removeAllListeners(), this.historyManager.clear(), this.featureStore.clear(), this.toolbar && (this.toolbar.destroy(), this.toolbar = null));
|
|
2061
2239
|
}
|
|
2062
2240
|
/**
|
|
2063
2241
|
* Initialize rendering and input handling after the map is ready.
|
|
2064
2242
|
*/
|
|
2065
2243
|
initialize() {
|
|
2066
|
-
this.destroyed || (this.renderManager.initialize(), this.inputHandler.enable());
|
|
2244
|
+
this.destroyed || (this.renderManager.initialize(), this.inputEnabled || (this.inputHandler.enable(), this.inputEnabled = !0), this.renderAllFeatures());
|
|
2067
2245
|
}
|
|
2068
2246
|
/**
|
|
2069
2247
|
* Render all features from the store to the map.
|
|
@@ -2076,7 +2254,7 @@ class tt {
|
|
|
2076
2254
|
* Create the toolbar UI.
|
|
2077
2255
|
*/
|
|
2078
2256
|
createToolbar(e) {
|
|
2079
|
-
this.toolbar = new
|
|
2257
|
+
this.toolbar = new pt(
|
|
2080
2258
|
this.map,
|
|
2081
2259
|
{
|
|
2082
2260
|
onDrawClick: () => {
|
|
@@ -2092,8 +2270,8 @@ class tt {
|
|
|
2092
2270
|
onDeleteClick: () => {
|
|
2093
2271
|
if (this.modeManager.getMode() === "select") {
|
|
2094
2272
|
const t = this.selectMode.getSelectedIds();
|
|
2095
|
-
for (const
|
|
2096
|
-
this.deleteFeature(
|
|
2273
|
+
for (const r of t)
|
|
2274
|
+
this.deleteFeature(r);
|
|
2097
2275
|
}
|
|
2098
2276
|
},
|
|
2099
2277
|
onUndoClick: () => {
|
|
@@ -2109,6 +2287,12 @@ class tt {
|
|
|
2109
2287
|
this.historyManager.canRedo()
|
|
2110
2288
|
);
|
|
2111
2289
|
}
|
|
2290
|
+
/**
|
|
2291
|
+
* Apply map interaction settings declared by the active mode.
|
|
2292
|
+
*/
|
|
2293
|
+
applyMapInteractions(e) {
|
|
2294
|
+
e.dragPan ? this.map.dragPan.enable() : this.map.dragPan.disable(), e.doubleClickZoom ? this.map.doubleClickZoom.enable() : this.map.doubleClickZoom.disable();
|
|
2295
|
+
}
|
|
2112
2296
|
/**
|
|
2113
2297
|
* Update toolbar undo/redo button states.
|
|
2114
2298
|
*/
|
|
@@ -2118,6 +2302,12 @@ class tt {
|
|
|
2118
2302
|
this.historyManager.canRedo()
|
|
2119
2303
|
);
|
|
2120
2304
|
}
|
|
2305
|
+
/**
|
|
2306
|
+
* Clear selection-related rendering and state.
|
|
2307
|
+
*/
|
|
2308
|
+
resetSelectionState() {
|
|
2309
|
+
this.selectMode.clearSelection(), this.renderManager.setSelectedIds([]), this.renderManager.clearVertices();
|
|
2310
|
+
}
|
|
2121
2311
|
/**
|
|
2122
2312
|
* Assert that this instance has not been destroyed.
|
|
2123
2313
|
* @throws LibreDrawError if destroyed.
|
|
@@ -2130,7 +2320,9 @@ class tt {
|
|
|
2130
2320
|
}
|
|
2131
2321
|
}
|
|
2132
2322
|
export {
|
|
2133
|
-
|
|
2134
|
-
|
|
2323
|
+
N as DEFAULT_STYLE_CONFIG,
|
|
2324
|
+
yt as LibreDraw,
|
|
2325
|
+
E as LibreDrawError,
|
|
2326
|
+
ot as mergeStyleConfig
|
|
2135
2327
|
};
|
|
2136
2328
|
//# sourceMappingURL=libre-draw.js.map
|