use of org.onebusaway.geospatial.model.XYPoint in project onebusaway-application-modules by camsys.
the class GtfsComputePolylineBoundaryForStopsMain method printLineString.
private void printLineString(PrintWriter out, UTMProjection proj, LineString line, boolean latFirst) {
for (int i = 0; i < line.getNumPoints(); i++) {
Point point = line.getPointN(i);
XYPoint p = new XYPoint(point.getX(), point.getY());
CoordinatePoint c = proj.reverse(p);
if (latFirst)
out.println(c.getLat() + " " + c.getLon());
else
out.println(c.getLon() + " " + c.getLat());
}
}
use of org.onebusaway.geospatial.model.XYPoint in project onebusaway-application-modules by camsys.
the class ProjectedShapePointServiceImpl method getProjectedShapePoints.
@Cacheable
@Override
public T2<List<XYPoint>, double[]> getProjectedShapePoints(List<AgencyAndId> shapeIds, int utmZoneId) {
ShapePoints shapePoints = _shapePointService.getShapePointsForShapeIds(shapeIds);
if (shapePoints == null || shapePoints.isEmpty())
return null;
UTMProjection projection = new UTMProjection(utmZoneId);
List<XYPoint> projected = _shapePointsLibrary.getProjectedShapePoints(shapePoints, projection);
return Tuples.tuple(projected, shapePoints.getDistTraveled());
}
use of org.onebusaway.geospatial.model.XYPoint in project onebusaway-application-modules by camsys.
the class ShapePointsLibrary method computePotentialAssignments.
/**
* Here is the idea:
*
* Given a shape as an array of XY Points, a range over those points, and a
* target point, find the closest location(s) along the shape for the target
* point.
*
* The trick is that there may be multiple good assignments, especially for a
* shape that loops back on itself. In this case, we look for assignments
* within our {@link #_localMinimumThreshold} distance. There will typically
* be ranges of assignments that apply and we take the local min within each
* range. We then return each of these local mins as a potential assignment.
*
* There is an additional wrinkle when the section of the shape that loops
* back occurs where all the shape points are within
* {@link #_localMinimumThreshold} of the target point. In this case, we no
* longer consider the local min for the section, but the individual local
* mins within the section. That is to say, if we find a local min and then
* the shape moves away and comes back, we'll consider the second local min as
* a new potential assignment.
*
* If no assignments are found within the {@link #_localMinimumThreshold}
* distance, we just return the global min.
*
* @param projectedShapePoints
* @param shapePointDistance
* @param targetPoint
* @param fromIndex
* @param toIndex
* @return
*/
public List<PointAndIndex> computePotentialAssignments(List<XYPoint> projectedShapePoints, double[] shapePointDistance, XYPoint targetPoint, int fromIndex, int toIndex) {
/**
* The absolute closest assignment
*/
Min<PointAndIndex> min = new Min<PointAndIndex>();
/**
*/
Min<PointAndIndex> localMin = new Min<PointAndIndex>();
List<PointAndIndex> localMins = new ArrayList<PointAndIndex>();
/**
* For our multi-local min within the _localMinimumThreshold detection, we
* keep track of whether the endpoint of the previous segment was further
* away from the target point than the snapped point, indicating the shape
* is moving away from the target point. We also keep track of the distance
* of the target point from the endpoint of the previous segment. If the
* snapped point of the next section is closer to the target point than the
* previous endpoint AND the shape was moving away from the target point in
* the previous section, we establish a new local min.
*/
boolean previousEndpointDistanceGreaterThanSnappedDistance = false;
double previousEndpointDistance = Double.POSITIVE_INFINITY;
for (int i = fromIndex; i < toIndex - 1; i++) {
XYPoint from = projectedShapePoints.get(i);
XYPoint to = projectedShapePoints.get(i + 1);
XYPoint location = GeometryLibrary.projectPointToSegment(targetPoint, from, to);
double d = location.getDistance(targetPoint);
double distanceAlongShape = shapePointDistance[i] + location.getDistance(from);
PointAndIndex pindex = new PointAndIndex(location, i, d, distanceAlongShape);
min.add(d, pindex);
if (d <= _localMinimumThreshold) {
if (previousEndpointDistanceGreaterThanSnappedDistance && d < previousEndpointDistance && !localMin.isEmpty()) {
localMins.add(localMin.getMinElement());
localMin = new Min<PointAndIndex>();
}
localMin.add(d, pindex);
} else if (!localMin.isEmpty()) {
localMins.add(localMin.getMinElement());
localMin = new Min<PointAndIndex>();
}
previousEndpointDistance = to.getDistance(targetPoint);
previousEndpointDistanceGreaterThanSnappedDistance = previousEndpointDistance > d;
}
/**
* If don't have ANY potential assignments, return an empty list
*/
if (min.isEmpty())
return Collections.emptyList();
/**
* Check to see if we have a localMin element that needs to be added to our
* collection of local mins
*/
if (!localMin.isEmpty())
localMins.add(localMin.getMinElement());
/**
* If we don't have ANY local mins (aka assignments that were within our
* _localMinimumThreshold), we just use the best assigment(s) from the
* global min
*/
if (localMins.isEmpty())
localMins.addAll(min.getMinElements());
return localMins;
}
use of org.onebusaway.geospatial.model.XYPoint in project onebusaway-application-modules by camsys.
the class ShapePointsLibraryTest method shapePointDistances.
private double[] shapePointDistances(List<XYPoint> points) {
double[] distances = new double[points.size()];
double accumulatedDistance = 0;
for (int i = 0; i < points.size(); i++) {
XYPoint point = points.get(i);
if (i > 0)
accumulatedDistance += point.getDistance(points.get(i - 1));
distances[i] = accumulatedDistance;
}
return distances;
}
use of org.onebusaway.geospatial.model.XYPoint in project onebusaway-application-modules by camsys.
the class ShapePointsLibraryTest method test03.
@Test
public void test03() {
ShapePointsLibrary spl = new ShapePointsLibrary();
spl.setLocalMinimumThreshold(15);
List<XYPoint> points = new ArrayList<XYPoint>();
points.add(p(0, 0));
points.add(p(10, 0));
points.add(p(10, 1));
points.add(p(0, 1));
double[] shapePointDistances = shapePointDistances(points);
XYPoint target = p(1, 0.5);
List<PointAndIndex> result = spl.computePotentialAssignments(points, shapePointDistances, target, 0, points.size());
assertEquals(3, result.size());
PointAndIndex pi = result.get(0);
assertEquals(1.0, pi.point.getX(), 0.0);
assertEquals(0.0, pi.point.getY(), 0.0);
pi = result.get(1);
assertEquals(10.0, pi.point.getX(), 0.0);
assertEquals(0.5, pi.point.getY(), 0.0);
pi = result.get(2);
assertEquals(1.0, pi.point.getX(), 0.0);
assertEquals(1.0, pi.point.getY(), 0.0);
}
Aggregations