|
19 | 19 |
|
20 | 20 | import {Feature} from '../features/Feature';
|
21 | 21 | import Provider from './TileProvider/TileProvider';
|
22 |
| -import {geometry, geotools} from '@here/xyz-maps-common'; |
| 22 | +import {AStar, geometry, geotools} from '@here/xyz-maps-common'; |
23 | 23 | import {Tile} from '../tile/Tile';
|
24 | 24 | import {calcBBox} from '../features/utils';
|
25 | 25 | import RTree from '../features/RTree';
|
@@ -857,43 +857,44 @@ export class FeatureProvider extends Provider {
|
857 | 857 | return distance;
|
858 | 858 | },
|
859 | 859 | get path() {
|
860 |
| - const coordinates = this.features.map((feature) => feature.geometry.coordinates); |
861 |
| - const isReverseDirection = (fromLink, toLink) => { |
862 |
| - const fromGeom = fromLink.geometry.coordinates; |
863 |
| - const toGeom = toLink.geometry.coordinates; |
864 |
| - const minDistance = (p) => Math.min(geotools.distance(p, toGeom[0]), geotools.distance(p, toGeom[toGeom.length - 1])); |
865 |
| - return minDistance(fromGeom[0]) < minDistance(fromGeom[fromGeom.length - 1]); |
866 |
| - }; |
| 860 | + const {features} = this; |
| 861 | + let coords0 = [...features[0].geometry.coordinates]; |
| 862 | + let coords1 = features[1].geometry.coordinates; |
867 | 863 |
|
868 |
| - let reverseDirection = isReverseDirection(nodes[0].data.link, nodes[1].data.link); |
869 |
| - let {point, segment} = geometry.findPointOnLineString(coordinates[0], from as GeoJSONCoordinate); |
870 |
| - if (reverseDirection) { |
871 |
| - coordinates[0] = coordinates[0].slice(0, segment + 1); |
872 |
| - coordinates[0][segment + 1] = point; |
873 |
| - } else { |
874 |
| - coordinates[0] = coordinates[0].slice(segment); |
875 |
| - coordinates[0][0] = point; |
| 864 | + if (AStar.isPointEqual(coords0[0], coords1[0]) || AStar.isPointEqual(coords0[0], coords1[coords1.length - 1])) { |
| 865 | + // the travel of direction of the first lineString is reversed |
| 866 | + coords0.reverse(); |
| 867 | + } |
| 868 | + const multiLineString = [coords0]; |
| 869 | + |
| 870 | + for (let i = 1; i < features.length; i++) { |
| 871 | + const prevCoordinates = multiLineString[i - 1]; |
| 872 | + const lineString = [...features[i].geometry.coordinates]; |
| 873 | + if (!AStar.isPointEqual(lineString[0], prevCoordinates[prevCoordinates.length - 1])) { |
| 874 | + // does not match initial travel of direction |
| 875 | + lineString.reverse(); |
| 876 | + } |
| 877 | + multiLineString.push(lineString); |
876 | 878 | }
|
877 | 879 |
|
878 |
| - const lastIndex = coordinates.length - 1; |
| 880 | + const {point, segment} = geometry.findPointOnLineString(multiLineString[0], from as GeoJSONCoordinate); |
| 881 | + multiLineString[0] = multiLineString[0].slice(segment); |
| 882 | + multiLineString[0][0] = point; |
| 883 | + |
| 884 | + const lastIndex = multiLineString.length - 1; |
879 | 885 | let {
|
880 | 886 | point: pointEnd,
|
881 | 887 | segment: segmentEnd
|
882 |
| - } = geometry.findPointOnLineString(coordinates[lastIndex], to as GeoJSONCoordinate); |
883 |
| - if (nodes[nodes.length - 1].data.index == 0) { |
884 |
| - // reverse direction |
885 |
| - coordinates[lastIndex] = coordinates[lastIndex].slice(segmentEnd); |
886 |
| - coordinates[lastIndex][0] = pointEnd; |
887 |
| - } else { |
888 |
| - coordinates[lastIndex] = coordinates[lastIndex].slice(0, segmentEnd + 1); |
889 |
| - coordinates[lastIndex][segmentEnd + 1] = pointEnd; |
890 |
| - } |
| 888 | + } = geometry.findPointOnLineString(multiLineString[lastIndex], to as GeoJSONCoordinate); |
| 889 | + |
| 890 | + multiLineString[lastIndex] = multiLineString[lastIndex].slice(0, segmentEnd + 1); |
| 891 | + multiLineString[lastIndex][segmentEnd + 1] = pointEnd; |
891 | 892 |
|
892 | 893 | return {
|
893 | 894 | type: 'Feature',
|
894 | 895 | geometry: {
|
895 | 896 | type: 'MultiLineString',
|
896 |
| - coordinates |
| 897 | + coordinates: multiLineString |
897 | 898 | },
|
898 | 899 | properties: {}
|
899 | 900 | };
|
|
0 commit comments