mapshaper 0.6.0 → 0.6.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/README.md +3 -3
- package/mapshaper.js +205 -193
- package/package.json +6 -3
- package/www/mapshaper-gui.js +37 -41
- package/www/mapshaper.js +205 -193
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "mapshaper",
|
|
3
|
-
"version": "0.6.
|
|
3
|
+
"version": "0.6.2",
|
|
4
4
|
"description": "A tool for editing vector datasets for mapping and GIS.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"shapefile",
|
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
"cartography",
|
|
10
10
|
"simplification",
|
|
11
11
|
"topology",
|
|
12
|
-
|
|
12
|
+
"csv",
|
|
13
13
|
"gis"
|
|
14
14
|
],
|
|
15
15
|
"author": "Matthew Bloch <masiyou@gmail.com>",
|
|
@@ -25,7 +25,8 @@
|
|
|
25
25
|
"scripts": {
|
|
26
26
|
"test": "mocha test",
|
|
27
27
|
"build": "rollup --config",
|
|
28
|
-
|
|
28
|
+
"lint": "eslint --ext mjs src/",
|
|
29
|
+
"prepublishOnly": "npm lint; npm test; ./pre-publish",
|
|
29
30
|
"postpublish": "./release_web_ui; ./release_github_version",
|
|
30
31
|
"browserify": "browserify -r sync-request -r mproj -r buffer -r iconv-lite -r fs -r flatbush -r rw -r path -r kdbush -r @tmcw/togeojson -o www/modules.js",
|
|
31
32
|
"dev": "rollup --config --watch"
|
|
@@ -61,6 +62,7 @@
|
|
|
61
62
|
"@rollup/plugin-node-resolve": "^13.3.0",
|
|
62
63
|
"browserify": "^17.0.0",
|
|
63
64
|
"csv-spectrum": "^1.0.0",
|
|
65
|
+
"eslint": "^8.16.0",
|
|
64
66
|
"mocha": "^10.0.0",
|
|
65
67
|
"rollup": "^2.73.0",
|
|
66
68
|
"shell-quote": "^1.6.1",
|
|
@@ -71,6 +73,7 @@
|
|
|
71
73
|
"node-option": [
|
|
72
74
|
"experimental-specifier-resolution=node"
|
|
73
75
|
],
|
|
76
|
+
"check-leaks": true,
|
|
74
77
|
"parallel": true,
|
|
75
78
|
"jobs": 4
|
|
76
79
|
},
|
package/www/mapshaper-gui.js
CHANGED
|
@@ -1682,7 +1682,6 @@
|
|
|
1682
1682
|
}
|
|
1683
1683
|
|
|
1684
1684
|
function Slider(ref, opts) {
|
|
1685
|
-
var _el = El(ref);
|
|
1686
1685
|
var _self = this;
|
|
1687
1686
|
var defaults = {
|
|
1688
1687
|
space: 7
|
|
@@ -1713,7 +1712,7 @@
|
|
|
1713
1712
|
_handle = El(ref);
|
|
1714
1713
|
draggable(_handle)
|
|
1715
1714
|
.on('drag', function(e) {
|
|
1716
|
-
setHandlePos(startX + e.dx
|
|
1715
|
+
setHandlePos(startX + e.dx);
|
|
1717
1716
|
})
|
|
1718
1717
|
.on('dragstart', function(e) {
|
|
1719
1718
|
startX = position();
|
|
@@ -1739,7 +1738,7 @@
|
|
|
1739
1738
|
return _pct;
|
|
1740
1739
|
};
|
|
1741
1740
|
|
|
1742
|
-
function setHandlePos(x
|
|
1741
|
+
function setHandlePos(x) {
|
|
1743
1742
|
x = utils$1.clamp(x, 0, size());
|
|
1744
1743
|
var pct = x / size();
|
|
1745
1744
|
if (pct != _pct) {
|
|
@@ -3122,7 +3121,7 @@
|
|
|
3122
3121
|
|
|
3123
3122
|
function cleanLayerName(raw) {
|
|
3124
3123
|
return raw.replace(/[\n\t/\\]/g, '')
|
|
3125
|
-
.replace(/^[
|
|
3124
|
+
.replace(/^[.\s]+/, '').replace(/[.\s]+$/, '');
|
|
3126
3125
|
}
|
|
3127
3126
|
|
|
3128
3127
|
function updateLayerStackOrder(layers) {
|
|
@@ -3856,8 +3855,6 @@
|
|
|
3856
3855
|
}
|
|
3857
3856
|
}
|
|
3858
3857
|
|
|
3859
|
-
var snapVerticesToPoint = internal.snapVerticesToPoint;
|
|
3860
|
-
var cloneShape = internal.cloneShape;
|
|
3861
3858
|
var copyRecord = internal.copyRecord;
|
|
3862
3859
|
|
|
3863
3860
|
function Undo(gui) {
|
|
@@ -4741,7 +4738,7 @@
|
|
|
4741
4738
|
'/': '/'
|
|
4742
4739
|
};
|
|
4743
4740
|
function htmlEscape(s) {
|
|
4744
|
-
return String(s).replace(/[&<>"'
|
|
4741
|
+
return String(s).replace(/[&<>"'/]/g, function(s) {
|
|
4745
4742
|
return entityMap[s];
|
|
4746
4743
|
});
|
|
4747
4744
|
}
|
|
@@ -5384,8 +5381,8 @@
|
|
|
5384
5381
|
var type = matches[4];
|
|
5385
5382
|
var isString = type == 's',
|
|
5386
5383
|
isHex = type == 'x' || type == 'X',
|
|
5387
|
-
isInt = type == 'd' || type == 'i',
|
|
5388
|
-
isFloat = type == 'f',
|
|
5384
|
+
// isInt = type == 'd' || type == 'i',
|
|
5385
|
+
// isFloat = type == 'f',
|
|
5389
5386
|
isNumber = !isString;
|
|
5390
5387
|
|
|
5391
5388
|
var sign = "",
|
|
@@ -5444,7 +5441,7 @@
|
|
|
5444
5441
|
|
|
5445
5442
|
// Get a function for interpolating formatted values into a string.
|
|
5446
5443
|
function formatter(fmt) {
|
|
5447
|
-
var codeRxp = /%([
|
|
5444
|
+
var codeRxp = /%([',+0]*)([1-9]?)((?:\.[1-9])?)([sdifxX%])/g;
|
|
5448
5445
|
var literals = [],
|
|
5449
5446
|
formatCodes = [],
|
|
5450
5447
|
startIdx = 0,
|
|
@@ -5844,27 +5841,21 @@
|
|
|
5844
5841
|
|
|
5845
5842
|
function pointTest(x, y) {
|
|
5846
5843
|
var bullseyeDist = 2, // hit all points w/in 2 px
|
|
5847
|
-
tinyDist = 0.5,
|
|
5848
|
-
toPx = ext.getTransform().mx,
|
|
5849
|
-
hits = [],
|
|
5850
5844
|
hitThreshold = 25,
|
|
5851
|
-
|
|
5845
|
+
toPx = ext.getTransform().mx,
|
|
5846
|
+
hits = [];
|
|
5852
5847
|
|
|
5848
|
+
// inlining forEachPoint() does not not appreciably speed this up
|
|
5853
5849
|
internal.forEachPoint(displayLayer.layer.shapes, function(p, id) {
|
|
5854
5850
|
var dist = geom.distance2D(x, y, p[0], p[1]) * toPx;
|
|
5855
5851
|
if (dist > hitThreshold) return;
|
|
5856
|
-
|
|
5857
|
-
|
|
5858
|
-
|
|
5859
|
-
hits = [id];
|
|
5860
|
-
hitThreshold = Math.max(bullseyeDist, dist + tinyDist);
|
|
5861
|
-
newThreshold = dist < bullseyeDist ? -1 : dist - tinyDist;
|
|
5862
|
-
} else {
|
|
5863
|
-
// add to hits if inside bullseye or is same dist as previous hit
|
|
5864
|
-
hits.push(id);
|
|
5852
|
+
if (dist < hitThreshold && hitThreshold > bullseyeDist) {
|
|
5853
|
+
hits = [];
|
|
5854
|
+
hitThreshold = Math.max(bullseyeDist, dist);
|
|
5865
5855
|
}
|
|
5856
|
+
hits.push(id);
|
|
5866
5857
|
});
|
|
5867
|
-
// TODO: add info on what part of a shape gets hit
|
|
5858
|
+
// TODO: add info on what part of a shape gets hit?
|
|
5868
5859
|
return {
|
|
5869
5860
|
ids: utils$1.uniq(hits) // multipoint features can register multiple hits
|
|
5870
5861
|
};
|
|
@@ -8754,7 +8745,7 @@
|
|
|
8754
8745
|
bx = t.bx,
|
|
8755
8746
|
by = t.by;
|
|
8756
8747
|
if (size === 0) return;
|
|
8757
|
-
if (size <=
|
|
8748
|
+
if (size <= 6 && !styler) {
|
|
8758
8749
|
// optimized drawing of many small same-colored dots
|
|
8759
8750
|
_self.drawSquareDotsFaster(shapes, color, size, t);
|
|
8760
8751
|
return;
|
|
@@ -8811,14 +8802,12 @@
|
|
|
8811
8802
|
// pixels: Uint32Array of pixel colors
|
|
8812
8803
|
// w, h: Size of canvas
|
|
8813
8804
|
function drawSquareFaster(x, y, rgba, size, pixels, w, h) {
|
|
8814
|
-
var xmin = (x - size * 0.5) | 0;
|
|
8815
|
-
var ymin = (y - size * 0.5) | 0;
|
|
8816
|
-
var xmax = xmin + size - 1;
|
|
8817
|
-
var ymax = ymin + size - 1;
|
|
8818
|
-
var
|
|
8819
|
-
|
|
8820
|
-
if (c < 0 || c >= w) continue;
|
|
8821
|
-
for (r = ymin; r <= ymax && r >= 0 && r < h; r++) {
|
|
8805
|
+
var xmin = x < 0 ? 0 : (x - size * 0.5) | 0;
|
|
8806
|
+
var ymin = y < 0 ? 0 : (y - size * 0.5) | 0;
|
|
8807
|
+
var xmax = x >= w-1 ? w-1 : xmin + size - 1;
|
|
8808
|
+
var ymax = y >= h-1 ? h-1 : ymin + size - 1;
|
|
8809
|
+
for (var r = ymin; r <= ymax; r++) {
|
|
8810
|
+
for (var c = xmin; c <= xmax; c++) {
|
|
8822
8811
|
pixels[r * w + c] = rgba;
|
|
8823
8812
|
}
|
|
8824
8813
|
}
|
|
@@ -8905,24 +8894,25 @@
|
|
|
8905
8894
|
return s;
|
|
8906
8895
|
}
|
|
8907
8896
|
|
|
8908
|
-
|
|
8909
8897
|
function getDotScale(ext) {
|
|
8910
8898
|
var smallSide = Math.min(ext.width(), ext.height());
|
|
8899
|
+
var mapScale = ext.scale();
|
|
8911
8900
|
// reduce size on smaller screens
|
|
8912
8901
|
var j = smallSide < 200 && 0.5 || smallSide < 400 && 0.75 || 1;
|
|
8902
|
+
// grow dots as map zooms in
|
|
8913
8903
|
var k = 1;
|
|
8914
|
-
var mapScale = ext.scale();
|
|
8915
8904
|
if (mapScale < 0.5) {
|
|
8916
8905
|
k = Math.pow(mapScale + 0.5, 0.35);
|
|
8917
|
-
}
|
|
8918
|
-
if (mapScale > 1) {
|
|
8906
|
+
} else if (mapScale > 1) {
|
|
8919
8907
|
// scale faster at first, so small dots in large datasets
|
|
8920
8908
|
// become easily visible and clickable after zooming in a bit
|
|
8921
8909
|
k *= Math.pow(Math.min(mapScale, 10), 0.3);
|
|
8922
8910
|
k *= Math.pow(mapScale, 0.1);
|
|
8923
8911
|
}
|
|
8924
|
-
|
|
8925
|
-
|
|
8912
|
+
// grow pixels more slowly on retina displays (to reduce number of pixels to
|
|
8913
|
+
// draw for large point datasets when slightly zoomed in)
|
|
8914
|
+
var l = Math.pow(GUI.getPixelRatio(), 0.8);
|
|
8915
|
+
return j * k * l;
|
|
8926
8916
|
}
|
|
8927
8917
|
|
|
8928
8918
|
function getScaledTransform(ext) {
|
|
@@ -9495,7 +9485,7 @@
|
|
|
9495
9485
|
|
|
9496
9486
|
// Only generate low-detail arcs for larger datasets
|
|
9497
9487
|
if (size > 5e5) {
|
|
9498
|
-
if (
|
|
9488
|
+
if (unfilteredArcs.getVertexData().zz) {
|
|
9499
9489
|
// Use precalculated simplification data for vertex filtering, if available
|
|
9500
9490
|
filteredArcs = initFilteredArcs(unfilteredArcs);
|
|
9501
9491
|
filteredSegLen = internal.getAvgSegment(filteredArcs);
|
|
@@ -9861,7 +9851,13 @@
|
|
|
9861
9851
|
var warning;
|
|
9862
9852
|
|
|
9863
9853
|
if (!dataCRS || !displayCRS || !crsIsUsable(displayCRS) || !crsIsUsable(dataCRS)) {
|
|
9864
|
-
warning = '
|
|
9854
|
+
warning = 'This data is incompatible with the basemaps.';
|
|
9855
|
+
if (!internal.layerHasGeometry(activeLyr.layer)) {
|
|
9856
|
+
warning += ' Reason: layer is missing geographic data';
|
|
9857
|
+
} else if (!dataCRS) {
|
|
9858
|
+
warning += ' Reason: unknown projection.';
|
|
9859
|
+
}
|
|
9860
|
+
|
|
9865
9861
|
basemapWarning.html(warning).show();
|
|
9866
9862
|
basemapNote.hide();
|
|
9867
9863
|
} else {
|