@superrouteca/smap 1.2.0 → 1.2.2
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/CHANGELOG.md +13 -0
- package/README.md +2 -2
- package/dist/SOURCE.json +7 -7
- package/dist/smap-client.cjs +2 -2
- package/dist/smap-client.js +2 -2
- package/dist/smap-client.mjs +2 -2
- package/dist/smap.cjs +97 -32
- package/dist/smap.js +96 -31
- package/dist/smap.mjs +97 -32
- package/package.json +1 -1
- package/types/smap.d.cts +1 -1
- package/types/smap.d.mts +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,18 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 1.2.2 — 2026-10-29
|
|
4
|
+
|
|
5
|
+
- Plan editor: opening a distance snapshot sends the plan's points (every job location and vehicle start and end), so
|
|
6
|
+
the legs between them are measured ahead and edits are answered faster. Nothing to change in your code; servers
|
|
7
|
+
that do not read the points work as before.
|
|
8
|
+
|
|
9
|
+
## 1.2.1 — 2026-10-28
|
|
10
|
+
|
|
11
|
+
- Pins: the number and the count badge are drawn into each pin at every zoom, so where pins overlap the upper pin
|
|
12
|
+
covers the lower one with its number and badge, as on Superroute's route map. Before, further out than zoom 13
|
|
13
|
+
numbers and badges were their own layers above every pin. `bakeZoom` (a zoom) keeps the former drawing further out
|
|
14
|
+
than it; `bakeZoom: false` at every zoom.
|
|
15
|
+
|
|
3
16
|
## 1.2.0 — 2026-10-28
|
|
4
17
|
|
|
5
18
|
- Maps without WebGL: where the browser has no WebGL 2 (old computers, remote desktops, graphics acceleration
|
package/README.md
CHANGED
|
@@ -450,8 +450,8 @@ editor.destroy();
|
|
|
450
450
|
fast path may appear or go). `state().path` and the `change` event's `path` say where the last answer came from
|
|
451
451
|
(`'fast'` or `'standard'`); `fastPath: false` keeps every call on the standard path. The snapshot works on both
|
|
452
452
|
paths with the same id.
|
|
453
|
-
- **Distance snapshot**: the editor opens one (`POST /v1/plan/matrix
|
|
454
|
-
once are not measured again. When an answer says the snapshot expired (`X-Plan-Matrix: expired`, or a `410`), it
|
|
453
|
+
- **Distance snapshot**: the editor opens one (`POST /v1/plan/matrix`, with the plan's points so the legs between
|
|
454
|
+
them can be measured ahead) and names it in every call, so legs measured once are not measured again. When an answer says the snapshot expired (`X-Plan-Matrix: expired`, or a `410`), it
|
|
455
455
|
opens a new one and carries on; a snapshot that cannot be opened never stops an edit. `destroy()` closes it.
|
|
456
456
|
- **Calls in flight**: a newer edit cancels the call before it. An edit you can see the outcome of (a move, an order,
|
|
457
457
|
a removal) is drawn at once and priced when the answer arrives; `pending` in the `change` event says it is not
|
package/dist/SOURCE.json
CHANGED
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
{
|
|
2
|
-
"sdkVersion": "1.2.
|
|
2
|
+
"sdkVersion": "1.2.2",
|
|
3
3
|
"engine": "maplibre-gl 6.16.0",
|
|
4
4
|
"files": {
|
|
5
|
-
"smap.js": "
|
|
5
|
+
"smap.js": "b5c9dae63b6999dbc28ec9ae76a828e1cfd061a6c2acb157f631e75786c26367",
|
|
6
6
|
"smap.css": "9bc4b14821de97da199e6af4f18541eeaf53a2ae91e5831e7224f57fe6b77660",
|
|
7
|
-
"smap-client.js": "
|
|
7
|
+
"smap-client.js": "169f1b6efc7241404be51e21e40238b20098b471f7d560809a7a4cfde5116f5a",
|
|
8
8
|
"smap-client.d.ts": "5f0df11bf60c5a9ced34522a284de81260c27871678ab772f16da9ccf6883f58",
|
|
9
|
-
"smap.mjs": "
|
|
10
|
-
"smap.cjs": "
|
|
11
|
-
"smap-client.cjs": "
|
|
12
|
-
"smap-client.mjs": "
|
|
9
|
+
"smap.mjs": "9f2e3dc715d33b647475d6082a39843a5f5acf683d45f2a8373c0e5a361c4092",
|
|
10
|
+
"smap.cjs": "6e51c2b7df527b09a77cc551d4d7c8c06a7f884333d920c7c2009029cea41890",
|
|
11
|
+
"smap-client.cjs": "0328f85f3313d55b3a120b123dea5a1f319fceaa42b3321ff9122c6b15ed31bf",
|
|
12
|
+
"smap-client.mjs": "b649b0ff23677164ccca36122ddc244689d6dfbd8cb69604ce245304c13b06cd",
|
|
13
13
|
"smap-client.d.cts": "e0fe4eb54cd66b831116082f42bd2f7de260f9f12a2741f4004f8cf10c252116",
|
|
14
14
|
"smap-client.d.mts": "96830d316ddb33b4ff8edb8b6f810337479636114f75c4170d95038ffda74103",
|
|
15
15
|
"vendor-licenses.txt": "ee5fc05a0677eaf69601d2c7db0d9ecd6cc27c3abc1d0733bc9ed34707cf8ef2"
|
package/dist/smap-client.cjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/* Generated by js/build.mjs from js/src (see SOURCE.json). Do not edit. */
|
|
2
|
-
/*! sMap JS client 1.2.
|
|
2
|
+
/*! sMap JS client 1.2.2 — tokens, the nearest node, styles, tiles and raw reads, without a map view. */
|
|
3
3
|
/*
|
|
4
4
|
* Runs wherever `fetch` exists: browsers, Node.js 18+, workers; elsewhere (mini programs, older runtimes) pass your
|
|
5
5
|
* own `fetch`. UMD: `window.SMapClient`, `require('smap-client')`, or an AMD module.
|
|
@@ -19,7 +19,7 @@
|
|
|
19
19
|
}(typeof self !== 'undefined' ? self : this, function () {
|
|
20
20
|
'use strict';
|
|
21
21
|
|
|
22
|
-
var VERSION = '1.2.
|
|
22
|
+
var VERSION = '1.2.2';
|
|
23
23
|
var NODE_TTL = 3600 * 1000; // the measured order
|
|
24
24
|
var KNOWN_TTL = 30 * 86400 * 1000; // the last node list received, used when none can be read
|
|
25
25
|
|
package/dist/smap-client.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! sMap JS client 1.2.
|
|
1
|
+
/*! sMap JS client 1.2.2 — tokens, the nearest node, styles, tiles and raw reads, without a map view. */
|
|
2
2
|
/*
|
|
3
3
|
* Runs wherever `fetch` exists: browsers, Node.js 18+, workers; elsewhere (mini programs, older runtimes) pass your
|
|
4
4
|
* own `fetch`. UMD: `window.SMapClient`, `require('smap-client')`, or an AMD module.
|
|
@@ -18,7 +18,7 @@
|
|
|
18
18
|
}(typeof self !== 'undefined' ? self : this, function () {
|
|
19
19
|
'use strict';
|
|
20
20
|
|
|
21
|
-
var VERSION = '1.2.
|
|
21
|
+
var VERSION = '1.2.2';
|
|
22
22
|
var NODE_TTL = 3600 * 1000; // the measured order
|
|
23
23
|
var KNOWN_TTL = 30 * 86400 * 1000; // the last node list received, used when none can be read
|
|
24
24
|
|
package/dist/smap-client.mjs
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/* Generated by js/build.mjs from js/src (see SOURCE.json). Do not edit. */
|
|
2
2
|
var smapClientModule = { exports: {} };
|
|
3
3
|
(function (module, exports, define) {
|
|
4
|
-
/*! sMap JS client 1.2.
|
|
4
|
+
/*! sMap JS client 1.2.2 — tokens, the nearest node, styles, tiles and raw reads, without a map view. */
|
|
5
5
|
/*
|
|
6
6
|
* Runs wherever `fetch` exists: browsers, Node.js 18+, workers; elsewhere (mini programs, older runtimes) pass your
|
|
7
7
|
* own `fetch`. UMD: `window.SMapClient`, `require('smap-client')`, or an AMD module.
|
|
@@ -21,7 +21,7 @@ var smapClientModule = { exports: {} };
|
|
|
21
21
|
}(typeof self !== 'undefined' ? self : this, function () {
|
|
22
22
|
'use strict';
|
|
23
23
|
|
|
24
|
-
var VERSION = '1.2.
|
|
24
|
+
var VERSION = '1.2.2';
|
|
25
25
|
var NODE_TTL = 3600 * 1000; // the measured order
|
|
26
26
|
var KNOWN_TTL = 30 * 86400 * 1000; // the last node list received, used when none can be read
|
|
27
27
|
|
package/dist/smap.cjs
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/* Generated by js/build.mjs from js/src (see SOURCE.json). Do not edit. */
|
|
2
2
|
'use strict';
|
|
3
|
-
/*! sMap Web SDK 1.2.
|
|
3
|
+
/*! sMap Web SDK 1.2.2. Bundles maplibre-gl 6.16.0 (BSD-3-Clause), see vendor-licenses.txt. */
|
|
4
4
|
|
|
5
5
|
var smapCore = null;
|
|
6
6
|
function smapCreateEngine() {
|
|
@@ -28461,7 +28461,7 @@ function smapCreateCanvas() {
|
|
|
28461
28461
|
var exports = module.exports;
|
|
28462
28462
|
var define;
|
|
28463
28463
|
var self = {};
|
|
28464
|
-
// sMap canvas renderer (
|
|
28464
|
+
// sMap canvas renderer (M67): the map drawn on a 2D canvas for browsers without WebGL 2. It answers the part of the
|
|
28465
28465
|
// rendering engine's map interface the Web SDK uses — camera, events, sources, layers of the kinds the SDK makes
|
|
28466
28466
|
// (raster, fill, line, circle, symbol, heatmap), hit tests, controls and popups — so the SDK's calls work unchanged.
|
|
28467
28467
|
// The street map comes as raster tiles. What needs WebGL (3D buildings, terrain, tilting, turning, custom 3D layers,
|
|
@@ -30757,6 +30757,9 @@ function smapCreatePlan() {
|
|
|
30757
30757
|
var body = {};
|
|
30758
30758
|
if (this._context.region) { body.region = this._context.region; }
|
|
30759
30759
|
if (this._context.profile) { body.profile = this._context.profile; }
|
|
30760
|
+
// The plan's points, so the server can measure their legs into the snapshot ahead of the edits (E24).
|
|
30761
|
+
var points = this._points();
|
|
30762
|
+
if (points.length) { body.points = points; }
|
|
30760
30763
|
this._openingKey = key;
|
|
30761
30764
|
var opening = this._transport.send('POST', PATHS.matrix, body).then(function (res) {
|
|
30762
30765
|
var id = res.data && res.data.matrix;
|
|
@@ -30781,6 +30784,27 @@ function smapCreatePlan() {
|
|
|
30781
30784
|
return opening;
|
|
30782
30785
|
};
|
|
30783
30786
|
|
|
30787
|
+
// The plan's points as a snapshot opening sends them: every job location, then every vehicle's start and end, exactly
|
|
30788
|
+
// as the plan holds them (the numbers the plan calls send, since legs are matched exactly), each sent once, first seen
|
|
30789
|
+
// first.
|
|
30790
|
+
PlanEditor.prototype._points = function () {
|
|
30791
|
+
var entry = this._history[this._at];
|
|
30792
|
+
var out = [];
|
|
30793
|
+
var seen = {};
|
|
30794
|
+
function add(v) {
|
|
30795
|
+
var ll = lngLat(v);
|
|
30796
|
+
if (!ll || !isFinite(ll[0]) || !isFinite(ll[1])) { return; }
|
|
30797
|
+
var p = { lat: ll[1], lng: ll[0] };
|
|
30798
|
+
var k = p.lat + ',' + p.lng;
|
|
30799
|
+
if (seen[k]) { return; }
|
|
30800
|
+
seen[k] = true;
|
|
30801
|
+
out.push(p);
|
|
30802
|
+
}
|
|
30803
|
+
((entry && entry.jobs) || []).forEach(function (j) { add(j && j.location); });
|
|
30804
|
+
(this._vehicles || []).forEach(function (v) { if (v) { add(v.start); add(v.end); } });
|
|
30805
|
+
return out;
|
|
30806
|
+
};
|
|
30807
|
+
|
|
30784
30808
|
// ------------------------------------------------------------------ texts (14 languages)
|
|
30785
30809
|
|
|
30786
30810
|
var TEXT_KEYS = ['editor', 'busy', 'undo', 'redo', 'refine', 'total', 'distance', 'drivingTime', 'stops', 'violations',
|
|
@@ -31590,7 +31614,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
31590
31614
|
})(typeof self !== 'undefined' ? self : this, function (engine, interop, canvasLib, plan) {
|
|
31591
31615
|
'use strict';
|
|
31592
31616
|
|
|
31593
|
-
var VERSION = '1.2.
|
|
31617
|
+
var VERSION = '1.2.2';
|
|
31594
31618
|
var FLAVORS = ['light', 'white', 'grayscale', 'dark', 'black'];
|
|
31595
31619
|
var BASEMAP_SOURCE = 'basemap';
|
|
31596
31620
|
var BUILDINGS_LAYER = 'smap-buildings-3d';
|
|
@@ -31815,28 +31839,51 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
31815
31839
|
},
|
|
31816
31840
|
};
|
|
31817
31841
|
},
|
|
31818
|
-
// pinnum|shape|fill|border|borderWidth|size|textColor|text: a pin with its number
|
|
31819
|
-
// pin
|
|
31842
|
+
// pinnum|shape|fill|border|borderWidth|size|textColor|badge|text: a pin with its number and its count badge drawn
|
|
31843
|
+
// in, so a pin above covers a pin below completely, number and badge included, as one element of the route map's
|
|
31844
|
+
// pins does. An empty number or badge is left out; the text comes last because it may hold '|'.
|
|
31820
31845
|
pinnum: function (args, measure) {
|
|
31821
31846
|
var pin = IMAGE_KINDS.pin(args.slice(0, 5));
|
|
31822
|
-
var size = Number(args[4]), color = args[5], text = args.slice(
|
|
31847
|
+
var size = Number(args[4]), color = args[5], badgeText = args[6] || '', text = args.slice(7).join('|');
|
|
31823
31848
|
var px = 14 * size / 32, font = 'bold ' + px + 'px monospace';
|
|
31849
|
+
var badge = badgeText !== '' ? IMAGE_KINDS.badge([badgeText], measure) : null;
|
|
31850
|
+
var g = markerGeometry(args[0], size);
|
|
31851
|
+
// The badge's centre is where its own layer puts it: g.badge from the tip, i.e. from the head's centre for a
|
|
31852
|
+
// pin (the image's centre), so the image is widened on both sides when the badge reaches past it.
|
|
31853
|
+
var w = pin.width, h = pin.height;
|
|
31854
|
+
if (badge) {
|
|
31855
|
+
var reach = Math.abs(g.badge[0]) + badge.width / 2;
|
|
31856
|
+
w = Math.max(w, Math.ceil(2 * reach));
|
|
31857
|
+
}
|
|
31824
31858
|
return {
|
|
31825
|
-
width:
|
|
31859
|
+
width: w, height: h,
|
|
31826
31860
|
draw: function (ctx, ratio) {
|
|
31827
|
-
pin.draw(ctx, ratio);
|
|
31828
|
-
if (text === '') { return; }
|
|
31829
31861
|
ctx.save();
|
|
31830
|
-
ctx.
|
|
31831
|
-
ctx
|
|
31832
|
-
ctx.textBaseline = 'middle';
|
|
31833
|
-
ctx.shadowColor = 'rgba(0,0,0,0.5)';
|
|
31834
|
-
ctx.shadowOffsetX = ratio;
|
|
31835
|
-
ctx.shadowOffsetY = ratio;
|
|
31836
|
-
ctx.shadowBlur = 2 * ratio;
|
|
31837
|
-
ctx.fillStyle = color;
|
|
31838
|
-
ctx.fillText(text, pin.width / 2, pin.height / 2 + 0.5);
|
|
31862
|
+
ctx.translate((w - pin.width) / 2, 0);
|
|
31863
|
+
pin.draw(ctx, ratio);
|
|
31839
31864
|
ctx.restore();
|
|
31865
|
+
if (text !== '') {
|
|
31866
|
+
ctx.save();
|
|
31867
|
+
ctx.font = font;
|
|
31868
|
+
ctx.textAlign = 'center';
|
|
31869
|
+
ctx.textBaseline = 'middle';
|
|
31870
|
+
ctx.shadowColor = 'rgba(0,0,0,0.5)';
|
|
31871
|
+
ctx.shadowOffsetX = ratio;
|
|
31872
|
+
ctx.shadowOffsetY = ratio;
|
|
31873
|
+
ctx.shadowBlur = 2 * ratio;
|
|
31874
|
+
ctx.fillStyle = color;
|
|
31875
|
+
ctx.fillText(text, w / 2, h / 2 + 0.5);
|
|
31876
|
+
ctx.restore();
|
|
31877
|
+
}
|
|
31878
|
+
if (badge) {
|
|
31879
|
+
// A pin's head is the image's centre and its tip half the image height lower; the badge sits g.badge from
|
|
31880
|
+
// the tip (a circle's centre is the image's centre).
|
|
31881
|
+
var tipY = args[0] === 'pin' ? h / 2 + g.tipToHead : h / 2;
|
|
31882
|
+
ctx.save();
|
|
31883
|
+
ctx.translate(w / 2 + g.badge[0] - badge.width / 2, tipY + g.badge[1] - badge.height / 2);
|
|
31884
|
+
badge.draw(ctx, ratio);
|
|
31885
|
+
ctx.restore();
|
|
31886
|
+
}
|
|
31840
31887
|
},
|
|
31841
31888
|
};
|
|
31842
31889
|
},
|
|
@@ -32002,7 +32049,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
32002
32049
|
* minWidth, offset, anchor, closeButton, closeOnClick, focusAfterOpen)
|
|
32003
32050
|
* @param {string|Node} [options.popupLoading] shown while a popup's content is a pending promise (default: dots)
|
|
32004
32051
|
* @param {'auto'|'webgl'|'canvas'} [options.renderer] 'auto' (default): the WebGL map, or the canvas map (raster
|
|
32005
|
-
* tiles, layers drawn in 2D) where the browser has no WebGL 2 (
|
|
32052
|
+
* tiles, layers drawn in 2D) where the browser has no WebGL 2 (M67)
|
|
32006
32053
|
* Every other option (center, zoom, pitch, bearing, minZoom, maxZoom, maxBounds, hash, …) goes to the engine.
|
|
32007
32054
|
*/
|
|
32008
32055
|
function SMap(options) {
|
|
@@ -32058,7 +32105,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
32058
32105
|
this._toolHandlers = [];
|
|
32059
32106
|
|
|
32060
32107
|
var self = this;
|
|
32061
|
-
// The renderer (
|
|
32108
|
+
// The renderer (M67): the WebGL engine, or the canvas map where there is no WebGL 2 (or when asked for).
|
|
32062
32109
|
var want = options.renderer || 'auto';
|
|
32063
32110
|
// Asked of the page itself; without a page (a server, a test) the WebGL engine is kept.
|
|
32064
32111
|
var hasPage = typeof document !== 'undefined' && !!document && typeof document.createElement === 'function';
|
|
@@ -34405,7 +34452,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
34405
34452
|
*/
|
|
34406
34453
|
SMap.prototype.setBaseImagery = function (imagery) {
|
|
34407
34454
|
if (imagery && (!Array.isArray(imagery.tiles) || !imagery.tiles.length)) { throw new Error('sMap: base imagery needs tiles'); }
|
|
34408
|
-
// Google's and Bing's tiles only through their own terms: Google's with setGoogleBase (M31,
|
|
34455
|
+
// Google's and Bing's tiles only through their own terms: Google's with setGoogleBase (M31, M72).
|
|
34409
34456
|
if (imagery) { interop.refuseForbidden(imagery.tiles); }
|
|
34410
34457
|
return this._setBaseImagery(imagery);
|
|
34411
34458
|
};
|
|
@@ -35446,13 +35493,31 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35446
35493
|
// Opacity of the pin, its number and its badge together (the route map draws settled stops at .72).
|
|
35447
35494
|
var markerPaint = mk.opacity !== undefined ? { 'icon-opacity': valueExpr(mk.opacity, 1) } : undefined;
|
|
35448
35495
|
main = src + '-points';
|
|
35449
|
-
//
|
|
35450
|
-
//
|
|
35451
|
-
// pins
|
|
35496
|
+
// A pin's number and count badge are drawn into its own image (as one element of the route map's pins), so an
|
|
35497
|
+
// upper pin covers a lower one completely, number and badge included. bakeZoom (a zoom) keeps them their own
|
|
35498
|
+
// layers above the pins further out than it — fewer images where thousands of pins are in view, but numbers
|
|
35499
|
+
// over every pin there — and bakeZoom: false keeps them apart at every zoom. textMinzoom / badgeMinzoom start
|
|
35500
|
+
// them at their zoom either way.
|
|
35452
35501
|
var plainPin = drawnImageId('pin', [shape, str(mk.fill, '#ffffff'), str(mk.border, color), String(bw), String(size)]);
|
|
35453
|
-
var
|
|
35454
|
-
var
|
|
35455
|
-
|
|
35502
|
+
var hasText = mk.text !== undefined, hasBadge = mk.badge !== undefined;
|
|
35503
|
+
var bakeZoom = (hasText || hasBadge) && mk.bakeZoom !== false ? (typeof mk.bakeZoom === 'number' ? mk.bakeZoom : 0) : null;
|
|
35504
|
+
var badgeNumber = ['to-number', valueExpr(mk.badge, 0), 0];
|
|
35505
|
+
var textMin = typeof mk.textMinzoom === 'number' ? mk.textMinzoom : 0;
|
|
35506
|
+
var badgeMin = typeof mk.badgeMinzoom === 'number' ? mk.badgeMinzoom : 0;
|
|
35507
|
+
var imageAt = function (z) {
|
|
35508
|
+
if (bakeZoom === null || z < bakeZoom) { return plainPin; }
|
|
35509
|
+
var withText = hasText && z >= textMin, withBadge = hasBadge && z >= badgeMin;
|
|
35510
|
+
if (!withText && !withBadge) { return plainPin; }
|
|
35511
|
+
return drawnImageId('pinnum', [shape, str(mk.fill, '#ffffff'), str(mk.border, color), String(bw), String(size), str(mk.textColor, '#ffffff'),
|
|
35512
|
+
withBadge ? ['case', ['>', badgeNumber, 1], ['to-string', badgeNumber], ''] : '', withText ? str(mk.text, '') : '']);
|
|
35513
|
+
};
|
|
35514
|
+
var breaks = [bakeZoom, textMin, badgeMin].filter(function (z, i, all) { return typeof z === 'number' && z > 0 && all.indexOf(z) === i; })
|
|
35515
|
+
.sort(function (x, y) { return x - y; });
|
|
35516
|
+
var pinImage = imageAt(0);
|
|
35517
|
+
if (breaks.length) {
|
|
35518
|
+
pinImage = ['step', ['zoom'], imageAt(0)];
|
|
35519
|
+
breaks.forEach(function (z) { pinImage.push(z, imageAt(z)); });
|
|
35520
|
+
}
|
|
35456
35521
|
var markerSpecs = [];
|
|
35457
35522
|
var addMarker = function (layer) { markerSpecs.push(JSON.parse(JSON.stringify(layer))); add(layer); };
|
|
35458
35523
|
addMarker({
|
|
@@ -35465,7 +35530,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35465
35530
|
'icon-allow-overlap': true, 'icon-ignore-placement': true,
|
|
35466
35531
|
},
|
|
35467
35532
|
});
|
|
35468
|
-
if (
|
|
35533
|
+
if (hasText && bakeZoom !== 0) {
|
|
35469
35534
|
var text = str(mk.text, '');
|
|
35470
35535
|
addMarker({
|
|
35471
35536
|
id: src + '-numbers', type: 'symbol', filter: both(['!=', text, '']), minzoom: mk.textMinzoom, maxzoom: bakeZoom === null ? undefined : bakeZoom, paint: markerPaint,
|
|
@@ -35475,10 +35540,10 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35475
35540
|
},
|
|
35476
35541
|
});
|
|
35477
35542
|
}
|
|
35478
|
-
if (
|
|
35479
|
-
var badge =
|
|
35543
|
+
if (hasBadge && bakeZoom !== 0) {
|
|
35544
|
+
var badge = badgeNumber;
|
|
35480
35545
|
addMarker({
|
|
35481
|
-
id: src + '-badges', type: 'symbol', filter: both(['>', badge, 1]), minzoom: mk.badgeMinzoom, paint: markerPaint,
|
|
35546
|
+
id: src + '-badges', type: 'symbol', filter: both(['>', badge, 1]), minzoom: mk.badgeMinzoom, maxzoom: bakeZoom === null ? undefined : bakeZoom, paint: markerPaint,
|
|
35482
35547
|
layout: {
|
|
35483
35548
|
'icon-image': drawnImageId('badge', [['to-string', badge]]),
|
|
35484
35549
|
'icon-offset': g.badge, 'icon-size': scale,
|
|
@@ -35732,7 +35797,7 @@ function SMapMap(options) {
|
|
|
35732
35797
|
SMapMap.prototype = core.Map.prototype;
|
|
35733
35798
|
return new core.Map(options);
|
|
35734
35799
|
}
|
|
35735
|
-
var smapVersion = "1.2.
|
|
35800
|
+
var smapVersion = "1.2.2";
|
|
35736
35801
|
var smapStyles = ['light', 'white', 'grayscale', 'dark', 'black'];
|
|
35737
35802
|
/** The bundled rendering engine, for anything the SDK does not wrap (loaded on the first call). */
|
|
35738
35803
|
function smapGetEngine() { return smapLoad().engine; }
|
package/dist/smap.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! sMap Web SDK 1.2.
|
|
1
|
+
/*! sMap Web SDK 1.2.2. Bundles maplibre-gl 6.16.0 (BSD-3-Clause), see vendor-licenses.txt. */
|
|
2
2
|
(function () {
|
|
3
3
|
function smapCreateEngine() {
|
|
4
4
|
var SMAP_BASE_URL = (typeof document !== 'undefined' && document.baseURI) || (typeof location !== 'undefined' && location.href) || 'about:blank';
|
|
@@ -28458,7 +28458,7 @@ function smapCreateCanvas() {
|
|
|
28458
28458
|
var exports = module.exports;
|
|
28459
28459
|
var define;
|
|
28460
28460
|
var self = {};
|
|
28461
|
-
// sMap canvas renderer (
|
|
28461
|
+
// sMap canvas renderer (M67): the map drawn on a 2D canvas for browsers without WebGL 2. It answers the part of the
|
|
28462
28462
|
// rendering engine's map interface the Web SDK uses — camera, events, sources, layers of the kinds the SDK makes
|
|
28463
28463
|
// (raster, fill, line, circle, symbol, heatmap), hit tests, controls and popups — so the SDK's calls work unchanged.
|
|
28464
28464
|
// The street map comes as raster tiles. What needs WebGL (3D buildings, terrain, tilting, turning, custom 3D layers,
|
|
@@ -30754,6 +30754,9 @@ function smapCreatePlan() {
|
|
|
30754
30754
|
var body = {};
|
|
30755
30755
|
if (this._context.region) { body.region = this._context.region; }
|
|
30756
30756
|
if (this._context.profile) { body.profile = this._context.profile; }
|
|
30757
|
+
// The plan's points, so the server can measure their legs into the snapshot ahead of the edits (E24).
|
|
30758
|
+
var points = this._points();
|
|
30759
|
+
if (points.length) { body.points = points; }
|
|
30757
30760
|
this._openingKey = key;
|
|
30758
30761
|
var opening = this._transport.send('POST', PATHS.matrix, body).then(function (res) {
|
|
30759
30762
|
var id = res.data && res.data.matrix;
|
|
@@ -30778,6 +30781,27 @@ function smapCreatePlan() {
|
|
|
30778
30781
|
return opening;
|
|
30779
30782
|
};
|
|
30780
30783
|
|
|
30784
|
+
// The plan's points as a snapshot opening sends them: every job location, then every vehicle's start and end, exactly
|
|
30785
|
+
// as the plan holds them (the numbers the plan calls send, since legs are matched exactly), each sent once, first seen
|
|
30786
|
+
// first.
|
|
30787
|
+
PlanEditor.prototype._points = function () {
|
|
30788
|
+
var entry = this._history[this._at];
|
|
30789
|
+
var out = [];
|
|
30790
|
+
var seen = {};
|
|
30791
|
+
function add(v) {
|
|
30792
|
+
var ll = lngLat(v);
|
|
30793
|
+
if (!ll || !isFinite(ll[0]) || !isFinite(ll[1])) { return; }
|
|
30794
|
+
var p = { lat: ll[1], lng: ll[0] };
|
|
30795
|
+
var k = p.lat + ',' + p.lng;
|
|
30796
|
+
if (seen[k]) { return; }
|
|
30797
|
+
seen[k] = true;
|
|
30798
|
+
out.push(p);
|
|
30799
|
+
}
|
|
30800
|
+
((entry && entry.jobs) || []).forEach(function (j) { add(j && j.location); });
|
|
30801
|
+
(this._vehicles || []).forEach(function (v) { if (v) { add(v.start); add(v.end); } });
|
|
30802
|
+
return out;
|
|
30803
|
+
};
|
|
30804
|
+
|
|
30781
30805
|
// ------------------------------------------------------------------ texts (14 languages)
|
|
30782
30806
|
|
|
30783
30807
|
var TEXT_KEYS = ['editor', 'busy', 'undo', 'redo', 'refine', 'total', 'distance', 'drivingTime', 'stops', 'violations',
|
|
@@ -31587,7 +31611,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
31587
31611
|
})(typeof self !== 'undefined' ? self : this, function (engine, interop, canvasLib, plan) {
|
|
31588
31612
|
'use strict';
|
|
31589
31613
|
|
|
31590
|
-
var VERSION = '1.2.
|
|
31614
|
+
var VERSION = '1.2.2';
|
|
31591
31615
|
var FLAVORS = ['light', 'white', 'grayscale', 'dark', 'black'];
|
|
31592
31616
|
var BASEMAP_SOURCE = 'basemap';
|
|
31593
31617
|
var BUILDINGS_LAYER = 'smap-buildings-3d';
|
|
@@ -31812,28 +31836,51 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
31812
31836
|
},
|
|
31813
31837
|
};
|
|
31814
31838
|
},
|
|
31815
|
-
// pinnum|shape|fill|border|borderWidth|size|textColor|text: a pin with its number
|
|
31816
|
-
// pin
|
|
31839
|
+
// pinnum|shape|fill|border|borderWidth|size|textColor|badge|text: a pin with its number and its count badge drawn
|
|
31840
|
+
// in, so a pin above covers a pin below completely, number and badge included, as one element of the route map's
|
|
31841
|
+
// pins does. An empty number or badge is left out; the text comes last because it may hold '|'.
|
|
31817
31842
|
pinnum: function (args, measure) {
|
|
31818
31843
|
var pin = IMAGE_KINDS.pin(args.slice(0, 5));
|
|
31819
|
-
var size = Number(args[4]), color = args[5], text = args.slice(
|
|
31844
|
+
var size = Number(args[4]), color = args[5], badgeText = args[6] || '', text = args.slice(7).join('|');
|
|
31820
31845
|
var px = 14 * size / 32, font = 'bold ' + px + 'px monospace';
|
|
31846
|
+
var badge = badgeText !== '' ? IMAGE_KINDS.badge([badgeText], measure) : null;
|
|
31847
|
+
var g = markerGeometry(args[0], size);
|
|
31848
|
+
// The badge's centre is where its own layer puts it: g.badge from the tip, i.e. from the head's centre for a
|
|
31849
|
+
// pin (the image's centre), so the image is widened on both sides when the badge reaches past it.
|
|
31850
|
+
var w = pin.width, h = pin.height;
|
|
31851
|
+
if (badge) {
|
|
31852
|
+
var reach = Math.abs(g.badge[0]) + badge.width / 2;
|
|
31853
|
+
w = Math.max(w, Math.ceil(2 * reach));
|
|
31854
|
+
}
|
|
31821
31855
|
return {
|
|
31822
|
-
width:
|
|
31856
|
+
width: w, height: h,
|
|
31823
31857
|
draw: function (ctx, ratio) {
|
|
31824
|
-
pin.draw(ctx, ratio);
|
|
31825
|
-
if (text === '') { return; }
|
|
31826
31858
|
ctx.save();
|
|
31827
|
-
ctx.
|
|
31828
|
-
ctx
|
|
31829
|
-
ctx.textBaseline = 'middle';
|
|
31830
|
-
ctx.shadowColor = 'rgba(0,0,0,0.5)';
|
|
31831
|
-
ctx.shadowOffsetX = ratio;
|
|
31832
|
-
ctx.shadowOffsetY = ratio;
|
|
31833
|
-
ctx.shadowBlur = 2 * ratio;
|
|
31834
|
-
ctx.fillStyle = color;
|
|
31835
|
-
ctx.fillText(text, pin.width / 2, pin.height / 2 + 0.5);
|
|
31859
|
+
ctx.translate((w - pin.width) / 2, 0);
|
|
31860
|
+
pin.draw(ctx, ratio);
|
|
31836
31861
|
ctx.restore();
|
|
31862
|
+
if (text !== '') {
|
|
31863
|
+
ctx.save();
|
|
31864
|
+
ctx.font = font;
|
|
31865
|
+
ctx.textAlign = 'center';
|
|
31866
|
+
ctx.textBaseline = 'middle';
|
|
31867
|
+
ctx.shadowColor = 'rgba(0,0,0,0.5)';
|
|
31868
|
+
ctx.shadowOffsetX = ratio;
|
|
31869
|
+
ctx.shadowOffsetY = ratio;
|
|
31870
|
+
ctx.shadowBlur = 2 * ratio;
|
|
31871
|
+
ctx.fillStyle = color;
|
|
31872
|
+
ctx.fillText(text, w / 2, h / 2 + 0.5);
|
|
31873
|
+
ctx.restore();
|
|
31874
|
+
}
|
|
31875
|
+
if (badge) {
|
|
31876
|
+
// A pin's head is the image's centre and its tip half the image height lower; the badge sits g.badge from
|
|
31877
|
+
// the tip (a circle's centre is the image's centre).
|
|
31878
|
+
var tipY = args[0] === 'pin' ? h / 2 + g.tipToHead : h / 2;
|
|
31879
|
+
ctx.save();
|
|
31880
|
+
ctx.translate(w / 2 + g.badge[0] - badge.width / 2, tipY + g.badge[1] - badge.height / 2);
|
|
31881
|
+
badge.draw(ctx, ratio);
|
|
31882
|
+
ctx.restore();
|
|
31883
|
+
}
|
|
31837
31884
|
},
|
|
31838
31885
|
};
|
|
31839
31886
|
},
|
|
@@ -31999,7 +32046,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
31999
32046
|
* minWidth, offset, anchor, closeButton, closeOnClick, focusAfterOpen)
|
|
32000
32047
|
* @param {string|Node} [options.popupLoading] shown while a popup's content is a pending promise (default: dots)
|
|
32001
32048
|
* @param {'auto'|'webgl'|'canvas'} [options.renderer] 'auto' (default): the WebGL map, or the canvas map (raster
|
|
32002
|
-
* tiles, layers drawn in 2D) where the browser has no WebGL 2 (
|
|
32049
|
+
* tiles, layers drawn in 2D) where the browser has no WebGL 2 (M67)
|
|
32003
32050
|
* Every other option (center, zoom, pitch, bearing, minZoom, maxZoom, maxBounds, hash, …) goes to the engine.
|
|
32004
32051
|
*/
|
|
32005
32052
|
function SMap(options) {
|
|
@@ -32055,7 +32102,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
32055
32102
|
this._toolHandlers = [];
|
|
32056
32103
|
|
|
32057
32104
|
var self = this;
|
|
32058
|
-
// The renderer (
|
|
32105
|
+
// The renderer (M67): the WebGL engine, or the canvas map where there is no WebGL 2 (or when asked for).
|
|
32059
32106
|
var want = options.renderer || 'auto';
|
|
32060
32107
|
// Asked of the page itself; without a page (a server, a test) the WebGL engine is kept.
|
|
32061
32108
|
var hasPage = typeof document !== 'undefined' && !!document && typeof document.createElement === 'function';
|
|
@@ -34402,7 +34449,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
34402
34449
|
*/
|
|
34403
34450
|
SMap.prototype.setBaseImagery = function (imagery) {
|
|
34404
34451
|
if (imagery && (!Array.isArray(imagery.tiles) || !imagery.tiles.length)) { throw new Error('sMap: base imagery needs tiles'); }
|
|
34405
|
-
// Google's and Bing's tiles only through their own terms: Google's with setGoogleBase (M31,
|
|
34452
|
+
// Google's and Bing's tiles only through their own terms: Google's with setGoogleBase (M31, M72).
|
|
34406
34453
|
if (imagery) { interop.refuseForbidden(imagery.tiles); }
|
|
34407
34454
|
return this._setBaseImagery(imagery);
|
|
34408
34455
|
};
|
|
@@ -35443,13 +35490,31 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35443
35490
|
// Opacity of the pin, its number and its badge together (the route map draws settled stops at .72).
|
|
35444
35491
|
var markerPaint = mk.opacity !== undefined ? { 'icon-opacity': valueExpr(mk.opacity, 1) } : undefined;
|
|
35445
35492
|
main = src + '-points';
|
|
35446
|
-
//
|
|
35447
|
-
//
|
|
35448
|
-
// pins
|
|
35493
|
+
// A pin's number and count badge are drawn into its own image (as one element of the route map's pins), so an
|
|
35494
|
+
// upper pin covers a lower one completely, number and badge included. bakeZoom (a zoom) keeps them their own
|
|
35495
|
+
// layers above the pins further out than it — fewer images where thousands of pins are in view, but numbers
|
|
35496
|
+
// over every pin there — and bakeZoom: false keeps them apart at every zoom. textMinzoom / badgeMinzoom start
|
|
35497
|
+
// them at their zoom either way.
|
|
35449
35498
|
var plainPin = drawnImageId('pin', [shape, str(mk.fill, '#ffffff'), str(mk.border, color), String(bw), String(size)]);
|
|
35450
|
-
var
|
|
35451
|
-
var
|
|
35452
|
-
|
|
35499
|
+
var hasText = mk.text !== undefined, hasBadge = mk.badge !== undefined;
|
|
35500
|
+
var bakeZoom = (hasText || hasBadge) && mk.bakeZoom !== false ? (typeof mk.bakeZoom === 'number' ? mk.bakeZoom : 0) : null;
|
|
35501
|
+
var badgeNumber = ['to-number', valueExpr(mk.badge, 0), 0];
|
|
35502
|
+
var textMin = typeof mk.textMinzoom === 'number' ? mk.textMinzoom : 0;
|
|
35503
|
+
var badgeMin = typeof mk.badgeMinzoom === 'number' ? mk.badgeMinzoom : 0;
|
|
35504
|
+
var imageAt = function (z) {
|
|
35505
|
+
if (bakeZoom === null || z < bakeZoom) { return plainPin; }
|
|
35506
|
+
var withText = hasText && z >= textMin, withBadge = hasBadge && z >= badgeMin;
|
|
35507
|
+
if (!withText && !withBadge) { return plainPin; }
|
|
35508
|
+
return drawnImageId('pinnum', [shape, str(mk.fill, '#ffffff'), str(mk.border, color), String(bw), String(size), str(mk.textColor, '#ffffff'),
|
|
35509
|
+
withBadge ? ['case', ['>', badgeNumber, 1], ['to-string', badgeNumber], ''] : '', withText ? str(mk.text, '') : '']);
|
|
35510
|
+
};
|
|
35511
|
+
var breaks = [bakeZoom, textMin, badgeMin].filter(function (z, i, all) { return typeof z === 'number' && z > 0 && all.indexOf(z) === i; })
|
|
35512
|
+
.sort(function (x, y) { return x - y; });
|
|
35513
|
+
var pinImage = imageAt(0);
|
|
35514
|
+
if (breaks.length) {
|
|
35515
|
+
pinImage = ['step', ['zoom'], imageAt(0)];
|
|
35516
|
+
breaks.forEach(function (z) { pinImage.push(z, imageAt(z)); });
|
|
35517
|
+
}
|
|
35453
35518
|
var markerSpecs = [];
|
|
35454
35519
|
var addMarker = function (layer) { markerSpecs.push(JSON.parse(JSON.stringify(layer))); add(layer); };
|
|
35455
35520
|
addMarker({
|
|
@@ -35462,7 +35527,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35462
35527
|
'icon-allow-overlap': true, 'icon-ignore-placement': true,
|
|
35463
35528
|
},
|
|
35464
35529
|
});
|
|
35465
|
-
if (
|
|
35530
|
+
if (hasText && bakeZoom !== 0) {
|
|
35466
35531
|
var text = str(mk.text, '');
|
|
35467
35532
|
addMarker({
|
|
35468
35533
|
id: src + '-numbers', type: 'symbol', filter: both(['!=', text, '']), minzoom: mk.textMinzoom, maxzoom: bakeZoom === null ? undefined : bakeZoom, paint: markerPaint,
|
|
@@ -35472,10 +35537,10 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35472
35537
|
},
|
|
35473
35538
|
});
|
|
35474
35539
|
}
|
|
35475
|
-
if (
|
|
35476
|
-
var badge =
|
|
35540
|
+
if (hasBadge && bakeZoom !== 0) {
|
|
35541
|
+
var badge = badgeNumber;
|
|
35477
35542
|
addMarker({
|
|
35478
|
-
id: src + '-badges', type: 'symbol', filter: both(['>', badge, 1]), minzoom: mk.badgeMinzoom, paint: markerPaint,
|
|
35543
|
+
id: src + '-badges', type: 'symbol', filter: both(['>', badge, 1]), minzoom: mk.badgeMinzoom, maxzoom: bakeZoom === null ? undefined : bakeZoom, paint: markerPaint,
|
|
35479
35544
|
layout: {
|
|
35480
35545
|
'icon-image': drawnImageId('badge', [['to-string', badge]]),
|
|
35481
35546
|
'icon-offset': g.badge, 'icon-size': scale,
|
package/dist/smap.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/* Generated by js/build.mjs from js/src (see SOURCE.json). Do not edit. */
|
|
2
|
-
/*! sMap Web SDK 1.2.
|
|
2
|
+
/*! sMap Web SDK 1.2.2. Bundles maplibre-gl 6.16.0 (BSD-3-Clause), see vendor-licenses.txt. */
|
|
3
3
|
|
|
4
4
|
var smapCore = null;
|
|
5
5
|
function smapCreateEngine() {
|
|
@@ -28460,7 +28460,7 @@ function smapCreateCanvas() {
|
|
|
28460
28460
|
var exports = module.exports;
|
|
28461
28461
|
var define;
|
|
28462
28462
|
var self = {};
|
|
28463
|
-
// sMap canvas renderer (
|
|
28463
|
+
// sMap canvas renderer (M67): the map drawn on a 2D canvas for browsers without WebGL 2. It answers the part of the
|
|
28464
28464
|
// rendering engine's map interface the Web SDK uses — camera, events, sources, layers of the kinds the SDK makes
|
|
28465
28465
|
// (raster, fill, line, circle, symbol, heatmap), hit tests, controls and popups — so the SDK's calls work unchanged.
|
|
28466
28466
|
// The street map comes as raster tiles. What needs WebGL (3D buildings, terrain, tilting, turning, custom 3D layers,
|
|
@@ -30756,6 +30756,9 @@ function smapCreatePlan() {
|
|
|
30756
30756
|
var body = {};
|
|
30757
30757
|
if (this._context.region) { body.region = this._context.region; }
|
|
30758
30758
|
if (this._context.profile) { body.profile = this._context.profile; }
|
|
30759
|
+
// The plan's points, so the server can measure their legs into the snapshot ahead of the edits (E24).
|
|
30760
|
+
var points = this._points();
|
|
30761
|
+
if (points.length) { body.points = points; }
|
|
30759
30762
|
this._openingKey = key;
|
|
30760
30763
|
var opening = this._transport.send('POST', PATHS.matrix, body).then(function (res) {
|
|
30761
30764
|
var id = res.data && res.data.matrix;
|
|
@@ -30780,6 +30783,27 @@ function smapCreatePlan() {
|
|
|
30780
30783
|
return opening;
|
|
30781
30784
|
};
|
|
30782
30785
|
|
|
30786
|
+
// The plan's points as a snapshot opening sends them: every job location, then every vehicle's start and end, exactly
|
|
30787
|
+
// as the plan holds them (the numbers the plan calls send, since legs are matched exactly), each sent once, first seen
|
|
30788
|
+
// first.
|
|
30789
|
+
PlanEditor.prototype._points = function () {
|
|
30790
|
+
var entry = this._history[this._at];
|
|
30791
|
+
var out = [];
|
|
30792
|
+
var seen = {};
|
|
30793
|
+
function add(v) {
|
|
30794
|
+
var ll = lngLat(v);
|
|
30795
|
+
if (!ll || !isFinite(ll[0]) || !isFinite(ll[1])) { return; }
|
|
30796
|
+
var p = { lat: ll[1], lng: ll[0] };
|
|
30797
|
+
var k = p.lat + ',' + p.lng;
|
|
30798
|
+
if (seen[k]) { return; }
|
|
30799
|
+
seen[k] = true;
|
|
30800
|
+
out.push(p);
|
|
30801
|
+
}
|
|
30802
|
+
((entry && entry.jobs) || []).forEach(function (j) { add(j && j.location); });
|
|
30803
|
+
(this._vehicles || []).forEach(function (v) { if (v) { add(v.start); add(v.end); } });
|
|
30804
|
+
return out;
|
|
30805
|
+
};
|
|
30806
|
+
|
|
30783
30807
|
// ------------------------------------------------------------------ texts (14 languages)
|
|
30784
30808
|
|
|
30785
30809
|
var TEXT_KEYS = ['editor', 'busy', 'undo', 'redo', 'refine', 'total', 'distance', 'drivingTime', 'stops', 'violations',
|
|
@@ -31589,7 +31613,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
31589
31613
|
})(typeof self !== 'undefined' ? self : this, function (engine, interop, canvasLib, plan) {
|
|
31590
31614
|
'use strict';
|
|
31591
31615
|
|
|
31592
|
-
var VERSION = '1.2.
|
|
31616
|
+
var VERSION = '1.2.2';
|
|
31593
31617
|
var FLAVORS = ['light', 'white', 'grayscale', 'dark', 'black'];
|
|
31594
31618
|
var BASEMAP_SOURCE = 'basemap';
|
|
31595
31619
|
var BUILDINGS_LAYER = 'smap-buildings-3d';
|
|
@@ -31814,28 +31838,51 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
31814
31838
|
},
|
|
31815
31839
|
};
|
|
31816
31840
|
},
|
|
31817
|
-
// pinnum|shape|fill|border|borderWidth|size|textColor|text: a pin with its number
|
|
31818
|
-
// pin
|
|
31841
|
+
// pinnum|shape|fill|border|borderWidth|size|textColor|badge|text: a pin with its number and its count badge drawn
|
|
31842
|
+
// in, so a pin above covers a pin below completely, number and badge included, as one element of the route map's
|
|
31843
|
+
// pins does. An empty number or badge is left out; the text comes last because it may hold '|'.
|
|
31819
31844
|
pinnum: function (args, measure) {
|
|
31820
31845
|
var pin = IMAGE_KINDS.pin(args.slice(0, 5));
|
|
31821
|
-
var size = Number(args[4]), color = args[5], text = args.slice(
|
|
31846
|
+
var size = Number(args[4]), color = args[5], badgeText = args[6] || '', text = args.slice(7).join('|');
|
|
31822
31847
|
var px = 14 * size / 32, font = 'bold ' + px + 'px monospace';
|
|
31848
|
+
var badge = badgeText !== '' ? IMAGE_KINDS.badge([badgeText], measure) : null;
|
|
31849
|
+
var g = markerGeometry(args[0], size);
|
|
31850
|
+
// The badge's centre is where its own layer puts it: g.badge from the tip, i.e. from the head's centre for a
|
|
31851
|
+
// pin (the image's centre), so the image is widened on both sides when the badge reaches past it.
|
|
31852
|
+
var w = pin.width, h = pin.height;
|
|
31853
|
+
if (badge) {
|
|
31854
|
+
var reach = Math.abs(g.badge[0]) + badge.width / 2;
|
|
31855
|
+
w = Math.max(w, Math.ceil(2 * reach));
|
|
31856
|
+
}
|
|
31823
31857
|
return {
|
|
31824
|
-
width:
|
|
31858
|
+
width: w, height: h,
|
|
31825
31859
|
draw: function (ctx, ratio) {
|
|
31826
|
-
pin.draw(ctx, ratio);
|
|
31827
|
-
if (text === '') { return; }
|
|
31828
31860
|
ctx.save();
|
|
31829
|
-
ctx.
|
|
31830
|
-
ctx
|
|
31831
|
-
ctx.textBaseline = 'middle';
|
|
31832
|
-
ctx.shadowColor = 'rgba(0,0,0,0.5)';
|
|
31833
|
-
ctx.shadowOffsetX = ratio;
|
|
31834
|
-
ctx.shadowOffsetY = ratio;
|
|
31835
|
-
ctx.shadowBlur = 2 * ratio;
|
|
31836
|
-
ctx.fillStyle = color;
|
|
31837
|
-
ctx.fillText(text, pin.width / 2, pin.height / 2 + 0.5);
|
|
31861
|
+
ctx.translate((w - pin.width) / 2, 0);
|
|
31862
|
+
pin.draw(ctx, ratio);
|
|
31838
31863
|
ctx.restore();
|
|
31864
|
+
if (text !== '') {
|
|
31865
|
+
ctx.save();
|
|
31866
|
+
ctx.font = font;
|
|
31867
|
+
ctx.textAlign = 'center';
|
|
31868
|
+
ctx.textBaseline = 'middle';
|
|
31869
|
+
ctx.shadowColor = 'rgba(0,0,0,0.5)';
|
|
31870
|
+
ctx.shadowOffsetX = ratio;
|
|
31871
|
+
ctx.shadowOffsetY = ratio;
|
|
31872
|
+
ctx.shadowBlur = 2 * ratio;
|
|
31873
|
+
ctx.fillStyle = color;
|
|
31874
|
+
ctx.fillText(text, w / 2, h / 2 + 0.5);
|
|
31875
|
+
ctx.restore();
|
|
31876
|
+
}
|
|
31877
|
+
if (badge) {
|
|
31878
|
+
// A pin's head is the image's centre and its tip half the image height lower; the badge sits g.badge from
|
|
31879
|
+
// the tip (a circle's centre is the image's centre).
|
|
31880
|
+
var tipY = args[0] === 'pin' ? h / 2 + g.tipToHead : h / 2;
|
|
31881
|
+
ctx.save();
|
|
31882
|
+
ctx.translate(w / 2 + g.badge[0] - badge.width / 2, tipY + g.badge[1] - badge.height / 2);
|
|
31883
|
+
badge.draw(ctx, ratio);
|
|
31884
|
+
ctx.restore();
|
|
31885
|
+
}
|
|
31839
31886
|
},
|
|
31840
31887
|
};
|
|
31841
31888
|
},
|
|
@@ -32001,7 +32048,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
32001
32048
|
* minWidth, offset, anchor, closeButton, closeOnClick, focusAfterOpen)
|
|
32002
32049
|
* @param {string|Node} [options.popupLoading] shown while a popup's content is a pending promise (default: dots)
|
|
32003
32050
|
* @param {'auto'|'webgl'|'canvas'} [options.renderer] 'auto' (default): the WebGL map, or the canvas map (raster
|
|
32004
|
-
* tiles, layers drawn in 2D) where the browser has no WebGL 2 (
|
|
32051
|
+
* tiles, layers drawn in 2D) where the browser has no WebGL 2 (M67)
|
|
32005
32052
|
* Every other option (center, zoom, pitch, bearing, minZoom, maxZoom, maxBounds, hash, …) goes to the engine.
|
|
32006
32053
|
*/
|
|
32007
32054
|
function SMap(options) {
|
|
@@ -32057,7 +32104,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
32057
32104
|
this._toolHandlers = [];
|
|
32058
32105
|
|
|
32059
32106
|
var self = this;
|
|
32060
|
-
// The renderer (
|
|
32107
|
+
// The renderer (M67): the WebGL engine, or the canvas map where there is no WebGL 2 (or when asked for).
|
|
32061
32108
|
var want = options.renderer || 'auto';
|
|
32062
32109
|
// Asked of the page itself; without a page (a server, a test) the WebGL engine is kept.
|
|
32063
32110
|
var hasPage = typeof document !== 'undefined' && !!document && typeof document.createElement === 'function';
|
|
@@ -34404,7 +34451,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
34404
34451
|
*/
|
|
34405
34452
|
SMap.prototype.setBaseImagery = function (imagery) {
|
|
34406
34453
|
if (imagery && (!Array.isArray(imagery.tiles) || !imagery.tiles.length)) { throw new Error('sMap: base imagery needs tiles'); }
|
|
34407
|
-
// Google's and Bing's tiles only through their own terms: Google's with setGoogleBase (M31,
|
|
34454
|
+
// Google's and Bing's tiles only through their own terms: Google's with setGoogleBase (M31, M72).
|
|
34408
34455
|
if (imagery) { interop.refuseForbidden(imagery.tiles); }
|
|
34409
34456
|
return this._setBaseImagery(imagery);
|
|
34410
34457
|
};
|
|
@@ -35445,13 +35492,31 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35445
35492
|
// Opacity of the pin, its number and its badge together (the route map draws settled stops at .72).
|
|
35446
35493
|
var markerPaint = mk.opacity !== undefined ? { 'icon-opacity': valueExpr(mk.opacity, 1) } : undefined;
|
|
35447
35494
|
main = src + '-points';
|
|
35448
|
-
//
|
|
35449
|
-
//
|
|
35450
|
-
// pins
|
|
35495
|
+
// A pin's number and count badge are drawn into its own image (as one element of the route map's pins), so an
|
|
35496
|
+
// upper pin covers a lower one completely, number and badge included. bakeZoom (a zoom) keeps them their own
|
|
35497
|
+
// layers above the pins further out than it — fewer images where thousands of pins are in view, but numbers
|
|
35498
|
+
// over every pin there — and bakeZoom: false keeps them apart at every zoom. textMinzoom / badgeMinzoom start
|
|
35499
|
+
// them at their zoom either way.
|
|
35451
35500
|
var plainPin = drawnImageId('pin', [shape, str(mk.fill, '#ffffff'), str(mk.border, color), String(bw), String(size)]);
|
|
35452
|
-
var
|
|
35453
|
-
var
|
|
35454
|
-
|
|
35501
|
+
var hasText = mk.text !== undefined, hasBadge = mk.badge !== undefined;
|
|
35502
|
+
var bakeZoom = (hasText || hasBadge) && mk.bakeZoom !== false ? (typeof mk.bakeZoom === 'number' ? mk.bakeZoom : 0) : null;
|
|
35503
|
+
var badgeNumber = ['to-number', valueExpr(mk.badge, 0), 0];
|
|
35504
|
+
var textMin = typeof mk.textMinzoom === 'number' ? mk.textMinzoom : 0;
|
|
35505
|
+
var badgeMin = typeof mk.badgeMinzoom === 'number' ? mk.badgeMinzoom : 0;
|
|
35506
|
+
var imageAt = function (z) {
|
|
35507
|
+
if (bakeZoom === null || z < bakeZoom) { return plainPin; }
|
|
35508
|
+
var withText = hasText && z >= textMin, withBadge = hasBadge && z >= badgeMin;
|
|
35509
|
+
if (!withText && !withBadge) { return plainPin; }
|
|
35510
|
+
return drawnImageId('pinnum', [shape, str(mk.fill, '#ffffff'), str(mk.border, color), String(bw), String(size), str(mk.textColor, '#ffffff'),
|
|
35511
|
+
withBadge ? ['case', ['>', badgeNumber, 1], ['to-string', badgeNumber], ''] : '', withText ? str(mk.text, '') : '']);
|
|
35512
|
+
};
|
|
35513
|
+
var breaks = [bakeZoom, textMin, badgeMin].filter(function (z, i, all) { return typeof z === 'number' && z > 0 && all.indexOf(z) === i; })
|
|
35514
|
+
.sort(function (x, y) { return x - y; });
|
|
35515
|
+
var pinImage = imageAt(0);
|
|
35516
|
+
if (breaks.length) {
|
|
35517
|
+
pinImage = ['step', ['zoom'], imageAt(0)];
|
|
35518
|
+
breaks.forEach(function (z) { pinImage.push(z, imageAt(z)); });
|
|
35519
|
+
}
|
|
35455
35520
|
var markerSpecs = [];
|
|
35456
35521
|
var addMarker = function (layer) { markerSpecs.push(JSON.parse(JSON.stringify(layer))); add(layer); };
|
|
35457
35522
|
addMarker({
|
|
@@ -35464,7 +35529,7 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35464
35529
|
'icon-allow-overlap': true, 'icon-ignore-placement': true,
|
|
35465
35530
|
},
|
|
35466
35531
|
});
|
|
35467
|
-
if (
|
|
35532
|
+
if (hasText && bakeZoom !== 0) {
|
|
35468
35533
|
var text = str(mk.text, '');
|
|
35469
35534
|
addMarker({
|
|
35470
35535
|
id: src + '-numbers', type: 'symbol', filter: both(['!=', text, '']), minzoom: mk.textMinzoom, maxzoom: bakeZoom === null ? undefined : bakeZoom, paint: markerPaint,
|
|
@@ -35474,10 +35539,10 @@ function smapCreateSdk(engine, interop, canvas, plan) {
|
|
|
35474
35539
|
},
|
|
35475
35540
|
});
|
|
35476
35541
|
}
|
|
35477
|
-
if (
|
|
35478
|
-
var badge =
|
|
35542
|
+
if (hasBadge && bakeZoom !== 0) {
|
|
35543
|
+
var badge = badgeNumber;
|
|
35479
35544
|
addMarker({
|
|
35480
|
-
id: src + '-badges', type: 'symbol', filter: both(['>', badge, 1]), minzoom: mk.badgeMinzoom, paint: markerPaint,
|
|
35545
|
+
id: src + '-badges', type: 'symbol', filter: both(['>', badge, 1]), minzoom: mk.badgeMinzoom, maxzoom: bakeZoom === null ? undefined : bakeZoom, paint: markerPaint,
|
|
35481
35546
|
layout: {
|
|
35482
35547
|
'icon-image': drawnImageId('badge', [['to-string', badge]]),
|
|
35483
35548
|
'icon-offset': g.badge, 'icon-size': scale,
|
|
@@ -35731,7 +35796,7 @@ function SMapMap(options) {
|
|
|
35731
35796
|
SMapMap.prototype = core.Map.prototype;
|
|
35732
35797
|
return new core.Map(options);
|
|
35733
35798
|
}
|
|
35734
|
-
var smapVersion = "1.2.
|
|
35799
|
+
var smapVersion = "1.2.2";
|
|
35735
35800
|
var smapStyles = ['light', 'white', 'grayscale', 'dark', 'black'];
|
|
35736
35801
|
/** The bundled rendering engine, for anything the SDK does not wrap (loaded on the first call). */
|
|
35737
35802
|
function smapGetEngine() { return smapLoad().engine; }
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@superrouteca/smap",
|
|
3
|
-
"version": "1.2.
|
|
3
|
+
"version": "1.2.2",
|
|
4
4
|
"description": "sMap for the web: maps from Superroute's sMap service, the Web SDK (map view) and the JS client (tokens, nearest node, styles, tiles).",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": "Goodneo Solutions",
|
package/types/smap.d.cts
CHANGED
|
@@ -257,7 +257,7 @@ export interface MarkerOptions {
|
|
|
257
257
|
scale?: number | unknown[];
|
|
258
258
|
/** The pin under the pointer comes to the front (default true). */
|
|
259
259
|
hoverRaise?: boolean;
|
|
260
|
-
/**
|
|
260
|
+
/** Numbers and badges are drawn into each pin, so an upper pin covers a lower one with them. A zoom keeps them their own layers above the pins further out (fewer images where thousands of pins are in view); false keeps them apart at every zoom. */
|
|
261
261
|
bakeZoom?: number | false;
|
|
262
262
|
/**
|
|
263
263
|
* Pins piled up under a click (default on): with `threshold` (4) or more within `radius` (12 px) the map zooms in by
|
package/types/smap.d.mts
CHANGED
|
@@ -257,7 +257,7 @@ export interface MarkerOptions {
|
|
|
257
257
|
scale?: number | unknown[];
|
|
258
258
|
/** The pin under the pointer comes to the front (default true). */
|
|
259
259
|
hoverRaise?: boolean;
|
|
260
|
-
/**
|
|
260
|
+
/** Numbers and badges are drawn into each pin, so an upper pin covers a lower one with them. A zoom keeps them their own layers above the pins further out (fewer images where thousands of pins are in view); false keeps them apart at every zoom. */
|
|
261
261
|
bakeZoom?: number | false;
|
|
262
262
|
/**
|
|
263
263
|
* Pins piled up under a click (default on): with `threshold` (4) or more within `radius` (12 px) the map zooms in by
|