Skip to content

Commit cc5d006

Browse files
committed
Add d3.geo.path.distance.
Unfortunately, d3.geo.path.length is unavailable since d3.geo.path() returns a function, for which the "length" property cannot be overridden. Fixes d3#1556.
1 parent 2c93d9c commit cc5d006

4 files changed

Lines changed: 62 additions & 5 deletions

File tree

d3.js

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3487,6 +3487,33 @@ d3 = function() {
34873487
}
34883488
return stream;
34893489
}
3490+
var d3_geo_pathDistanceSum, d3_geo_pathDistancePolygon, d3_geo_pathDistance = {
3491+
point: d3_noop,
3492+
lineStart: d3_geo_pathDistanceLineStart,
3493+
lineEnd: d3_noop,
3494+
polygonStart: function() {
3495+
d3_geo_pathDistancePolygon = true;
3496+
},
3497+
polygonEnd: function() {
3498+
d3_geo_pathDistancePolygon = false;
3499+
}
3500+
};
3501+
function d3_geo_pathDistanceLineStart() {
3502+
var x00, y00, x0, y0;
3503+
d3_geo_pathDistance.point = function(x, y) {
3504+
d3_geo_pathDistance.point = nextPoint;
3505+
x00 = x0 = x, y00 = y0 = y;
3506+
};
3507+
d3_geo_pathDistance.lineEnd = function() {
3508+
if (d3_geo_pathDistancePolygon) nextPoint(x00, y00);
3509+
d3_geo_pathDistance.point = d3_geo_pathDistance.lineEnd = d3_noop;
3510+
};
3511+
function nextPoint(x, y) {
3512+
var dx = x - x0, dy = y - y0;
3513+
d3_geo_pathDistanceSum += Math.sqrt(dx * dx + dy * dy);
3514+
x0 = x, y0 = y;
3515+
}
3516+
}
34903517
function d3_geo_resample(project) {
34913518
var δ2 = .5, cosMinDistance = Math.cos(30 * d3_radians), maxDepth = 16;
34923519
function resample(stream) {
@@ -3613,6 +3640,11 @@ d3 = function() {
36133640
d3.geo.stream(object, projectStream(d3_geo_pathBounds));
36143641
return [ [ d3_geo_pathBoundsX0, d3_geo_pathBoundsY0 ], [ d3_geo_pathBoundsX1, d3_geo_pathBoundsY1 ] ];
36153642
};
3643+
path.distance = function(object) {
3644+
d3_geo_pathDistanceSum = 0;
3645+
d3.geo.stream(object, projectStream(d3_geo_pathDistance));
3646+
return d3_geo_pathDistanceSum;
3647+
};
36163648
path.projection = function(_) {
36173649
if (!arguments.length) return projection;
36183650
projectStream = (projection = _) ? _.stream || d3_geo_pathProjectStream(_) : d3_identity;

d3.min.js

Lines changed: 5 additions & 5 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/geo/path.js

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import "path-bounds";
1010
import "path-buffer";
1111
import "path-centroid";
1212
import "path-context";
13+
import "path-distance";
1314
import "projection";
1415
import "resample";
1516
import "stream";
@@ -55,6 +56,12 @@ d3.geo.path = function() {
5556
return [[d3_geo_pathBoundsX0, d3_geo_pathBoundsY0], [d3_geo_pathBoundsX1, d3_geo_pathBoundsY1]];
5657
};
5758

59+
path.distance = function(object) {
60+
d3_geo_pathDistanceSum = 0;
61+
d3.geo.stream(object, projectStream(d3_geo_pathDistance));
62+
return d3_geo_pathDistanceSum;
63+
};
64+
5865
path.projection = function(_) {
5966
if (!arguments.length) return projection;
6067
projectStream = (projection = _) ? _.stream || d3_geo_pathProjectStream(_) : d3_identity;

test/geo/path-test.js

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -122,6 +122,24 @@ suite.addBatch({
122122
}
123123
},
124124

125+
"distance": {
126+
topic: function(p) {
127+
return p.distance;
128+
},
129+
"of a point": function(distance) {
130+
assert.strictEqual(distance({type: "Point", coordinates: [30, 0]}), 0);
131+
},
132+
"of a line with one segment": function(distance) {
133+
assert.strictEqual(distance({type: "LineString", coordinates: [[30, 0], [0, 0]]}), 150);
134+
},
135+
"of a line with two segments": function(distance) {
136+
assert.strictEqual(distance({type: "LineString", coordinates: [[30, 0], [0, 0], [30, 0]]}), 300);
137+
},
138+
"of a polygon": function(distance) {
139+
assert.strictEqual(distance({type: "Polygon", coordinates: [[[0, 0], [0, 30], [30, 30], [30, 0], [0, 0]]]}), 600);
140+
}
141+
},
142+
125143
"centroid": {
126144
topic: function(p) {
127145
return p.centroid;

0 commit comments

Comments
 (0)