Review fixes
This commit is contained in:
parent
9713d04c7f
commit
367b2bc27e
2 changed files with 106 additions and 90 deletions
|
@ -340,6 +340,30 @@ public class OsmMapUtils {
|
|||
}
|
||||
}
|
||||
|
||||
public static void simplifyDouglasPeucker(List<Node> nodes, int start, int end, List<Node> survivedNodes, double epsilon) {
|
||||
double dmax = Double.NEGATIVE_INFINITY;
|
||||
int index = -1;
|
||||
|
||||
Node startPt = nodes.get(start);
|
||||
Node endPt = nodes.get(end);
|
||||
|
||||
for (int i = start + 1; i < end; i++) {
|
||||
Node pt = nodes.get(i);
|
||||
double d = MapUtils.getOrthogonalDistance(pt.getLatitude(), pt.getLongitude(),
|
||||
startPt.getLatitude(), startPt.getLongitude(), endPt.getLatitude(), endPt.getLongitude());
|
||||
if (d > dmax) {
|
||||
dmax = d;
|
||||
index = i;
|
||||
}
|
||||
}
|
||||
if (dmax > epsilon) {
|
||||
simplifyDouglasPeucker(nodes, start, index, survivedNodes, epsilon);
|
||||
simplifyDouglasPeucker(nodes, index, end, survivedNodes, epsilon);
|
||||
} else {
|
||||
survivedNodes.add(nodes.get(end));
|
||||
}
|
||||
}
|
||||
|
||||
private static double orthogonalDistance(int zoom, Node nodeLineStart, Node nodeLineEnd, Node node) {
|
||||
LatLon p = MapUtils.getProjection(node.getLatitude(), node.getLongitude(), nodeLineStart.getLatitude(),
|
||||
nodeLineStart.getLongitude(), nodeLineEnd.getLatitude(), nodeLineEnd.getLongitude());
|
||||
|
@ -619,30 +643,6 @@ public class OsmMapUtils {
|
|||
return new Cell(x / area, y / area, 0, rings);
|
||||
}
|
||||
|
||||
public static void simplifyDouglasPeucker(List<Node> nodes, int start, int end, List<Node> survivedNodes, double epsilon) {
|
||||
double dmax = Double.NEGATIVE_INFINITY;
|
||||
int index = -1;
|
||||
|
||||
Node startPt = nodes.get(start);
|
||||
Node endPt = nodes.get(end);
|
||||
|
||||
for (int i = start + 1; i < end; i++) {
|
||||
Node pt = nodes.get(i);
|
||||
double d = MapUtils.getOrthogonalDistance(pt.getLatitude(), pt.getLongitude(),
|
||||
startPt.getLatitude(), startPt.getLongitude(), endPt.getLatitude(), endPt.getLongitude());
|
||||
if (d > dmax) {
|
||||
dmax = d;
|
||||
index = i;
|
||||
}
|
||||
}
|
||||
if (dmax > epsilon) {
|
||||
simplifyDouglasPeucker(nodes, start, index, survivedNodes, epsilon);
|
||||
simplifyDouglasPeucker(nodes, index, end, survivedNodes, epsilon);
|
||||
} else {
|
||||
survivedNodes.add(nodes.get(end));
|
||||
}
|
||||
}
|
||||
|
||||
private static class CellComparator implements Comparator<Cell> {
|
||||
@Override
|
||||
public int compare(Cell o1, Cell o2) {
|
||||
|
|
|
@ -118,8 +118,7 @@ public class GPXLayer extends OsmandMapLayer implements IContextMenuProvider, IM
|
|||
private MapMarkersHelper mapMarkersHelper;
|
||||
private GpxSelectionHelper selectedGpxHelper;
|
||||
|
||||
private final Map<String, Long> cachedModifiedTime = new HashMap<>();
|
||||
private final Map<String, List<TrkSegment>> cachedZoomedSegments = new HashMap<>();
|
||||
private final Map<String, CachedTrack> segmentsCache = new HashMap<>();
|
||||
|
||||
private List<WptPt> cache = new ArrayList<>();
|
||||
private Map<WptPt, SelectedGpxFile> pointFileMap = new HashMap<>();
|
||||
|
@ -688,7 +687,7 @@ public class GPXLayer extends OsmandMapLayer implements IContextMenuProvider, IM
|
|||
|
||||
private void drawSelectedFileSegments(SelectedGpxFile selectedGpxFile, boolean currentTrack, Canvas canvas,
|
||||
RotatedTileBox tileBox, DrawSettings settings) {
|
||||
boolean visible = QuadRect.trivialOverlap(tileBox.getLatLonBounds(), GPXUtilities.calculateTrackBounds(selectedGpxFile.getModifiablePointsToDisplay()));
|
||||
boolean visible = QuadRect.trivialOverlap(tileBox.getLatLonBounds(), GPXUtilities.calculateTrackBounds(selectedGpxFile.getPointsToDisplay()));
|
||||
if (!selectedGpxFile.getGpxFile().hasTrkPt() || !visible) {
|
||||
return;
|
||||
}
|
||||
|
@ -698,7 +697,7 @@ public class GPXLayer extends OsmandMapLayer implements IContextMenuProvider, IM
|
|||
List<TrkSegment> segments = new ArrayList<>();
|
||||
|
||||
if (scaleType == null) {
|
||||
segments.addAll(selectedGpxFile.getModifiablePointsToDisplay());
|
||||
segments.addAll(selectedGpxFile.getPointsToDisplay());
|
||||
} else {
|
||||
segments.addAll(getCachedSegments(selectedGpxFile, scaleType));
|
||||
}
|
||||
|
@ -728,69 +727,14 @@ public class GPXLayer extends OsmandMapLayer implements IContextMenuProvider, IM
|
|||
|
||||
private List<TrkSegment> getCachedSegments(SelectedGpxFile selectedGpxFile, GradientScaleType scaleType) {
|
||||
GPXFile gpxFile = selectedGpxFile.getGpxFile();
|
||||
String fileName = gpxFile.path;
|
||||
String trackId = view.getZoom() + "_" + scaleType.toString() + "_" + fileName;
|
||||
|
||||
if (cachedModifiedTime.get(fileName) != null && cachedModifiedTime.get(fileName) == gpxFile.modifiedTime) {
|
||||
List<TrkSegment> segments = cachedZoomedSegments.get(trackId);
|
||||
if (segments == null) {
|
||||
segments = calculateGradientTrack(selectedGpxFile, scaleType);
|
||||
cachedZoomedSegments.put(trackId, segments);
|
||||
String path = gpxFile.path;
|
||||
long modifiedTime = gpxFile.modifiedTime;
|
||||
CachedTrack cachedTrack = segmentsCache.get(path);
|
||||
if (cachedTrack == null) {
|
||||
cachedTrack = new CachedTrack(view.getApplication(), modifiedTime);
|
||||
segmentsCache.put(path, cachedTrack);
|
||||
}
|
||||
return segments;
|
||||
} else {
|
||||
if (cachedModifiedTime.get(fileName) != null) {
|
||||
for (String key : cachedZoomedSegments.keySet()) {
|
||||
if (key.contains("_" + fileName)) {
|
||||
cachedZoomedSegments.remove(key);
|
||||
}
|
||||
}
|
||||
}
|
||||
cachedModifiedTime.put(fileName, gpxFile.modifiedTime);
|
||||
List<TrkSegment> segments = calculateGradientTrack(selectedGpxFile, scaleType);
|
||||
cachedZoomedSegments.put(trackId, segments);
|
||||
return segments;
|
||||
}
|
||||
}
|
||||
|
||||
private List<TrkSegment> calculateGradientTrack(SelectedGpxFile selectedGpxFile, GradientScaleType scaleType) {
|
||||
OsmandApplication app = view.getApplication();
|
||||
GPXFile gpxFile = selectedGpxFile.getGpxFile();
|
||||
RouteColorize colorize = new RouteColorize(view.getZoom(), gpxFile, selectedGpxFile.getTrackAnalysis(app),
|
||||
scaleType.toColorizationType(), app.getSettings().getApplicationMode().getMaxSpeed());
|
||||
colorize.setPalette(getColorizationPalette(gpxFile, scaleType));
|
||||
List<RouteColorizationPoint> colorsOfPoints = colorize.getResult(true);
|
||||
return createSimplifiedSegmentsFromColorizedPoints(selectedGpxFile.getGpxFile(), colorsOfPoints, scaleType);
|
||||
}
|
||||
|
||||
private List<TrkSegment> createSimplifiedSegmentsFromColorizedPoints(GPXFile gpxFile,
|
||||
List<RouteColorizationPoint> colorizationPoints,
|
||||
GradientScaleType scaleType) {
|
||||
List<TrkSegment> simplifiedSegments = new ArrayList<>();
|
||||
ColorizationType colorizationType = scaleType.toColorizationType();
|
||||
int id = 0;
|
||||
int colorPointIdx = 0;
|
||||
|
||||
for (GPXUtilities.Track track : gpxFile.tracks) {
|
||||
for (TrkSegment segment : track.segments) {
|
||||
TrkSegment simplifiedSegment = new TrkSegment();
|
||||
simplifiedSegments.add(simplifiedSegment);
|
||||
for (WptPt pt : segment.points) {
|
||||
if (colorPointIdx >= colorizationPoints.size()) {
|
||||
return simplifiedSegments;
|
||||
}
|
||||
RouteColorizationPoint colorPoint = colorizationPoints.get(colorPointIdx);
|
||||
if (colorPoint.id == id) {
|
||||
simplifiedSegment.points.add(pt);
|
||||
pt.setColor(colorizationType, colorPoint.color);
|
||||
colorPointIdx++;
|
||||
}
|
||||
id++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return simplifiedSegments;
|
||||
return cachedTrack.getCachedSegments(selectedGpxFile, view.getZoom(), scaleType, getColorizationPalette(gpxFile, scaleType));
|
||||
}
|
||||
|
||||
private float getTrackWidth(String width, float defaultTrackWidth) {
|
||||
|
@ -1238,4 +1182,76 @@ public class GPXLayer extends OsmandMapLayer implements IContextMenuProvider, IM
|
|||
view.getApplication().getItineraryHelper().runSynchronization(group);
|
||||
}
|
||||
}
|
||||
|
||||
private static class CachedTrack {
|
||||
|
||||
private OsmandApplication app;
|
||||
|
||||
private long modifiedTime;
|
||||
private final Map<String, List<TrkSegment>> cache = new HashMap<>();
|
||||
|
||||
public CachedTrack(@NonNull OsmandApplication app, long modifiedTime) {
|
||||
this.app = app;
|
||||
this.modifiedTime = modifiedTime;
|
||||
}
|
||||
|
||||
public List<TrkSegment> getCachedSegments(@NonNull SelectedGpxFile selectedGpxFile, int zoom,
|
||||
@NonNull GradientScaleType scaleType,
|
||||
int[] gradientPalette) {
|
||||
GPXFile gpxFile = selectedGpxFile.getGpxFile();
|
||||
String trackId = zoom + "_" + scaleType.toString();
|
||||
if (modifiedTime == gpxFile.modifiedTime) {
|
||||
List<TrkSegment> segments = cache.get(trackId);
|
||||
if (segments == null) {
|
||||
segments = calculateGradientTrack(selectedGpxFile, zoom, scaleType, gradientPalette);
|
||||
cache.put(trackId, segments);
|
||||
}
|
||||
return segments;
|
||||
} else {
|
||||
cache.clear();
|
||||
modifiedTime = gpxFile.modifiedTime;
|
||||
List<TrkSegment> segments = calculateGradientTrack(selectedGpxFile, zoom, scaleType, gradientPalette);
|
||||
cache.put(trackId, segments);
|
||||
return segments;
|
||||
}
|
||||
}
|
||||
|
||||
private List<TrkSegment> calculateGradientTrack(SelectedGpxFile selectedGpxFile, int zoom,
|
||||
GradientScaleType scaleType, int[] gradientPalette) {
|
||||
GPXFile gpxFile = selectedGpxFile.getGpxFile();
|
||||
RouteColorize colorize = new RouteColorize(zoom, gpxFile, selectedGpxFile.getTrackAnalysis(app),
|
||||
scaleType.toColorizationType(), app.getSettings().getApplicationMode().getMaxSpeed());
|
||||
colorize.setPalette(gradientPalette);
|
||||
List<RouteColorizationPoint> colorsOfPoints = colorize.getResult(true);
|
||||
return createSimplifiedSegments(selectedGpxFile.getGpxFile(), colorsOfPoints, scaleType);
|
||||
}
|
||||
|
||||
private List<TrkSegment> createSimplifiedSegments(GPXFile gpxFile,
|
||||
List<RouteColorizationPoint> colorizationPoints,
|
||||
GradientScaleType scaleType) {
|
||||
List<TrkSegment> simplifiedSegments = new ArrayList<>();
|
||||
ColorizationType colorizationType = scaleType.toColorizationType();
|
||||
int id = 0;
|
||||
int colorPointIdx = 0;
|
||||
|
||||
for (TrkSegment segment : gpxFile.getNonEmptyTrkSegments(false)) {
|
||||
TrkSegment simplifiedSegment = new TrkSegment();
|
||||
simplifiedSegments.add(simplifiedSegment);
|
||||
for (WptPt pt : segment.points) {
|
||||
if (colorPointIdx >= colorizationPoints.size()) {
|
||||
return simplifiedSegments;
|
||||
}
|
||||
RouteColorizationPoint colorPoint = colorizationPoints.get(colorPointIdx);
|
||||
if (colorPoint.id == id) {
|
||||
simplifiedSegment.points.add(pt);
|
||||
pt.setColor(colorizationType, colorPoint.color);
|
||||
colorPointIdx++;
|
||||
}
|
||||
id++;
|
||||
}
|
||||
}
|
||||
|
||||
return simplifiedSegments;
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue