Merge branch 'r3.4' into save_trk_6258

This commit is contained in:
madwasp79 2019-07-09 14:49:32 +03:00
commit 37e220081f
66 changed files with 905 additions and 1018 deletions

View file

@ -158,16 +158,14 @@ public class LocationConvert {
StringBuilder sb = new StringBuilder();
// Handle negative values and append cardinal directions if necessary
if (addCardinalDirection) {
sb.append(latitude < 0 ? 'S' : 'N');
} else if (latitude < 0) {
if (!addCardinalDirection && latitude < 0) {
sb.append('-');
}
if (latitude < 0) {
latitude = -latitude;
formatDegrees(latitude < 0 ? -latitude : latitude, outputType, sb);
if (addCardinalDirection) {
sb.append(' ').append(latitude < 0 ? 'S' : 'N');
}
return formatDegrees(latitude, outputType, sb);
return sb.toString();
}
public static String convertLongitude(double longitude, int outputType, boolean addCardinalDirection) {
@ -181,16 +179,14 @@ public class LocationConvert {
StringBuilder sb = new StringBuilder();
// Handle negative values and append cardinal directions if necessary
if (addCardinalDirection) {
sb.append(longitude < 0 ? 'W' : 'E');
} else if (longitude < 0) {
if (!addCardinalDirection && longitude < 0) {
sb.append('-');
}
if (longitude < 0) {
longitude = -longitude;
formatDegrees(longitude < 0 ? -longitude : longitude, outputType, sb);
if (addCardinalDirection) {
sb.append(' ').append(longitude < 0 ? 'W' : 'E');
}
return formatDegrees(longitude, outputType, sb);
return sb.toString();
}
private static double formatCoordinate(double coordinate, StringBuilder sb, char delimiter) {

View file

@ -192,12 +192,6 @@ public class Postcode {
String res = matcher.replaceAll(replacement);
if (res != null) {
result = res.replaceAll("null", "");
if (!result.equals(postcode)) {
log.info("Normalize " + country + "'s postcode: " + postcode + " -> " + result);
}
if (!matcher.matches()) {
log.info("Not matches " + country + "'s postcode regex: " + postcode);
}
}
}
}

View file

@ -290,7 +290,8 @@ public class RenderingRuleProperty {
return false;
}
String val2 = req.getStorage().getStringValue(vl);
return val != null && val.equals(val2);
return val != null && (val.equals(val2) ||
(val2.indexOf(';') != -1 && val2.contains(val+';')));
}
int k = val.indexOf('=');

View file

@ -67,6 +67,9 @@ public class RoutePlannerFrontEnd {
if (dataObjects.isEmpty()) {
ctx.loadTileData(px, py, 15, dataObjects);
}
if (dataObjects.isEmpty()) {
ctx.loadTileData(px, py, 13, dataObjects);
}
if (list == null) {
list = new ArrayList<BinaryRoutePlanner.RouteSegmentPoint>();
}
@ -196,6 +199,9 @@ public class RoutePlannerFrontEnd {
RoutingContext nctx = buildRoutingContext(ctx.config, ctx.nativeLib, ctx.getMaps(), RouteCalculationMode.BASE);
nctx.calculationProgress = ctx.calculationProgress;
List<RouteSegmentResult> ls = searchRoute(nctx, start, end, intermediates);
if(ls == null) {
return null;
}
routeDirection = PrecalculatedRouteDirection.build(ls, ctx.config.DEVIATION_RADIUS, ctx.getRouter().getMaxSpeed());
}
if (intermediatesEmpty && ctx.nativeLib != null) {

View file

@ -1,34 +1,42 @@
package net.osmand.router;
import gnu.trove.iterator.TIntIterator;
import gnu.trove.list.array.TIntArrayList;
import gnu.trove.set.hash.TIntHashSet;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStream;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import org.apache.commons.logging.Log;
import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
import gnu.trove.iterator.TIntIterator;
import gnu.trove.list.array.TIntArrayList;
import gnu.trove.set.hash.TIntHashSet;
import net.osmand.PlatformUtil;
import net.osmand.binary.BinaryMapIndexReader;
import net.osmand.binary.BinaryMapRouteReaderAdapter.RouteTypeRule;
import net.osmand.binary.RouteDataObject;
import net.osmand.data.LatLon;
import net.osmand.osm.MapRenderingTypes;
import net.osmand.render.RenderingRuleSearchRequest;
import net.osmand.render.RenderingRulesStorage;
import net.osmand.render.RenderingRulesStorage.RenderingRulesStorageResolver;
import net.osmand.router.BinaryRoutePlanner.FinalRouteSegment;
import net.osmand.router.BinaryRoutePlanner.RouteSegment;
import net.osmand.router.GeneralRouter.GeneralRouterProfile;
import net.osmand.router.RoutePlannerFrontEnd.RouteCalculationMode;
import net.osmand.router.RouteStatisticsHelper.RouteStatistics;
import net.osmand.util.Algorithms;
import net.osmand.util.MapAlgorithms;
import net.osmand.util.MapUtils;
import org.apache.commons.logging.Log;
public class RouteResultPreparation {
public static boolean PRINT_TO_CONSOLE_ROUTE_INFORMATION_TO_TEST = false;
@ -603,6 +611,52 @@ public class RouteResultPreparation {
}
println("</test>");
println(msg);
// calculateStatistics(result);
}
private void calculateStatistics(List<RouteSegmentResult> result) {
InputStream is = RenderingRulesStorage.class.getResourceAsStream("default.render.xml");
final Map<String, String> renderingConstants = new LinkedHashMap<String, String>();
try {
InputStream pis = RenderingRulesStorage.class.getResourceAsStream("default.render.xml");
try {
XmlPullParser parser = PlatformUtil.newXMLPullParser();
parser.setInput(pis, "UTF-8");
int tok;
while ((tok = parser.next()) != XmlPullParser.END_DOCUMENT) {
if (tok == XmlPullParser.START_TAG) {
String tagName = parser.getName();
if (tagName.equals("renderingConstant")) {
if (!renderingConstants.containsKey(parser.getAttributeValue("", "name"))) {
renderingConstants.put(parser.getAttributeValue("", "name"),
parser.getAttributeValue("", "value"));
}
}
}
}
} finally {
pis.close();
}
RenderingRulesStorage rrs = new RenderingRulesStorage("default", renderingConstants);
rrs.parseRulesFromXmlInputStream(is, new RenderingRulesStorageResolver() {
@Override
public RenderingRulesStorage resolve(String name, RenderingRulesStorageResolver ref)
throws XmlPullParserException, IOException {
throw new UnsupportedOperationException();
}
});
RenderingRuleSearchRequest req = new RenderingRuleSearchRequest(rrs);
List<RouteStatistics> rsr = RouteStatisticsHelper.calculateRouteStatistic(result, null, rrs, null, req);
for(RouteStatistics r : rsr) {
System.out.println(r);
}
} catch (Exception e) {
throw new IllegalStateException(e.getMessage(), e);
}
}
private void printAdditionalPointInfo(RouteSegmentResult res) {

View file

@ -228,15 +228,4 @@ public class RouteSegmentResult {
return object.toString() + ": " + startPointIndex + "-" + endPointIndex;
}
public String getSurface() {
return object.getValue("surface");
}
public String getSmoothness() {
return object.getValue("smoothness");
}
public String getHighway() {
return object.getHighway();
}
}

View file

@ -1,623 +0,0 @@
package net.osmand.router;
import net.osmand.render.RenderingRuleSearchRequest;
import net.osmand.render.RenderingRulesStorage;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;
public class RouteStatistics {
public static final String UNDEFINED_ATTR = "undefined";
private final List<RouteSegmentResult> route;
private final RenderingRulesStorage currentRenderer;
private final RenderingRulesStorage defaultRenderer;
private final RenderingRuleSearchRequest currentSearchRequest;
private final RenderingRuleSearchRequest defaultSearchRequest;
private RouteStatistics(List<RouteSegmentResult> route, RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer, RenderingRuleSearchRequest currentSearchRequest, RenderingRuleSearchRequest defaultSearchRequest) {
this.route = route;
this.currentRenderer = currentRenderer;
this.defaultRenderer = defaultRenderer;
this.defaultSearchRequest = defaultSearchRequest;
this.currentSearchRequest = currentSearchRequest;
}
public static RouteStatistics newRouteStatistic(List<RouteSegmentResult> route, RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer, RenderingRuleSearchRequest currentSearchRequest, RenderingRuleSearchRequest defaultSearchRequest) {
return new RouteStatistics(route, currentRenderer, defaultRenderer, currentSearchRequest, defaultSearchRequest);
}
public Statistics getRouteSurfaceStatistic() {
RouteStatisticComputer statisticComputer = new RouteSurfaceStatisticComputer(route, currentRenderer, defaultRenderer, currentSearchRequest, defaultSearchRequest);
return statisticComputer.computeStatistic();
}
public Statistics getRouteSmoothnessStatistic() {
RouteStatisticComputer statisticComputer = new RouteSmoothnessStatisticComputer(route, currentRenderer, defaultRenderer, currentSearchRequest, defaultSearchRequest);
return statisticComputer.computeStatistic();
}
public Statistics getRouteClassStatistic() {
RouteStatisticComputer statisticComputer = new RouteClassStatisticComputer(route, currentRenderer, defaultRenderer, currentSearchRequest, defaultSearchRequest);
return statisticComputer.computeStatistic();
}
public Statistics getRouteSteepnessStatistic(List<Incline> inclines) {
RouteStatisticComputer statisticComputer = new RouteSteepnessStatisticComputer(inclines, currentRenderer, defaultRenderer, currentSearchRequest, defaultSearchRequest);
return statisticComputer.computeStatistic();
}
private abstract static class RouteStatisticComputer<E extends Comparable<E>> {
private final List<RouteSegmentResult> route;
private final StatisticType type;
final RenderingRulesStorage currentRenderer;
final RenderingRulesStorage defaultRenderer;
final RenderingRuleSearchRequest currentRenderingRuleSearchRequest;
final RenderingRuleSearchRequest defaultRenderingRuleSearchRequest;
public RouteStatisticComputer(RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer, List<RouteSegmentResult> route, StatisticType type,
RenderingRuleSearchRequest currentRenderingRuleSearchRequest, RenderingRuleSearchRequest defaultRenderingRuleSearchRequest) {
this.route = route;
this.currentRenderer = currentRenderer;
this.defaultRenderer = defaultRenderer;
this.type = type;
this.currentRenderingRuleSearchRequest = currentRenderingRuleSearchRequest;
this.defaultRenderingRuleSearchRequest = defaultRenderingRuleSearchRequest;
}
protected Map<E, RouteSegmentAttribute<E>> makePartition(List<RouteSegmentAttribute<E>> routeAttributes) {
Map<E, RouteSegmentAttribute<E>> partition = new TreeMap<>();
for (RouteSegmentAttribute<E> attribute : routeAttributes) {
E key = attribute.getAttribute();
RouteSegmentAttribute<E> pattr = partition.get(key);
if (pattr == null) {
pattr = new RouteSegmentAttribute<>(attribute);
partition.put(key, pattr);
}
pattr.incrementDistanceBy(attribute.getDistance());
}
return partition;
}
private float computeTotalDistance(List<RouteSegmentAttribute<E>> attributes) {
float distance = 0f;
for (RouteSegmentAttribute attribute : attributes) {
distance += attribute.getDistance();
}
return distance;
}
protected List<RouteSegmentResult> getRoute() {
return route;
}
protected List<RouteSegmentAttribute<E>> processRoute() {
int index = 0;
List<RouteSegmentAttribute<E>> routes = new ArrayList<>();
E prev = null;
for (RouteSegmentResult segment : getRoute()) {
E current = getAttribute(segment);
if (prev != null && !prev.equals(current)) {
index++;
}
if (index >= routes.size()) {
int color = getColor(current);
String propertyName = getPropertyName(current);
routes.add(new RouteSegmentAttribute<>(index, current, propertyName, color));
}
RouteSegmentAttribute surface = routes.get(index);
surface.incrementDistanceBy(segment.getDistance());
prev = current;
}
return routes;
}
public Statistics<E> computeStatistic() {
List<RouteSegmentAttribute<E>> routeAttributes = processRoute();
Map<E, RouteSegmentAttribute<E>> partition = makePartition(routeAttributes);
float totalDistance = computeTotalDistance(routeAttributes);
return new Statistics<>(routeAttributes, partition, totalDistance, type);
}
RenderingRuleSearchRequest getSearchRequest(boolean useCurrentRenderer) {
return new RenderingRuleSearchRequest(useCurrentRenderer ? currentRenderingRuleSearchRequest : defaultRenderingRuleSearchRequest);
}
public int getColor(E attribute) {
int color = 0;
RenderingRuleSearchRequest currentRequest = getSearchRequest(true);
if (searchRenderingAttribute(currentRenderer, currentRequest, attribute)) {
color = currentRequest.getIntPropertyValue(currentRenderer.PROPS.R_ATTR_COLOR_VALUE);
} else {
RenderingRuleSearchRequest defaultRequest = getSearchRequest(false);
if (searchRenderingAttribute(defaultRenderer, defaultRequest, attribute)) {
color = defaultRequest.getIntPropertyValue(defaultRenderer.PROPS.R_ATTR_COLOR_VALUE);
}
}
return color;
}
public abstract E getAttribute(RouteSegmentResult segment);
public abstract String getPropertyName(E attribute);
protected abstract boolean searchRenderingAttribute(RenderingRulesStorage rrs, RenderingRuleSearchRequest req, E attribute);
}
private static class RouteSurfaceStatisticComputer extends RouteStatisticComputer<String> {
private static final String SURFACE_ATTR = "surface";
private static final String SURFACE_COLOR_ATTR = "surfaceColor";
public RouteSurfaceStatisticComputer(List<RouteSegmentResult> route, RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer, RenderingRuleSearchRequest currentSearchRequest, RenderingRuleSearchRequest defaultSearchRequest) {
super(currentRenderer, defaultRenderer, route, StatisticType.SURFACE, currentSearchRequest, defaultSearchRequest);
}
@Override
public String getAttribute(RouteSegmentResult segment) {
String segmentSurface = segment.getSurface();
if (segmentSurface == null) {
return UNDEFINED_ATTR;
}
RenderingRuleSearchRequest currentRequest = getSearchRequest(true);
if (searchRenderingAttribute(currentRenderer, currentRequest, segmentSurface)) {
return segmentSurface;
} else {
RenderingRuleSearchRequest defaultRequest = getSearchRequest(false);
if (searchRenderingAttribute(defaultRenderer, defaultRequest, segmentSurface)) {
return segmentSurface;
}
}
return UNDEFINED_ATTR;
}
@Override
public String getPropertyName(String attribute) {
if (attribute.equals(UNDEFINED_ATTR)) {
return UNDEFINED_ATTR;
} else {
return SURFACE_ATTR + "_" + attribute;
}
}
@Override
public boolean searchRenderingAttribute(RenderingRulesStorage rrs, RenderingRuleSearchRequest req, String attribute) {
String additional = SURFACE_ATTR + "=" + attribute;
req.setStringFilter(rrs.PROPS.R_ATTR_STRING_VALUE, SURFACE_ATTR + "_" + attribute);
req.setStringFilter(rrs.PROPS.R_ADDITIONAL, additional);
return req.searchRenderingAttribute(SURFACE_COLOR_ATTR);
}
}
private static class RouteSmoothnessStatisticComputer extends RouteStatisticComputer<String> {
private static final String SMOOTHNESS_ATTR = "smoothness";
private static final String SMOOTHNESS_COLOR_ATTR = "smoothnessColor";
public RouteSmoothnessStatisticComputer(List<RouteSegmentResult> route, RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer, RenderingRuleSearchRequest currentSearchRequest, RenderingRuleSearchRequest defaultSearchRequest) {
super(currentRenderer, defaultRenderer, route, StatisticType.SMOOTHNESS, currentSearchRequest, defaultSearchRequest);
}
@Override
public String getAttribute(RouteSegmentResult segment) {
String segmentSmoothness = segment.getSmoothness();
if (segmentSmoothness == null) {
return UNDEFINED_ATTR;
}
RenderingRuleSearchRequest currentRequest = getSearchRequest(true);
if (searchRenderingAttribute(currentRenderer, currentRequest, segmentSmoothness)) {
return segmentSmoothness;
} else {
RenderingRuleSearchRequest defaultRequest = getSearchRequest(false);
if (searchRenderingAttribute(defaultRenderer, defaultRequest, segmentSmoothness)) {
return segmentSmoothness;
}
}
return UNDEFINED_ATTR;
}
@Override
public String getPropertyName(String attribute) {
if (attribute.equals(UNDEFINED_ATTR)) {
return UNDEFINED_ATTR;
} else {
return SMOOTHNESS_ATTR + "_" + attribute;
}
}
@Override
public boolean searchRenderingAttribute(RenderingRulesStorage rrs, RenderingRuleSearchRequest req, String attribute) {
String additional = SMOOTHNESS_ATTR + "=" + attribute;
req.setStringFilter(rrs.PROPS.R_ATTR_STRING_VALUE, SMOOTHNESS_ATTR + "_" + attribute);
req.setStringFilter(rrs.PROPS.R_ADDITIONAL, additional);
return req.searchRenderingAttribute(SMOOTHNESS_COLOR_ATTR);
}
}
private static class RouteClassStatisticComputer extends RouteStatisticComputer<String> {
private static final String HIGHWAY_ATTR = "highway";
private static final String ROAD_CLASS_COLOR_ATTR = "roadClassColor";
public RouteClassStatisticComputer(List<RouteSegmentResult> route, RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer, RenderingRuleSearchRequest currentSearchRequest, RenderingRuleSearchRequest defaultSearchRequest) {
super(currentRenderer, defaultRenderer, route, StatisticType.CLASS, currentSearchRequest, defaultSearchRequest);
}
@Override
public String getAttribute(RouteSegmentResult segment) {
String segmentClass = segment.getHighway();
if (segmentClass == null) {
return UNDEFINED_ATTR;
}
String type = getAttributeType(segmentClass);
return type != null ? type : UNDEFINED_ATTR;
}
@Override
public int getColor(String attribute) {
int color = 0;
RenderingRuleSearchRequest currentRequest = getSearchRequest(true);
if (currentRequest.searchRenderingAttribute(attribute)) {
color = currentRequest.getIntPropertyValue(currentRenderer.PROPS.R_ATTR_COLOR_VALUE);
} else {
RenderingRuleSearchRequest defaultRequest = getSearchRequest(false);
if (defaultRequest.searchRenderingAttribute(attribute)) {
color = defaultRequest.getIntPropertyValue(defaultRenderer.PROPS.R_ATTR_COLOR_VALUE);
}
}
return color;
}
@Override
public String getPropertyName(String attribute) {
String type = getAttributeType(attribute);
return type != null ? type : attribute;
}
@Override
public boolean searchRenderingAttribute(RenderingRulesStorage rrs, RenderingRuleSearchRequest req, String attribute) {
req.setStringFilter(rrs.PROPS.R_TAG, HIGHWAY_ATTR);
req.setStringFilter(rrs.PROPS.R_VALUE, attribute);
return req.searchRenderingAttribute(ROAD_CLASS_COLOR_ATTR);
}
private String getAttributeType(String attribute) {
String type = null;
RenderingRuleSearchRequest currentRequest = getSearchRequest(true);
if (searchRenderingAttribute(currentRenderer, currentRequest, attribute)) {
type = currentRequest.getStringPropertyValue(currentRenderer.PROPS.R_ATTR_STRING_VALUE);
if (currentRequest.searchRenderingAttribute(type)) {
type = currentRequest.getStringPropertyValue(currentRenderer.PROPS.R_ATTR_STRING_VALUE);
}
} else {
RenderingRuleSearchRequest defaultRequest = getSearchRequest(false);
if (searchRenderingAttribute(defaultRenderer, defaultRequest, attribute)) {
type = defaultRequest.getStringPropertyValue(currentRenderer.PROPS.R_ATTR_STRING_VALUE);
if (defaultRequest.searchRenderingAttribute(type)) {
type = defaultRequest.getStringPropertyValue(currentRenderer.PROPS.R_ATTR_STRING_VALUE);
}
}
}
return type;
}
}
private static class RouteSteepnessStatisticComputer extends RouteStatisticComputer<Boundaries> {
private static final String STEEPNESS_ATTR = "steepness";
private static final String STEEPNESS_COLOR_ATTR = "steepnessColor";
private final List<Incline> inclines;
public RouteSteepnessStatisticComputer(List<Incline> inclines, RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer, RenderingRuleSearchRequest currentSearchRequest, RenderingRuleSearchRequest defaultSearchRequest) {
super(currentRenderer, defaultRenderer, null, StatisticType.STEEPNESS, currentSearchRequest, defaultSearchRequest);
this.inclines = inclines;
}
@Override
public List<RouteSegmentAttribute<Boundaries>> processRoute() {
List<RouteSegmentAttribute<Boundaries>> routeInclines = new ArrayList<>();
int index = 0;
Boundaries prev = null;
Incline prevIncline = null;
for (Incline incline : inclines) {
Boundaries current = incline.getBoundaries();
if (prev != null && !prev.equals(current)) {
index++;
}
if (index >= routeInclines.size()) {
String propertyName = getPropertyName(current);
int color = getColor(current);
RouteSegmentAttribute<Boundaries> attribute = new RouteSegmentAttribute<>(index, current, propertyName, color);
if (prevIncline != null) {
attribute.setInitDistance(prevIncline.getDistance());
}
routeInclines.add(attribute);
}
RouteSegmentAttribute routeIncline = routeInclines.get(index);
routeIncline.relativeSum(incline.getDistance());
prev = current;
prevIncline = incline;
}
return routeInclines;
}
@Override
public Boundaries getAttribute(RouteSegmentResult segment) {
/*
no-op
*/
return null;
}
@Override
public String getPropertyName(Boundaries attribute) {
int lowerBoundary = Math.round(attribute.getLowerBoundary());
int upperBoundary = Math.round(attribute.getUpperBoundary());
if (lowerBoundary >= Boundaries.MIN_DIVIDED_INCLINE) {
lowerBoundary++;
}
return String.format("%d%% ... %d%%", lowerBoundary, upperBoundary);
}
@Override
public boolean searchRenderingAttribute(RenderingRulesStorage rrs, RenderingRuleSearchRequest req, Boundaries attribute) {
int lowerBoundary = Math.round(attribute.getLowerBoundary());
int upperBoundary = Math.round(attribute.getUpperBoundary());
StringBuilder range = new StringBuilder();
if (lowerBoundary >= Boundaries.MIN_DIVIDED_INCLINE) {
lowerBoundary++;
} else {
lowerBoundary = Boundaries.MIN_INCLINE;
}
if (upperBoundary > Boundaries.MAX_DIVIDED_INCLINE) {
upperBoundary = Boundaries.MAX_INCLINE;
}
range.append(lowerBoundary);
range.append(upperBoundary < 0 ? "_" : "-");
range.append(upperBoundary);
String additional = STEEPNESS_ATTR + "=" + range;
req.setStringFilter(rrs.PROPS.R_ADDITIONAL, additional);
return req.searchRenderingAttribute(STEEPNESS_COLOR_ATTR);
}
}
public static class RouteSegmentAttribute<E> {
private final int index;
private final E attribute;
private final int color;
private final String propertyName;
private float distance;
private float initDistance;
public RouteSegmentAttribute(int index, E attribute, String propertyName, int color) {
this.index = index;
this.attribute = attribute;
this.propertyName = propertyName;
this.color = color;
}
public RouteSegmentAttribute(RouteSegmentAttribute<E> segmentAttribute) {
this.index = segmentAttribute.getIndex();
this.attribute = segmentAttribute.getAttribute();
this.propertyName = segmentAttribute.getPropertyName();
this.color = segmentAttribute.getColor();
}
public int getIndex() {
return index;
}
public E getAttribute() {
return attribute;
}
public float getDistance() {
return distance;
}
public void setInitDistance(float initDistance) {
this.initDistance = initDistance;
}
public void incrementDistanceBy(float distance) {
this.distance += distance;
}
public void relativeSum(float distance) {
this.distance = this.distance + ((distance - this.initDistance) - this.distance);
}
public String getPropertyName() {
return propertyName;
}
public int getColor() {
return color;
}
@Override
public String toString() {
return "RouteSegmentAttribute{" +
"index=" + index +
", attribute='" + attribute + '\'' +
", color='" + color + '\'' +
", distance=" + distance +
'}';
}
}
public static class Incline {
private final float inclineValue;
private final float distance;
private Boundaries boundaries;
public Incline(float inclineValue, float distance) {
this.inclineValue = inclineValue;
this.distance = distance;
}
public void computeBoundaries(float minIncline, float maxIncline) {
this.boundaries = Boundaries.newBoundariesFor(inclineValue, minIncline, maxIncline);
}
public float getValue() {
return inclineValue;
}
public float getDistance() {
return distance;
}
public Boundaries getBoundaries() {
return this.boundaries;
}
@Override
public String toString() {
return "Incline{" +
", incline=" + inclineValue +
", distance=" + distance +
'}';
}
}
public static class Boundaries implements Comparable<Boundaries> {
private static final int MIN_INCLINE = -100;
private static final int MIN_DIVIDED_INCLINE = -20;
private static final int MAX_INCLINE = 100;
private static final int MAX_DIVIDED_INCLINE = 20;
private static final int STEP = 4;
private static final int NUM;
private static final int[] BOUNDARIES_ARRAY;
static {
NUM = ((MAX_DIVIDED_INCLINE - MIN_DIVIDED_INCLINE) / STEP) + 3;
BOUNDARIES_ARRAY = new int[NUM];
BOUNDARIES_ARRAY[0] = MIN_INCLINE;
for (int i = 1; i < NUM - 1; i++) {
BOUNDARIES_ARRAY[i] = MIN_DIVIDED_INCLINE + (i - 1) * STEP;
}
BOUNDARIES_ARRAY[NUM - 1] = MAX_INCLINE;
}
private final float upperBoundary;
private final float lowerBoundary;
private Boundaries(float upperBoundary, float lowerBoundary) {
this.upperBoundary = upperBoundary;
this.lowerBoundary = lowerBoundary;
}
public static Boundaries newBoundariesFor(float incline, float minIncline, float maxIncline) {
int maxRoundedIncline = Math.round(maxIncline);
int minRoundedIncline = Math.round(minIncline);
if (incline > MAX_INCLINE) {
return new Boundaries(MAX_INCLINE, MAX_DIVIDED_INCLINE);
}
if (incline < MIN_INCLINE) {
return new Boundaries(MIN_DIVIDED_INCLINE, MIN_INCLINE);
}
for (int i = 1; i < NUM; i++) {
if (incline >= BOUNDARIES_ARRAY[i - 1] && incline < BOUNDARIES_ARRAY[i]) {
if (i == 1) {
return new Boundaries(BOUNDARIES_ARRAY[i], minRoundedIncline);
} else if (i == NUM - 1) {
return new Boundaries(maxRoundedIncline, BOUNDARIES_ARRAY[i - 1]);
} else {
return new Boundaries(BOUNDARIES_ARRAY[i], BOUNDARIES_ARRAY[i - 1]);
}
}
}
return null;
}
public float getUpperBoundary() {
return upperBoundary;
}
public float getLowerBoundary() {
return lowerBoundary;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Boundaries that = (Boundaries) o;
if (Float.compare(that.upperBoundary, upperBoundary) != 0) return false;
return Float.compare(that.lowerBoundary, lowerBoundary) == 0;
}
@Override
public int hashCode() {
int result = (upperBoundary != +0.0f ? Float.floatToIntBits(upperBoundary) : 0);
result = 31 * result + (lowerBoundary != +0.0f ? Float.floatToIntBits(lowerBoundary) : 0);
return result;
}
@Override
public int compareTo(Boundaries boundaries) {
return (int) (getLowerBoundary() - boundaries.getLowerBoundary());
}
@Override
public String toString() {
return String.format("%d%% ... %d%%", Math.round(getLowerBoundary()), Math.round(getUpperBoundary()));
}
}
public static class Statistics<E> {
private final List<RouteSegmentAttribute<E>> elements;
private final Map<E, RouteSegmentAttribute<E>> partition;
private final float totalDistance;
private final StatisticType type;
private Statistics(List<RouteSegmentAttribute<E>> elements,
Map<E, RouteSegmentAttribute<E>> partition,
float totalDistance, StatisticType type) {
this.elements = elements;
this.partition = partition;
this.totalDistance = totalDistance;
this.type = type;
}
public float getTotalDistance() {
return totalDistance;
}
public List<RouteSegmentAttribute<E>> getElements() {
return elements;
}
public Map<E, RouteSegmentAttribute<E>> getPartition() {
return partition;
}
public StatisticType getStatisticType() {
return type;
}
}
public enum StatisticType {
CLASS,
SURFACE,
SMOOTHNESS,
STEEPNESS
}
}

View file

@ -0,0 +1,435 @@
package net.osmand.router;
import net.osmand.binary.BinaryMapRouteReaderAdapter;
import net.osmand.binary.RouteDataObject;
import net.osmand.render.RenderingRuleSearchRequest;
import net.osmand.render.RenderingRulesStorage;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;
public class RouteStatisticsHelper {
public static final String UNDEFINED_ATTR = "undefined";
public static final String ROUTE_INFO_PREFIX = "routeInfo_";
private static final double H_STEP = 5;
private static final double H_SLOPE_APPROX = 100;
private static final int MIN_INCLINE = -101;
private static final int MIN_DIVIDED_INCLINE = -20;
private static final int MAX_INCLINE = 100;
private static final int MAX_DIVIDED_INCLINE = 20;
private static final int STEP = 4;
private static final int[] BOUNDARIES_ARRAY;
private static final String[] BOUNDARIES_CLASS;
static {
int NUM = ((MAX_DIVIDED_INCLINE - MIN_DIVIDED_INCLINE) / STEP) + 3;
BOUNDARIES_ARRAY = new int[NUM];
BOUNDARIES_CLASS = new String[NUM];
BOUNDARIES_ARRAY[0] = MIN_INCLINE;
BOUNDARIES_CLASS[0] = "steepness=" + (MIN_INCLINE + 1) + "_" + MIN_DIVIDED_INCLINE;
for (int i = 1; i < NUM - 1; i++) {
BOUNDARIES_ARRAY[i] = MIN_DIVIDED_INCLINE + (i - 1) * STEP;
BOUNDARIES_CLASS[i] = "steepness=" + (BOUNDARIES_ARRAY[i - 1] + 1) + "_" + BOUNDARIES_ARRAY[i];
}
BOUNDARIES_ARRAY[NUM - 1] = MAX_INCLINE;
BOUNDARIES_CLASS[NUM - 1] = "steepness="+MAX_DIVIDED_INCLINE+"_"+MAX_INCLINE;
}
public static class RouteStatistics {
public final List<RouteSegmentAttribute> elements;
public final Map<String, RouteSegmentAttribute> partition;
public final float totalDistance;
public final String name;
private RouteStatistics(String name, List<RouteSegmentAttribute> elements,
Map<String, RouteSegmentAttribute> partition,
float totalDistance) {
this.name = name.startsWith(ROUTE_INFO_PREFIX) ? name.substring(ROUTE_INFO_PREFIX.length()) : name;
this.elements = elements;
this.partition = partition;
this.totalDistance = totalDistance;
}
@Override
public String toString() {
StringBuilder s = new StringBuilder("Statistic '").append(name).append("':");
for (RouteSegmentAttribute a : elements) {
s.append(String.format(" %.0fm %s,", a.distance, a.getUserPropertyName()));
}
s.append("\n Partition: ").append(partition);
return s.toString();
}
}
private static class RouteSegmentWithIncline {
RouteDataObject obj;
float dist;
float h;
float[] interpolatedHeightByStep;
float[] slopeByStep;
String[] slopeClassUserString;
int[] slopeClass;
}
public static List<RouteStatistics> calculateRouteStatistic(List<RouteSegmentResult> route, RenderingRulesStorage currentRenderer,
RenderingRulesStorage defaultRenderer, RenderingRuleSearchRequest currentSearchRequest,
RenderingRuleSearchRequest defaultSearchRequest) {
List<RouteSegmentWithIncline> routeSegmentWithInclines = calculateInclineRouteSegments(route);
List<String> attributeNames = new ArrayList<>();
if (currentRenderer != null) {
for (String s : currentRenderer.getRenderingAttributeNames()) {
if (s.startsWith(ROUTE_INFO_PREFIX)) {
attributeNames.add(s);
}
}
}
if(attributeNames.isEmpty()) {
for (String s : defaultRenderer.getRenderingAttributeNames()) {
if (s.startsWith(ROUTE_INFO_PREFIX)) {
attributeNames.add(s);
}
}
}
// "steepnessColor", "surfaceColor", "roadClassColor", "smoothnessColor"
// steepness=-19_-16
List<RouteStatistics> result = new ArrayList<>();
for(String attributeName : attributeNames) {
RouteStatisticComputer statisticComputer =
new RouteStatisticComputer(currentRenderer, defaultRenderer, currentSearchRequest, defaultSearchRequest);
RouteStatistics routeStatistics = statisticComputer.computeStatistic(routeSegmentWithInclines, attributeName);
if (!routeStatistics.partition.isEmpty() && (routeStatistics.partition.size() != 1 || !routeStatistics.partition.containsKey(UNDEFINED_ATTR))) {
result.add(routeStatistics);
}
}
return result;
}
private static List<RouteSegmentWithIncline> calculateInclineRouteSegments(List<RouteSegmentResult> route) {
List<RouteSegmentWithIncline> input = new ArrayList<>();
float prevHeight = 0;
int totalArrayHeightsLength = 0;
for(RouteSegmentResult r : route) {
float[] heightValues = r.getHeightValues();
RouteSegmentWithIncline incl = new RouteSegmentWithIncline();
incl.dist = r.getDistance();
incl.obj = r.getObject();
input.add(incl);
float prevH = prevHeight;
int indStep = 0;
if(incl.dist > H_STEP) {
// for 10.1 meters 3 points (0, 5, 10)
incl.interpolatedHeightByStep = new float[(int) ((incl.dist) / H_STEP) + 1];
totalArrayHeightsLength += incl.interpolatedHeightByStep.length;
}
if(heightValues != null && heightValues.length > 0) {
int indH = 2;
float distCum = 0;
prevH = heightValues[1];
incl.h = prevH ;
if(incl.interpolatedHeightByStep != null && incl.interpolatedHeightByStep.length > indStep) {
incl.interpolatedHeightByStep[indStep++] = prevH;
}
while(incl.interpolatedHeightByStep != null &&
indStep < incl.interpolatedHeightByStep.length && indH < heightValues.length) {
float dist = heightValues[indH] + distCum;
if(dist > indStep * H_STEP) {
if(dist == distCum) {
incl.interpolatedHeightByStep[indStep] = prevH;
} else {
incl.interpolatedHeightByStep[indStep] = (float) (prevH +
(indStep * H_STEP - distCum) *
(heightValues[indH + 1] - prevH) / (dist - distCum));
}
indStep++;
} else {
distCum = dist;
prevH = heightValues[indH + 1];
indH += 2;
}
}
} else {
incl.h = prevH;
}
while(incl.interpolatedHeightByStep != null &&
indStep < incl.interpolatedHeightByStep.length) {
incl.interpolatedHeightByStep[indStep++] = prevH;
}
prevHeight = prevH;
}
int slopeSmoothShift = (int) (H_SLOPE_APPROX / (2 * H_STEP));
float[] heightArray = new float[totalArrayHeightsLength];
int iter = 0;
for(int i = 0; i < input.size(); i ++) {
RouteSegmentWithIncline rswi = input.get(i);
for(int k = 0; rswi.interpolatedHeightByStep != null &&
k < rswi.interpolatedHeightByStep.length; k++) {
heightArray[iter++] = rswi.interpolatedHeightByStep[k];
}
}
iter = 0;
int minSlope = Integer.MAX_VALUE;
int maxSlope = Integer.MIN_VALUE;
for(int i = 0; i < input.size(); i ++) {
RouteSegmentWithIncline rswi = input.get(i);
if(rswi.interpolatedHeightByStep != null) {
rswi.slopeByStep = new float[rswi.interpolatedHeightByStep.length];
for (int k = 0; k < rswi.slopeByStep.length; k++) {
if (iter > slopeSmoothShift && iter + slopeSmoothShift < heightArray.length) {
double slope = (heightArray[iter + slopeSmoothShift] - heightArray[iter - slopeSmoothShift]) * 100
/ H_SLOPE_APPROX;
rswi.slopeByStep[k] = (float) slope;
minSlope = Math.min((int) slope, minSlope);
maxSlope = Math.max((int) slope, maxSlope);
}
iter++;
}
}
}
String[] classFormattedStrings = new String[BOUNDARIES_ARRAY.length];
classFormattedStrings[0] = formatSlopeString(minSlope, MIN_DIVIDED_INCLINE);
classFormattedStrings[1] = formatSlopeString(minSlope, MIN_DIVIDED_INCLINE);
classFormattedStrings[BOUNDARIES_ARRAY.length - 1] = formatSlopeString(MAX_DIVIDED_INCLINE, maxSlope);
for (int k = 2; k < BOUNDARIES_ARRAY.length - 1; k++) {
classFormattedStrings[k] = formatSlopeString(BOUNDARIES_ARRAY[k - 1], BOUNDARIES_ARRAY[k]);
}
for(int i = 0; i < input.size(); i ++) {
RouteSegmentWithIncline rswi = input.get(i);
if(rswi.slopeByStep != null) {
rswi.slopeClass = new int[rswi.slopeByStep.length];
rswi.slopeClassUserString = new String[rswi.slopeByStep.length];
for (int t = 0; t < rswi.slopeClass.length; t++) {
for (int k = 0; k < BOUNDARIES_ARRAY.length; k++) {
if (rswi.slopeByStep[t] <= BOUNDARIES_ARRAY[k] || k == BOUNDARIES_ARRAY.length - 1) {
rswi.slopeClass[t] = k;
rswi.slopeClassUserString[t] = classFormattedStrings[k];
break;
}
}
// end of break
}
}
}
return input;
}
private static String formatSlopeString(int slope, int next) {
return String.format("%d%% .. %d%%", slope, next);
}
private static class RouteStatisticComputer {
final RenderingRulesStorage currentRenderer;
final RenderingRulesStorage defaultRenderer;
final RenderingRuleSearchRequest currentRenderingRuleSearchRequest;
final RenderingRuleSearchRequest defaultRenderingRuleSearchRequest;
RouteStatisticComputer(RenderingRulesStorage currentRenderer, RenderingRulesStorage defaultRenderer,
RenderingRuleSearchRequest currentRenderingRuleSearchRequest, RenderingRuleSearchRequest defaultRenderingRuleSearchRequest) {
this.currentRenderer = currentRenderer;
this.defaultRenderer = defaultRenderer;
this.currentRenderingRuleSearchRequest = currentRenderingRuleSearchRequest;
this.defaultRenderingRuleSearchRequest = defaultRenderingRuleSearchRequest;
}
public RouteStatistics computeStatistic(List<RouteSegmentWithIncline> route, String attribute) {
List<RouteSegmentAttribute> routeAttributes = processRoute(route, attribute);
Map<String, RouteSegmentAttribute> partition = makePartition(routeAttributes);
float totalDistance = computeTotalDistance(routeAttributes);
return new RouteStatistics(attribute, routeAttributes, partition, totalDistance);
}
Map<String, RouteSegmentAttribute> makePartition(List<RouteSegmentAttribute> routeAttributes) {
final Map<String, RouteSegmentAttribute> partition = new TreeMap<>();
for (RouteSegmentAttribute attribute : routeAttributes) {
RouteSegmentAttribute attr = partition.get(attribute.getUserPropertyName());
if (attr == null) {
attr = new RouteSegmentAttribute(attribute);
partition.put(attribute.getUserPropertyName(), attr);
}
attr.incrementDistanceBy(attribute.getDistance());
}
List<String> keys = new ArrayList<String>(partition.keySet());
Collections.sort(keys, new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
if (o1.equalsIgnoreCase(UNDEFINED_ATTR)) {
return 1;
}
if (o2.equalsIgnoreCase(UNDEFINED_ATTR)) {
return -1;
}
int cmp = Integer.compare(partition.get(o1).slopeIndex, partition.get(o2).slopeIndex);
if(cmp != 0) {
return cmp;
}
return -Float.compare(partition.get(o1).getDistance(), partition.get(o2).getDistance());
}
});
Map<String, RouteSegmentAttribute> sorted = new LinkedHashMap<String, RouteStatisticsHelper.RouteSegmentAttribute>();
for (String k : keys) {
sorted.put(k, partition.get(k));
}
return sorted;
}
private float computeTotalDistance(List<RouteSegmentAttribute> attributes) {
float distance = 0f;
for (RouteSegmentAttribute attribute : attributes) {
distance += attribute.getDistance();
}
return distance;
}
protected List<RouteSegmentAttribute> processRoute(List<RouteSegmentWithIncline> route, String attribute) {
List<RouteSegmentAttribute> routes = new ArrayList<>();
RouteSegmentAttribute prev = null;
for (RouteSegmentWithIncline segment : route) {
if(segment.slopeClass == null || segment.slopeClass.length == 0) {
RouteSegmentAttribute current = classifySegment(attribute, -1, segment);
current.distance = segment.dist;
if (prev != null && prev.getPropertyName() != null &&
prev.getPropertyName().equals(current.getPropertyName())) {
prev.incrementDistanceBy(current.distance);
} else {
routes.add(current);
prev = current;
}
} else {
for(int i = 0; i < segment.slopeClass.length; i++) {
float d = (float) (i == 0 ? (segment.dist - H_STEP * (segment.slopeClass.length - 1)) : H_STEP);
if(i > 0 && segment.slopeClass[i] == segment.slopeClass[i-1]) {
prev.incrementDistanceBy(d);
} else {
RouteSegmentAttribute current = classifySegment(attribute,
segment.slopeClass[i], segment);
current.distance = d;
if (prev != null && prev.getPropertyName() != null &&
prev.getPropertyName().equals(current.getPropertyName())) {
prev.incrementDistanceBy(current.distance);
} else {
if(current.slopeIndex == segment.slopeClass[i]) {
current.setUserPropertyName(segment.slopeClassUserString[i]);
}
routes.add(current);
prev = current;
}
}
}
}
}
return routes;
}
public RouteSegmentAttribute classifySegment(String attribute, int slopeClass, RouteSegmentWithIncline segment) {
RouteSegmentAttribute res = new RouteSegmentAttribute(UNDEFINED_ATTR, 0, -1);
RenderingRuleSearchRequest currentRequest =
currentRenderer == null ? null : new RenderingRuleSearchRequest(currentRenderingRuleSearchRequest);
if (currentRenderer != null && searchRenderingAttribute(attribute, currentRenderer, currentRequest, segment, slopeClass)) {
res = new RouteSegmentAttribute(currentRequest.getStringPropertyValue(currentRenderer.PROPS.R_ATTR_STRING_VALUE),
currentRequest.getIntPropertyValue(currentRenderer.PROPS.R_ATTR_COLOR_VALUE), slopeClass);
} else {
RenderingRuleSearchRequest defaultRequest = new RenderingRuleSearchRequest(defaultRenderingRuleSearchRequest);
if (searchRenderingAttribute(attribute, defaultRenderer, defaultRequest, segment, slopeClass)) {
res = new RouteSegmentAttribute(
defaultRequest.getStringPropertyValue(defaultRenderer.PROPS.R_ATTR_STRING_VALUE),
defaultRequest.getIntPropertyValue(defaultRenderer.PROPS.R_ATTR_COLOR_VALUE), slopeClass);
}
}
return res;
}
protected boolean searchRenderingAttribute(String attribute,
RenderingRulesStorage rrs, RenderingRuleSearchRequest req, RouteSegmentWithIncline segment,
int slopeClass) {
//String additional = attrName + "=" + attribute;
RouteDataObject obj = segment.obj;
int[] tps = obj.getTypes();
String additional = slopeClass >= 0 ? (BOUNDARIES_CLASS[slopeClass] + ";") : "";
for (int k = 0; k < tps.length; k++) {
BinaryMapRouteReaderAdapter.RouteTypeRule tp = obj.region.quickGetEncodingRule(tps[k]);
if (tp.getTag().equals("highway") || tp.getTag().equals("route") ||
tp.getTag().equals("railway") || tp.getTag().equals("aeroway") || tp.getTag().equals("aerialway")) {
req.setStringFilter(rrs.PROPS.R_TAG, tp.getTag());
req.setStringFilter(rrs.PROPS.R_VALUE, tp.getValue());
} else {
additional += tp.getTag() + "=" + tp.getValue() + ";";
}
}
req.setStringFilter(rrs.PROPS.R_ADDITIONAL, additional);
return req.searchRenderingAttribute(attribute);
}
}
public static class RouteSegmentAttribute {
private final int color;
private final String propertyName;
private final int slopeIndex;
private float distance;
private String userPropertyName;
RouteSegmentAttribute(String propertyName, int color, int slopeIndex) {
this.propertyName = propertyName == null ? UNDEFINED_ATTR : propertyName;
this.slopeIndex = slopeIndex >= 0 && BOUNDARIES_CLASS[slopeIndex].endsWith(this.propertyName) ? slopeIndex : -1;
this.color = color;
}
RouteSegmentAttribute(RouteSegmentAttribute segmentAttribute) {
this.propertyName = segmentAttribute.getPropertyName();
this.color = segmentAttribute.getColor();
this.slopeIndex = segmentAttribute.slopeIndex;
this.userPropertyName = segmentAttribute.userPropertyName;
}
public String getUserPropertyName() {
return userPropertyName == null ? propertyName : userPropertyName;
}
public void setUserPropertyName(String userPropertyName) {
this.userPropertyName = userPropertyName;
}
public float getDistance() {
return distance;
}
public void incrementDistanceBy(float distance) {
this.distance += distance;
}
public String getPropertyName() {
return propertyName;
}
public int getColor() {
return color;
}
@Override
public String toString() {
return String.format("%s - %.0f m %d", getUserPropertyName(), getDistance(), getColor());
}
}
}

View file

@ -28,7 +28,7 @@
android:textSize="@dimen/default_list_text_size"
osmand:typeface="@string/font_roboto_medium"
tools:ignore="UnusedAttribute"
tools:text="@string/route_class_stat_container" />
tools:text="@string/routeInfo_roadClass_name" />
<LinearLayout
android:id="@+id/info_type_details_button"

View file

@ -2834,17 +2834,17 @@
<string name="download_wikipedia_description">تحميل المواد ويكيبيديا عن %1$s لقراءتها دون اتصال.</string>
<string name="wiki_article_search_text">البحث عن مقالة ويكي المقابلة</string>
<string name="test_voice_desrc">اضغط على الزر للاستماع إلى موجه صوتية التالية لتحديد مطالبات مفقودة أو بها خلل.</string>
<string name="route_class_stat_container">الفئة</string>
<string name="route_surface_stat_container">السطح</string>
<string name="route_smoothness_stat_container">السلاسة</string>
<string name="route_steepness_stat_container">الوعورة</string>
<string name="routeInfo_roadClass_name">الفئة</string>
<string name="routeInfo_surface_name">السطح</string>
<string name="routeInfo_smoothness_name">السلاسة</string>
<string name="routeInfo_steepness_name">الوعورة</string>
<string name="run_full_osmand_msg">كنت تستخدم {0} الخريطة وهي مدعومة من osmand.هل تريد من osmand إطلاق النسخة الكاملة؟</string>
<string name="run_full_osmand_header">تشغيل osmand؟</string>
<string name="swap_start_and_destination">تبديل البداية والوجهة</string>
<string name="time_of_day">الوقت من اليوم</string>
<string name="by_transport_type">بواسطة %1$s</string>
<string name="step_by_step">خطوة بخطوة</string>
<string name="road_types">أنواع الطرق</string>
<string name="routeInfo_road_types_name">أنواع الطرق</string>
<string name="exit_at">خروج عند</string>
<string name="sit_on_the_stop">ابقى عند لوحة التوقف</string>
<string name="shared_string_swap">تبديل</string>

View file

@ -1372,7 +1372,7 @@
<string name="route_tsll">Xira llixeramente a la esquierda y sigui per</string>
<string name="route_head">De frente</string>
<string name="app_mode_pedestrian">Andadura</string>
<string name="route_surface_stat_container">Superficie</string>
<string name="routeInfo_surface_name">Superficie</string>
<string name="angular_measeurement">Unidaes de midida angular</string>
<string name="angular_measeurement_descr">Camuda en qué se mide l\'acimut.</string>
<string name="previous_route">Ruta anterior</string>

View file

@ -2901,7 +2901,7 @@ Praparcyjnaj pamiacі %4$s MB (Abmiežavańnie Android %5$s MB, Dalvik %6$s MB).
<string name="time_of_day">Čas sutak</string>
<string name="by_transport_type">Užyta %1$s</string>
<string name="step_by_step">Krok za krokam</string>
<string name="road_types">Typy daroh</string>
<string name="routeInfo_road_types_name">Typy daroh</string>
<string name="exit_at">Vychad na</string>
<string name="sit_on_the_stop">Pasadka na prypynku</string>
<string name="shared_string_swap">Pamianiać</string>
@ -2916,10 +2916,10 @@ Praparcyjnaj pamiacі %4$s MB (Abmiežavańnie Android %5$s MB, Dalvik %6$s MB).
<string name="add_home">Dadać dom</string>
<string name="add_work">Dadać pracu</string>
<string name="work_button">Praca</string>
<string name="route_class_stat_container">Klas</string>
<string name="route_surface_stat_container">Pavierchnia</string>
<string name="route_smoothness_stat_container">Hladkasć</string>
<string name="route_steepness_stat_container">Pakatasć</string>
<string name="routeInfo_roadClass_name">Klas</string>
<string name="routeInfo_surface_name">Pavierchnia</string>
<string name="routeInfo_smoothness_name">Hladkasć</string>
<string name="routeInfo_steepness_name">Pakatasć</string>
<string name="release_3_3">• Novy ekran «Napramki»: adliustroŭvaje knopki napramkaŭ dachaty i na pracu, skarot «papiaredni maršrut», spis aktyŭnych GPX-sliadoŭ i adznak, historyju pošuku
\n
\n • Dadatkovyja zviestki pad «Detali maršrutu»: typy daroh, pakryccio, pakatasć, hladkasć

View file

@ -2905,10 +2905,10 @@
<string name="quick_action_switch_day_mode">Дзённы рэжым</string>
<string name="quick_action_switch_night_mode">Начны рэжым</string>
<string name="quick_action_day_night_switch_mode">Пераключыць дзённы/начны рэжым</string>
<string name="route_class_stat_container">Клас</string>
<string name="route_surface_stat_container">Паверхня</string>
<string name="route_smoothness_stat_container">Гладкасць</string>
<string name="route_steepness_stat_container">Пакатасць</string>
<string name="routeInfo_roadClass_name">Клас</string>
<string name="routeInfo_surface_name">Паверхня</string>
<string name="routeInfo_smoothness_name">Гладкасць</string>
<string name="routeInfo_steepness_name">Пакатасць</string>
<string name="add_destination_query">Спачатку дадайце пункт прызначэння</string>
<string name="previous_route">Папярэдні маршрут</string>
<string name="add_home">Дадаць дом</string>
@ -2917,7 +2917,7 @@
<string name="time_of_day">Час сутак</string>
<string name="by_transport_type">Ужыта %1$s</string>
<string name="step_by_step">Крок за крокам</string>
<string name="road_types">Тыпы дарог</string>
<string name="routeInfo_road_types_name">Тыпы дарог</string>
<string name="exit_at">Выхад на</string>
<string name="sit_on_the_stop">Пасадка на прыпынку</string>
<string name="shared_string_swap">Памяняць</string>

View file

@ -2920,10 +2920,10 @@ Abasta l\'àrea: %1$s x %2$s</string>
<string name="shared_string_capacity">Capacitat</string>
<string name="shared_string_width">Amplada</string>
<string name="shared_string_height">Alçada</string>
<string name="route_class_stat_container">Classe</string>
<string name="route_surface_stat_container">Superfície</string>
<string name="route_smoothness_stat_container">Uniformitat</string>
<string name="route_steepness_stat_container">Pendent</string>
<string name="routeInfo_roadClass_name">Classe</string>
<string name="routeInfo_surface_name">Superfície</string>
<string name="routeInfo_smoothness_name">Uniformitat</string>
<string name="routeInfo_steepness_name">Pendent</string>
<string name="add_home">Afegeix casa meva</string>
<string name="add_work">Afegeix feina</string>
<string name="work_button">Feina</string>
@ -2935,7 +2935,7 @@ Abasta l\'àrea: %1$s x %2$s</string>
<string name="time_of_day">Hora del dia</string>
<string name="by_transport_type">Per %1$s</string>
<string name="step_by_step">Pas a pas</string>
<string name="road_types">Tipus de carretera</string>
<string name="routeInfo_road_types_name">Tipus de carretera</string>
<string name="exit_at">Sortida a</string>
<string name="quick_action_show_hide_gpx_tracks">"Mostra/amaga traces GPX "</string>
<string name="quick_action_show_hide_gpx_tracks_descr">Prement aquest botó d\'acció es mostren o s\'amaguen al mapa les traces GPX</string>

View file

@ -2884,15 +2884,15 @@ Zobrazená oblast: %1$s x %2$s</string>
<string name="add_home">Přidat domov</string>
<string name="add_work">Přidat práci</string>
<string name="work_button">Práce</string>
<string name="route_class_stat_container">Třída</string>
<string name="route_surface_stat_container">Povrch</string>
<string name="route_smoothness_stat_container">Hladkost povrchu</string>
<string name="route_steepness_stat_container">Strmost</string>
<string name="routeInfo_roadClass_name">Třída</string>
<string name="routeInfo_surface_name">Povrch</string>
<string name="routeInfo_smoothness_name">Hladkost povrchu</string>
<string name="routeInfo_steepness_name">Strmost</string>
<string name="show_more">Ukaž více</string>
<string name="tracks_on_map">Zobrazené trasy</string>
<string name="time_of_day">Denní doba</string>
<string name="step_by_step">Krok za krokem</string>
<string name="road_types">Typy silnic</string>
<string name="routeInfo_road_types_name">Typy silnic</string>
<string name="exit_at">Výjezd na</string>
<string name="shared_string_swap">Vyměnit</string>
<string name="quick_action_show_hide_gpx_tracks">Zobrazit/skrýt GPX trasy</string>

View file

@ -2907,10 +2907,10 @@ Repræsenterer område: %1$s x %2$s</string>
<string name="voice_announcements">Stemmemeddelelser</string>
<string name="arrive_at_time">Ankommer %1$s</string>
<string name="quick_action_switch_day_night_descr">Tryk på handlingsknappen skifter mellem dag- og nattilstand</string>
<string name="route_class_stat_container">Klasse</string>
<string name="route_surface_stat_container">Overflade</string>
<string name="route_smoothness_stat_container">Jævnhed</string>
<string name="route_steepness_stat_container">Stejlhed</string>
<string name="routeInfo_roadClass_name">Klasse</string>
<string name="routeInfo_surface_name">Overflade</string>
<string name="routeInfo_smoothness_name">Jævnhed</string>
<string name="routeInfo_steepness_name">Stejlhed</string>
<string name="run_full_osmand_msg">Der bruges {0} kort leveret af OsmAnd. Start den fulde version\?</string>
<string name="shared_string_swap">Byt rundt</string>
<string name="show_more">Vis mere</string>
@ -2922,7 +2922,7 @@ Repræsenterer område: %1$s x %2$s</string>
<string name="time_of_day">Tidspunkt på dagen</string>
<string name="by_transport_type">Med %1$s</string>
<string name="step_by_step">Trin for trin</string>
<string name="road_types">Vejtyper</string>
<string name="routeInfo_road_types_name">Vejtyper</string>
<string name="exit_at">Stå af ved</string>
<string name="sit_on_the_stop">Stig på ved stoppested</string>
<string name="quick_action_show_hide_gpx_tracks">Vis/skjul GPX spor</string>

View file

@ -2910,10 +2910,10 @@ Abgedeckte Fläche: %1$s x %2$s</string>
<string name="shared_string_capacity">Kapazität</string>
<string name="shared_string_width">Breite</string>
<string name="shared_string_height">Höhe</string>
<string name="route_class_stat_container">Typ</string>
<string name="route_surface_stat_container">Oberfläche</string>
<string name="route_smoothness_stat_container">Oberflächenbeschaffenheit</string>
<string name="route_steepness_stat_container">Steilheit</string>
<string name="routeInfo_roadClass_name">Typ</string>
<string name="routeInfo_surface_name">Oberfläche</string>
<string name="routeInfo_smoothness_name">Oberflächenbeschaffenheit</string>
<string name="routeInfo_steepness_name">Steilheit</string>
<string name="add_home">Zuhause hinzufügen</string>
<string name="add_work">Arbeitsadresse hinzufügen</string>
<string name="work_button">Arbeit</string>
@ -2925,7 +2925,7 @@ Abgedeckte Fläche: %1$s x %2$s</string>
<string name="time_of_day">Tageszeit</string>
<string name="by_transport_type">Von %1$s</string>
<string name="step_by_step">Schritt für Schritt</string>
<string name="road_types">Straßentypen</string>
<string name="routeInfo_road_types_name">Straßentypen</string>
<string name="quick_action_show_hide_gpx_tracks">GPX-Tracks ein-/ausblenden</string>
<string name="quick_action_show_hide_gpx_tracks_descr">Dücken dieser Aktionstaste blendet ausgewählte GPX-Tracks auf der Karte ein oder aus</string>
<string name="quick_action_gpx_tracks_hide">GPX-Tracks ausblenden</string>

View file

@ -2985,7 +2985,7 @@
<string name="time_of_day">Ώρα της ημέρας</string>
<string name="by_transport_type">Κατά %1$s</string>
<string name="step_by_step">Βήμα-βήμα</string>
<string name="road_types">Τύποι δρόμων</string>
<string name="routeInfo_road_types_name">Τύποι δρόμων</string>
<string name="exit_at">Έξοδος στο</string>
<string name="sit_on_the_stop">Επιβίβαση στη στάση</string>
<string name="shared_string_swap">Αλλαγή</string>
@ -3029,10 +3029,10 @@
<string name="quick_action_switch_day_mode">Κατάσταση ημέρας</string>
<string name="quick_action_switch_night_mode">Κατάσταση νύχτας</string>
<string name="quick_action_day_night_switch_mode">Εναλλαγή κατάστασης ημέρας/νύχτας</string>
<string name="route_class_stat_container">Κλάση</string>
<string name="route_surface_stat_container">Επιφάνεια</string>
<string name="route_smoothness_stat_container">Ομαλότητα</string>
<string name="route_steepness_stat_container">Απότομη κλίση</string>
<string name="routeInfo_roadClass_name">Κλάση</string>
<string name="routeInfo_surface_name">Επιφάνεια</string>
<string name="routeInfo_smoothness_name">Ομαλότητα</string>
<string name="routeInfo_steepness_name">Απότομη κλίση</string>
<string name="run_full_osmand_msg">Χρησιμοποιείτε τον χάρτη {0} που παρέχεται από το OsmAnd. Θέλετε να εκκινήσετε την πλήρη έκδοση του OsmAnd;</string>
<string name="run_full_osmand_header">Να εκκινήσει το OsmAnd;</string>
<string name="routing_attr_avoid_sett_name">Αποφυγή βοτσάλων και πλακών</string>

View file

@ -2888,10 +2888,10 @@ Indikas lokon: %1$s x %2$s"</string>
<string name="shared_string_capacity">Enhaveco</string>
<string name="shared_string_width">Larĝo</string>
<string name="shared_string_height">Alto</string>
<string name="route_class_stat_container">Kategorio</string>
<string name="route_surface_stat_container">Pavimo</string>
<string name="route_smoothness_stat_container">Glateco</string>
<string name="route_steepness_stat_container">Klineco</string>
<string name="routeInfo_roadClass_name">Kategorio</string>
<string name="routeInfo_surface_name">Pavimo</string>
<string name="routeInfo_smoothness_name">Glateco</string>
<string name="routeInfo_steepness_name">Klineco</string>
<string name="add_home">Aldoni hejmon</string>
<string name="add_work">Aldoni laborejon</string>
<string name="work_button">Laborejo</string>
@ -2903,7 +2903,7 @@ Indikas lokon: %1$s x %2$s"</string>
<string name="time_of_day">Tagtempo</string>
<string name="by_transport_type">Per %1$s</string>
<string name="step_by_step">Paŝon post paŝo</string>
<string name="road_types">Specoj de vojoj</string>
<string name="routeInfo_road_types_name">Specoj de vojoj</string>
<string name="exit_at">Eliru ĉe</string>
<string name="sit_on_the_stop">Atendu ĉe haltejo</string>
<string name="quick_action_show_hide_gpx_tracks">Montri/kaŝi GPX-spurojn</string>

View file

@ -2904,10 +2904,10 @@ Lon %2$s</string>
<string name="shared_string_capacity">Capacidad</string>
<string name="shared_string_width">Ancho</string>
<string name="shared_string_height">Altura</string>
<string name="route_class_stat_container">Clase</string>
<string name="route_surface_stat_container">Superficie</string>
<string name="route_smoothness_stat_container">Suavidad</string>
<string name="route_steepness_stat_container">Inclinación</string>
<string name="routeInfo_roadClass_name">Clase</string>
<string name="routeInfo_surface_name">Superficie</string>
<string name="routeInfo_smoothness_name">Suavidad</string>
<string name="routeInfo_steepness_name">Inclinación</string>
<string name="add_home">Añadir como «Casa»</string>
<string name="add_work">Añadir como «Trabajo»</string>
<string name="work_button">Trabajo</string>
@ -2919,7 +2919,7 @@ Lon %2$s</string>
<string name="time_of_day">Hora del día</string>
<string name="by_transport_type">En %1$s</string>
<string name="step_by_step">Paso a paso</string>
<string name="road_types">Tipos de caminos</string>
<string name="routeInfo_road_types_name">Tipos de caminos</string>
<string name="exit_at">Bajarse en</string>
<string name="sit_on_the_stop">Esperar en la parada</string>
<string name="quick_action_show_hide_gpx_tracks">Alternar vista de trazas GPX</string>

View file

@ -2905,10 +2905,10 @@ Lon %2$s</string>
<string name="shared_string_capacity">Capacidad</string>
<string name="shared_string_width">Ancho</string>
<string name="shared_string_height">Altura</string>
<string name="route_class_stat_container">Clase</string>
<string name="route_surface_stat_container">Superficie</string>
<string name="route_smoothness_stat_container">Suavidad</string>
<string name="route_steepness_stat_container">Inclinación</string>
<string name="routeInfo_roadClass_name">Clase</string>
<string name="routeInfo_surface_name">Superficie</string>
<string name="routeInfo_smoothness_name">Suavidad</string>
<string name="routeInfo_steepness_name">Inclinación</string>
<string name="add_home">Añadir como «Casa»</string>
<string name="add_work">Añadir como «Trabajo»</string>
<string name="work_button">Trabajo</string>
@ -2920,7 +2920,7 @@ Lon %2$s</string>
<string name="time_of_day">Hora del día</string>
<string name="by_transport_type">En %1$s</string>
<string name="step_by_step">Paso a paso</string>
<string name="road_types">Tipos de caminos</string>
<string name="routeInfo_road_types_name">Tipos de caminos</string>
<string name="exit_at">Bajarse en</string>
<string name="sit_on_the_stop">Esperar en la parada</string>
<string name="quick_action_show_hide_gpx_tracks">Alternar vista de trazas GPX</string>

View file

@ -2922,10 +2922,10 @@
<string name="shared_string_capacity">Capacidad</string>
<string name="shared_string_width">Ancho</string>
<string name="shared_string_height">Altura</string>
<string name="route_class_stat_container">Clase</string>
<string name="route_surface_stat_container">Superficie</string>
<string name="route_smoothness_stat_container">Suavidad</string>
<string name="route_steepness_stat_container">Inclinación</string>
<string name="routeInfo_roadClass_name">Clase</string>
<string name="routeInfo_surface_name">Superficie</string>
<string name="routeInfo_smoothness_name">Suavidad</string>
<string name="routeInfo_steepness_name">Inclinación</string>
<string name="previous_route">Ruta anterior</string>
<string name="add_home">Añadir como «Casa»</string>
<string name="add_work">Añadir como «Trabajo»</string>
@ -2937,7 +2937,7 @@
<string name="time_of_day">Hora del día</string>
<string name="by_transport_type">En %1$s</string>
<string name="step_by_step">Paso a paso</string>
<string name="road_types">Tipos de caminos</string>
<string name="routeInfo_road_types_name">Tipos de caminos</string>
<string name="exit_at">Bajarse en</string>
<string name="sit_on_the_stop">Esperar en la parada</string>
<string name="quick_action_show_hide_gpx_tracks">Alternar vista de trazas GPX</string>

View file

@ -2904,10 +2904,10 @@ Area honi dagokio: %1$s x %2$s</string>
<string name="waiting_for_route_calculation">Ibilbidea kalkulatzen…</string>
<string name="show_along_the_route">Erakutsi ibilbidean zehar</string>
<string name="choose_track_file_to_follow">Hautatu lorratz fitxategia jarraitzeko</string>
<string name="route_class_stat_container">Klasea</string>
<string name="route_surface_stat_container">Gainazala</string>
<string name="route_smoothness_stat_container">Lausotasuna</string>
<string name="route_steepness_stat_container">Aldapa</string>
<string name="routeInfo_roadClass_name">Klasea</string>
<string name="routeInfo_surface_name">Gainazala</string>
<string name="routeInfo_smoothness_name">Lausotasuna</string>
<string name="routeInfo_steepness_name">Aldapa</string>
<string name="add_home">Gehitu etxea</string>
<string name="add_work">Gehitu lana</string>
<string name="work_button">Lana</string>
@ -2918,7 +2918,7 @@ Area honi dagokio: %1$s x %2$s</string>
<string name="time_of_day">Eguneko ordua</string>
<string name="by_transport_type">Egilea: %1$s</string>
<string name="step_by_step">Urratsez urrats</string>
<string name="road_types">Bide motak</string>
<string name="routeInfo_road_types_name">Bide motak</string>
<string name="exit_at">Irten hemen</string>
<string name="sit_on_the_stop">Muntatu honako geltokian</string>
<string name="shared_string_swap">Aldatu</string>

View file

@ -2944,10 +2944,10 @@
<string name="shared_string_capacity">ظرفیت</string>
<string name="shared_string_width">عرض</string>
<string name="shared_string_height">ارتفاع</string>
<string name="route_class_stat_container">رده</string>
<string name="route_surface_stat_container">سطح</string>
<string name="route_smoothness_stat_container">همواری</string>
<string name="route_steepness_stat_container">شیب</string>
<string name="routeInfo_roadClass_name">رده</string>
<string name="routeInfo_surface_name">سطح</string>
<string name="routeInfo_smoothness_name">همواری</string>
<string name="routeInfo_steepness_name">شیب</string>
<string name="add_home">افزودن خانه</string>
<string name="add_work">افزودن محل کار</string>
<string name="work_button">محل کار</string>
@ -2959,7 +2959,7 @@
<string name="time_of_day">ساعت</string>
<string name="by_transport_type">با %1$s</string>
<string name="step_by_step">گام به گام</string>
<string name="road_types">نوع جاده‌ها</string>
<string name="routeInfo_road_types_name">نوع جاده‌ها</string>
<string name="exit_at">ایستگاه پیاده‌شدن</string>
<string name="sit_on_the_stop">ایستگاه سوارشدن</string>
<string name="quick_action_show_hide_gpx_tracks">آشکار/پنهان کردن ردهای GPX</string>

View file

@ -2303,7 +2303,7 @@ Jos pidät OsmAndista ja OSMsta ja haluat tukea niitä, on tämä täydellinen t
<string name="rendering_attr_highway_class_path_name">Polku</string>
<string name="rendering_attr_highway_class_cycleway_name">Pyörätie</string>
<string name="rendering_attr_undefined_name">Määrittelemätön</string>
<string name="road_types">Tietyypit</string>
<string name="routeInfo_road_types_name">Tietyypit</string>
<string name="shared_string_swap">Muuta</string>
<string name="show_more">Näytä lisää</string>
<string name="tracks_on_map">Näytä jäljet</string>

View file

@ -2879,10 +2879,10 @@ représentant la zone : %1$s x %2$s</string>
<string name="shared_string_capacity">Сapacité</string>
<string name="shared_string_width">Largeur</string>
<string name="shared_string_height">Hauteur</string>
<string name="route_class_stat_container">Classe</string>
<string name="route_surface_stat_container">Surface</string>
<string name="route_smoothness_stat_container">Régularité</string>
<string name="route_steepness_stat_container">Pente</string>
<string name="routeInfo_roadClass_name">Classe</string>
<string name="routeInfo_surface_name">Surface</string>
<string name="routeInfo_smoothness_name">Régularité</string>
<string name="routeInfo_steepness_name">Pente</string>
<string name="add_home">Ajouter domicile</string>
<string name="add_work">Ajouter travail</string>
<string name="work_button">Travail</string>
@ -2894,7 +2894,7 @@ représentant la zone : %1$s x %2$s</string>
<string name="time_of_day">Heure de la journée</string>
<string name="by_transport_type">Par %1$s</string>
<string name="step_by_step">Pas à pas</string>
<string name="road_types">Types de route</string>
<string name="routeInfo_road_types_name">Types de route</string>
<string name="exit_at">Sortir à</string>
<string name="quick_action_show_hide_gpx_tracks">Afficher / masquer les traces GPX</string>
<string name="quick_action_gpx_tracks_hide">Masquer les traces GPX</string>

View file

@ -2944,14 +2944,14 @@ Lon %2$s</string>
<string name="add_home">Engadir a miña casa</string>
<string name="add_work">Engadir o meu lugar de traballo</string>
<string name="work_button">Traballo</string>
<string name="route_class_stat_container">Clase</string>
<string name="route_surface_stat_container">Superficie</string>
<string name="route_smoothness_stat_container">Suavidade</string>
<string name="route_steepness_stat_container">Pendente</string>
<string name="routeInfo_roadClass_name">Clase</string>
<string name="routeInfo_surface_name">Superficie</string>
<string name="routeInfo_smoothness_name">Suavidade</string>
<string name="routeInfo_steepness_name">Pendente</string>
<string name="time_of_day">Hora do día</string>
<string name="by_transport_type">En %1$s</string>
<string name="step_by_step">Paseniño</string>
<string name="road_types">Tipos de estrada</string>
<string name="routeInfo_road_types_name">Tipos de estrada</string>
<string name="exit_at">Saír en</string>
<string name="sit_on_the_stop">Embarcar na paraxe</string>
<string name="shared_string_swap">Trocar</string>

View file

@ -2897,10 +2897,10 @@
<string name="shared_string_capacity">נפח</string>
<string name="shared_string_width">רוחב</string>
<string name="shared_string_height">גובה</string>
<string name="route_class_stat_container">מחלקה</string>
<string name="route_surface_stat_container">משטח</string>
<string name="route_smoothness_stat_container">רכות</string>
<string name="route_steepness_stat_container">תלילות</string>
<string name="routeInfo_roadClass_name">מחלקה</string>
<string name="routeInfo_surface_name">משטח</string>
<string name="routeInfo_smoothness_name">רכות</string>
<string name="routeInfo_steepness_name">תלילות</string>
<string name="add_home">הוספת בית</string>
<string name="add_work">הוספת עבודה</string>
<string name="work_button">עבודה</string>
@ -2912,7 +2912,7 @@
<string name="time_of_day">השעה ביום</string>
<string name="by_transport_type">עם %1$s</string>
<string name="step_by_step">שלב אחר שלב</string>
<string name="road_types">סוגי כבישים</string>
<string name="routeInfo_road_types_name">סוגי כבישים</string>
<string name="exit_at">לצאת ב־</string>
<string name="quick_action_show_hide_gpx_tracks">הצגה/הסתרה של מסלולי GPX</string>
<string name="quick_action_show_hide_gpx_tracks_descr">נגיעה בכפתור פעולה זה מציגה או מסתירה את מסלולי ה־GPX הנבחרים במפה</string>

View file

@ -2870,17 +2870,17 @@ Kérlek adj meg egy teljes kódot</string>
<string name="run_full_osmand_header">Elindítod az OsmAndot\?</string>
<string name="add_work">Munkahely hozzáadása</string>
<string name="work_button">Munkahely</string>
<string name="route_surface_stat_container">Burkolat</string>
<string name="route_smoothness_stat_container">Simaság</string>
<string name="route_steepness_stat_container">Lejtés</string>
<string name="routeInfo_surface_name">Burkolat</string>
<string name="routeInfo_smoothness_name">Simaság</string>
<string name="routeInfo_steepness_name">Lejtés</string>
<string name="previous_route">Előző útvonal</string>
<string name="add_home">Otthon hozzáadása</string>
<string name="shared_string_swap">Felcserélés</string>
<string name="show_more">Továbbiak megjelenítése</string>
<string name="tracks_on_map">Megjelenített nyomvonalak</string>
<string name="route_class_stat_container">Útkategória</string>
<string name="routeInfo_roadClass_name">Útkategória</string>
<string name="step_by_step">Lépésről lépésre</string>
<string name="road_types">Úttípusok</string>
<string name="routeInfo_road_types_name">Úttípusok</string>
<string name="exit_at">Szálljon le itt:</string>
<string name="quick_action_show_hide_gpx_tracks">GPX nyomvonalak megjelenítése/elrejtése</string>
<string name="quick_action_show_hide_gpx_tracks_descr">A műveletgombra koppintás elrejti vagy megjeleníti a GPX nyomvonalakat a térképen</string>

View file

@ -747,7 +747,7 @@
<string name="previous_route">Rute sebelumnya</string>
<string name="show_more">Tampilkan lainnya</string>
<string name="by_transport_type">Dengan %1$s</string>
<string name="road_types">Tipe jalan</string>
<string name="routeInfo_road_types_name">Tipe jalan</string>
<string name="add_destination_query">Silakan tambah Tujuan terlebih dahulu</string>
<string name="use_osm_live_public_transport_description">Aktifkan angkutan publik untuk perubahan OsmAnd Live.</string>
<string name="use_osm_live_public_transport">Angkutan publik OsmAnd Live</string>

View file

@ -2915,10 +2915,10 @@ Stendur fyrir svæði: %1$s x %2$s</string>
<string name="quick_action_switch_day_mode">Dagshamur</string>
<string name="quick_action_switch_night_mode">Næturhamur</string>
<string name="quick_action_day_night_switch_mode">Skipta á milli Dags/Næturhams</string>
<string name="route_class_stat_container">Flokkur</string>
<string name="route_surface_stat_container">Yfirborð</string>
<string name="route_smoothness_stat_container">Áferð</string>
<string name="route_steepness_stat_container">Bratti</string>
<string name="routeInfo_roadClass_name">Flokkur</string>
<string name="routeInfo_surface_name">Yfirborð</string>
<string name="routeInfo_smoothness_name">Áferð</string>
<string name="routeInfo_steepness_name">Bratti</string>
<string name="add_home">Bæta við heima</string>
<string name="add_work">Bæta við vinnu</string>
<string name="work_button">Vinna</string>
@ -2930,7 +2930,7 @@ Stendur fyrir svæði: %1$s x %2$s</string>
<string name="time_of_day">Tími dagsins</string>
<string name="by_transport_type">Eftir %1$s</string>
<string name="step_by_step">Skref fyrir skref</string>
<string name="road_types">Gerðir vega</string>
<string name="routeInfo_road_types_name">Gerðir vega</string>
<string name="exit_at">Fara útaf við</string>
<string name="sit_on_the_stop">Fara um borð við stöðvunina</string>
<string name="quick_action_show_hide_gpx_tracks">Birta/Fela GPX-ferla</string>

View file

@ -2901,16 +2901,16 @@ Rappresenta l\'area: %1$s x %2$s</string>
<string name="quick_action_switch_day_mode">Modalità Giorno</string>
<string name="quick_action_switch_night_mode">Modalità Notte</string>
<string name="quick_action_day_night_switch_mode">Cambia modalità giorno/notte</string>
<string name="route_class_stat_container">Tipo</string>
<string name="route_surface_stat_container">Superficie</string>
<string name="route_smoothness_stat_container">Levigatezza</string>
<string name="route_steepness_stat_container">Ripidezza</string>
<string name="routeInfo_roadClass_name">Tipo</string>
<string name="routeInfo_surface_name">Superficie</string>
<string name="routeInfo_smoothness_name">Levigatezza</string>
<string name="routeInfo_steepness_name">Ripidezza</string>
<string name="run_full_osmand_msg">Stai utilizzando la mappa {0} che è sviluppata da OsmAnd. Vuoi lanciare la versione completa di OsmAnd\?</string>
<string name="run_full_osmand_header">Lanciare OsmAnd\?</string>
<string name="previous_route">Percorsi precedenti</string>
<string name="add_home">Aggiungi alla home</string>
<string name="step_by_step">Passo dopo passo</string>
<string name="road_types">Tipi di strade</string>
<string name="routeInfo_road_types_name">Tipi di strade</string>
<string name="show_more">Mostra di più</string>
<string name="tracks_on_map">Tracciati mostrati</string>
<string name="quick_action_show_hide_gpx_tracks">Mostra/Nascondi Tracciati GPX</string>

View file

@ -2901,7 +2901,7 @@ POIの更新は利用できません</string>
<string name="use_osm_live_public_transport">OsmAnd Live 公共交通機関機能の使用</string>
<string name="time_of_day">時刻</string>
<string name="by_transport_type">%1$s を利用</string>
<string name="road_types">道路種別</string>
<string name="routeInfo_road_types_name">道路種別</string>
<string name="shared_string_swap">入れ替え</string>
<string name="show_more">詳細を見る</string>
<string name="tracks_on_map">マップ上の経路</string>
@ -2958,9 +2958,9 @@ POIの更新は利用できません</string>
<string name="quick_action_switch_night_mode">夜モード</string>
<string name="quick_action_day_night_switch_mode">昼/夜モードの切り替え</string>
<string name="favorite_autofill_toast_text">" は、以下の名前で保存されます:"</string>
<string name="route_surface_stat_container">路面</string>
<string name="route_smoothness_stat_container">滑らかさ</string>
<string name="route_steepness_stat_container">勾配</string>
<string name="routeInfo_surface_name">路面</string>
<string name="routeInfo_smoothness_name">滑らかさ</string>
<string name="routeInfo_steepness_name">勾配</string>
<string name="run_full_osmand_msg">あなたは今 OsmAndで動くマップを使用しています。{0} OsmAndのフルバージョンを起動しますか</string>
<string name="run_full_osmand_header">OsmAndを起動しますか</string>
<string name="add_intermediate">経由地点を追加する</string>

View file

@ -2642,7 +2642,7 @@ Tai yra puikus būdas paremti OsmAnd ir OSM, jei jie jums patinka.</string>
<string name="rendering_attr_highway_class_cycleway_name">Dviračių takas</string>
<string name="rendering_attr_undefined_name">Nenurodyta</string>
<string name="time_of_day">Dienos metas</string>
<string name="road_types">Kelių tipai</string>
<string name="routeInfo_road_types_name">Kelių tipai</string>
<string name="show_more">Rodyti daugiau</string>
<string name="quick_action_show_hide_gpx_tracks">Rodyti/slėpti GPX pėdsakus</string>
<string name="quick_action_show_hide_gpx_tracks_descr">Paspaudus šį mygtuką žemėlapyje parodomi arba paslepiami GPX pėdsakai</string>

View file

@ -3,7 +3,7 @@
<string name="back_to_search">Гэр тайхар</string>
<string name="rendering_attr_highway_class_road_name">Зам</string>
<string name="rendering_attr_highway_class_street_name">Гудамж</string>
<string name="road_types">замын төрөл</string>
<string name="routeInfo_road_types_name">замын төрөл</string>
<string name="search_street">Гудамж хайх</string>
<string name="search_no_results_feedback">илэрц алга</string>
<string name="download_all">Бүгдийг татах</string>

View file

@ -2902,10 +2902,10 @@
<string name="shared_string_capacity">Kapasitet</string>
<string name="shared_string_width">Bredde</string>
<string name="shared_string_height">Høyde</string>
<string name="route_class_stat_container">Klasse</string>
<string name="route_surface_stat_container">Overflate</string>
<string name="route_smoothness_stat_container">Jevnhet</string>
<string name="route_steepness_stat_container">Stigning</string>
<string name="routeInfo_roadClass_name">Klasse</string>
<string name="routeInfo_surface_name">Overflate</string>
<string name="routeInfo_smoothness_name">Jevnhet</string>
<string name="routeInfo_steepness_name">Stigning</string>
<string name="add_home">Legg til bosted</string>
<string name="add_work">Legg til arbeidssted</string>
<string name="work_button">Arbeid</string>
@ -2917,7 +2917,7 @@
<string name="time_of_day">Tid på dagen</string>
<string name="by_transport_type">Med %1$s</string>
<string name="step_by_step">Steg for steg</string>
<string name="road_types">Veityper</string>
<string name="routeInfo_road_types_name">Veityper</string>
<string name="exit_at">Gå av på</string>
<string name="sit_on_the_stop">Sitt på stoppet</string>
<string name="quick_action_show_hide_gpx_tracks">Vis/skjul GPX-spor</string>

View file

@ -2836,7 +2836,7 @@ voor Gebied: %1$s x %2$s</string>
<string name="use_osm_live_public_transport">OsmAnd Live Openbaar vervoer</string>
<string name="time_of_day">Huidige tijd</string>
<string name="step_by_step">Stap voor stap</string>
<string name="road_types">Weg types</string>
<string name="routeInfo_road_types_name">Weg types</string>
<string name="exit_at">Uitrit over</string>
<string name="shared_string_swap">Wissel</string>
<string name="show_more">Toon meer</string>
@ -2876,9 +2876,9 @@ voor Gebied: %1$s x %2$s</string>
<string name="quick_action_switch_day_mode">Dag Modus</string>
<string name="quick_action_switch_night_mode">Nacht Modus</string>
<string name="quick_action_day_night_switch_mode">Wissel tussen Dag/Nacht modus</string>
<string name="route_surface_stat_container">Oppervlakte</string>
<string name="route_smoothness_stat_container">Kwaliteit wegdek</string>
<string name="route_steepness_stat_container">Steilte</string>
<string name="routeInfo_surface_name">Oppervlakte</string>
<string name="routeInfo_smoothness_name">Kwaliteit wegdek</string>
<string name="routeInfo_steepness_name">Steilte</string>
<string name="run_full_osmand_msg">U gebruikt {0} kaart geleverd door OsmAnd. Wilt u de \"OsmAnd full\" versie openen\?</string>
<string name="run_full_osmand_header">Open OsmAnd\?</string>
<string name="release_3_3_7">• Toon de overstaptijden in Openbaar Vervoer

View file

@ -139,7 +139,7 @@
<string name="time_of_day">Ora de la jornada</string>
<string name="by_transport_type">Per %1$s</string>
<string name="step_by_step">Pas a pas</string>
<string name="road_types">Tipe de rota</string>
<string name="routeInfo_road_types_name">Tipe de rota</string>
<string name="exit_at">Sortida a</string>
<string name="sit_on_the_stop">Avançatz-vos a l\'aplant</string>
<string name="shared_string_swap">De l\'envèrs</string>

View file

@ -2908,17 +2908,17 @@ Reprezentuje obszar: %1$s x %2$s</string>
<string name="quick_action_switch_day_mode">Tryb Dzienny</string>
<string name="quick_action_switch_night_mode">Tryb Nocny</string>
<string name="quick_action_day_night_switch_mode">Zmień tryb Dzienny/Nocny</string>
<string name="route_class_stat_container">Kategoria</string>
<string name="route_surface_stat_container">Powierzchnia</string>
<string name="route_smoothness_stat_container">Wygładzanie</string>
<string name="route_steepness_stat_container">Nachylenie</string>
<string name="routeInfo_roadClass_name">Kategoria</string>
<string name="routeInfo_surface_name">Powierzchnia</string>
<string name="routeInfo_smoothness_name">Wygładzanie</string>
<string name="routeInfo_steepness_name">Nachylenie</string>
<string name="add_home">Dodaj dom</string>
<string name="add_work">Dodaj pracę</string>
<string name="work_button">Praca</string>
<string name="time_of_day">Pora dnia</string>
<string name="by_transport_type">Użyto %1$s</string>
<string name="step_by_step">Krok po kroku</string>
<string name="road_types">Typy dróg</string>
<string name="routeInfo_road_types_name">Typy dróg</string>
<string name="exit_at">Opuść na</string>
<string name="sit_on_the_stop">Tablica na przystanku</string>
<string name="shared_string_swap">Wymień</string>

View file

@ -2889,10 +2889,10 @@ Pôr do Sol: %2$s</string>
<string name="shared_string_capacity">Capacidade</string>
<string name="shared_string_width">Largura</string>
<string name="shared_string_height">Altura</string>
<string name="route_class_stat_container">Classe</string>
<string name="route_surface_stat_container">Superfície</string>
<string name="route_smoothness_stat_container">Suavidade</string>
<string name="route_steepness_stat_container">Inclinação</string>
<string name="routeInfo_roadClass_name">Classe</string>
<string name="routeInfo_surface_name">Superfície</string>
<string name="routeInfo_smoothness_name">Suavidade</string>
<string name="routeInfo_steepness_name">Inclinação</string>
<string name="add_destination_query">Por favor adicione o primeiro destino</string>
<string name="previous_route">Rota anterior</string>
<string name="add_home">Adicionar casa</string>
@ -2904,7 +2904,7 @@ Pôr do Sol: %2$s</string>
<string name="time_of_day">Hora do dia</string>
<string name="by_transport_type">Por %1$s</string>
<string name="step_by_step">Passo a passo</string>
<string name="road_types">Tipos de estrada</string>
<string name="routeInfo_road_types_name">Tipos de estrada</string>
<string name="exit_at">Desembarque em</string>
<string name="sit_on_the_stop">Embarque na parada</string>
<string name="quick_action_show_hide_gpx_tracks">Mostrar/Ocultar faixas GPX</string>

View file

@ -2982,7 +2982,7 @@
<string name="time_of_day">Hora do dia</string>
<string name="by_transport_type">Por %1$s</string>
<string name="step_by_step">Passo a passo</string>
<string name="road_types">Tipos de estrada</string>
<string name="routeInfo_road_types_name">Tipos de estrada</string>
<string name="exit_at">Sair em</string>
<string name="shared_string_swap">Trocar</string>
<string name="show_more">Mostrar mais</string>
@ -3021,10 +3021,10 @@
<string name="add_home">Adicionar casa</string>
<string name="add_work">Adicionar trabalho</string>
<string name="work_button">Trabalho</string>
<string name="route_class_stat_container">Classe</string>
<string name="route_surface_stat_container">Superfície</string>
<string name="route_smoothness_stat_container">Lisura</string>
<string name="route_steepness_stat_container">Inclinação</string>
<string name="routeInfo_roadClass_name">Classe</string>
<string name="routeInfo_surface_name">Superfície</string>
<string name="routeInfo_smoothness_name">Lisura</string>
<string name="routeInfo_steepness_name">Inclinação</string>
<string name="routing_attr_avoid_sett_name">Evitar paralelepípedo</string>
<string name="routing_attr_avoid_sett_description">Evitar paralelepípedo</string>
<string name="send_log">Enviar registo</string>

View file

@ -2201,7 +2201,7 @@
<string name="time_of_day">Ora din zi</string>
<string name="by_transport_type">După %1$s</string>
<string name="step_by_step">Pas cu pas</string>
<string name="road_types">Tipuri drum</string>
<string name="routeInfo_road_types_name">Tipuri drum</string>
<string name="exit_at">Ieșire la</string>
<string name="sit_on_the_stop">Îmbarcați-vă la oprirea</string>
<string name="shared_string_swap">Schimbați</string>
@ -2305,7 +2305,7 @@
<string name="empty_state_favourites_desc">Importați Favorite sau adăugați prin marcarea punctelor pe hartă.</string>
<string name="poi_cannot_be_found">Nodul sau calea nu pot fi găsite.</string>
<string name="run_full_osmand_header">Pornesc OsmAnd\?</string>
<string name="route_steepness_stat_container">Înclinație</string>
<string name="routeInfo_steepness_name">Înclinație</string>
<string name="move_maps">Mutați hărțile</string>
<string name="dont_move_maps">Nu muta</string>
<string name="public_transport_try_ped">Încercați navigarea pentru pietoni.</string>

View file

@ -2892,13 +2892,13 @@
<string name="transfers">пересадки</string>
<string name="on_foot">пешком</string>
<string name="show_along_the_route">Показывать вдоль маршрута</string>
<string name="route_surface_stat_container">Поверхность</string>
<string name="route_class_stat_container">Класс</string>
<string name="route_steepness_stat_container">Крутизна</string>
<string name="routeInfo_surface_name">Поверхность</string>
<string name="routeInfo_roadClass_name">Класс</string>
<string name="routeInfo_steepness_name">Крутизна</string>
<string name="add_home">Добавить дом</string>
<string name="add_work">Добавить работу</string>
<string name="work_button">Работа</string>
<string name="route_smoothness_stat_container">Проходимость</string>
<string name="routeInfo_smoothness_name">Проходимость</string>
<string name="previous_route">Предыдущий маршрут</string>
<string name="add_destination_query">Сначала добавьте пункт назначения</string>
<string name="shared_string_swap">Поменять</string>
@ -2909,7 +2909,7 @@
<string name="quick_action_gpx_tracks_show">Показать GPX треки</string>
<string name="time_of_day">Время суток</string>
<string name="step_by_step">Шаг за шагом</string>
<string name="road_types">Типы дорог</string>
<string name="routeInfo_road_types_name">Типы дорог</string>
<string name="quick_action_show_hide_gpx_tracks_descr">Нажатие на кнопку действия отобразит или скроет выбранные GPX треки на карте</string>
<string name="by_transport_type">На %1$s</string>
<string name="exit_at">Выход на</string>

View file

@ -2890,10 +2890,10 @@ Pro praghere iscrie su còdighe intreu</string>
<string name="voice_announcements">Annùntzios vocales</string>
<string name="intermediate_destinations">Destinatziones intermèdias</string>
<string name="arrive_at_time">Arribada a sas %1$s</string>
<string name="route_class_stat_container">Classe</string>
<string name="route_surface_stat_container">Superfìtzie</string>
<string name="route_smoothness_stat_container">Uniformidade</string>
<string name="route_steepness_stat_container">Ratesa</string>
<string name="routeInfo_roadClass_name">Classe</string>
<string name="routeInfo_surface_name">Superfìtzie</string>
<string name="routeInfo_smoothness_name">Uniformidade</string>
<string name="routeInfo_steepness_name">Ratesa</string>
<string name="add_home">Annanghe sa domo</string>
<string name="add_work">Annanghe su logu de traballu</string>
<string name="work_button">Traballu</string>
@ -2905,7 +2905,7 @@ Pro praghere iscrie su còdighe intreu</string>
<string name="time_of_day">Ora de sa die</string>
<string name="by_transport_type">Tràmite %1$s</string>
<string name="step_by_step">Passu pro passu</string>
<string name="road_types">Casta de àndalas</string>
<string name="routeInfo_road_types_name">Casta de àndalas</string>
<string name="exit_at">Essi in</string>
<string name="sit_on_the_stop">Sede·ti in sa firmada</string>
<string name="quick_action_show_hide_gpx_tracks">Ammustra/Istichi sas rastas GPX</string>

View file

@ -2890,10 +2890,10 @@ Zodpovedá oblasti: %1$s x %2$s</string>
<string name="voice_announcements">Hlasové oznámenia</string>
<string name="intermediate_destinations">Medziciele</string>
<string name="arrive_at_time">Príjazd o %1$s</string>
<string name="route_class_stat_container">Trieda</string>
<string name="route_surface_stat_container">Povrch</string>
<string name="route_smoothness_stat_container">Hladkosť povrchu</string>
<string name="route_steepness_stat_container">Strmosť</string>
<string name="routeInfo_roadClass_name">Trieda</string>
<string name="routeInfo_surface_name">Povrch</string>
<string name="routeInfo_smoothness_name">Hladkosť povrchu</string>
<string name="routeInfo_steepness_name">Strmosť</string>
<string name="previous_route">Predchádzajúca trasa</string>
<string name="add_home">Pridať Domov</string>
<string name="add_work">Pridať Prácu</string>
@ -2924,7 +2924,7 @@ Zodpovedá oblasti: %1$s x %2$s</string>
<string name="time_of_day">Denná doba</string>
<string name="by_transport_type">Pomocou %1$s</string>
<string name="step_by_step">Krok za krokom</string>
<string name="road_types">Druhy ciest</string>
<string name="routeInfo_road_types_name">Druhy ciest</string>
<string name="exit_at">Vystúpte na</string>
<string name="sit_on_the_stop">Nastúpte na zastávke</string>
<string name="quick_action_show_hide_gpx_tracks">Zobraziť/Skryť GPX stopy</string>

View file

@ -2941,7 +2941,7 @@ Koda predstavlja območje: %1$s x %2$s</string>
<string name="time_of_day">Čas dneva</string>
<string name="by_transport_type">Do %1$s</string>
<string name="step_by_step">Korak po korak</string>
<string name="road_types">Vrste poti</string>
<string name="routeInfo_road_types_name">Vrste poti</string>
<string name="shared_string_swap">Zamenjaj</string>
<string name="show_more">Pokaži več</string>
<string name="tracks_on_map">Prikazane sledi</string>
@ -2977,10 +2977,10 @@ Koda predstavlja območje: %1$s x %2$s</string>
<string name="exit_at">Izstopi na postaji</string>
<string name="sit_on_the_stop">Vstopi na postaji</string>
<string name="quick_action_show_hide_gpx_tracks_descr">S pritiskom na gumb dejanja se pokažejo ali skrijejo sledi GPX na zemljevidu</string>
<string name="route_class_stat_container">Razred</string>
<string name="route_surface_stat_container">Površina</string>
<string name="route_smoothness_stat_container">Gladkost</string>
<string name="route_steepness_stat_container">Naklon</string>
<string name="routeInfo_roadClass_name">Razred</string>
<string name="routeInfo_surface_name">Površina</string>
<string name="routeInfo_smoothness_name">Gladkost</string>
<string name="routeInfo_steepness_name">Naklon</string>
<string name="shared_string_degrees">Stopinje</string>
<string name="shared_string_milliradians">Miliradiani</string>
<string name="angular_measeurement">Kotne enote</string>

View file

@ -2916,10 +2916,10 @@
<string name="voice_announcements">Гласовне најаве</string>
<string name="intermediate_destinations">Успутна одредишта</string>
<string name="arrive_at_time">"Долазак у %1$s "</string>
<string name="route_class_stat_container">Класа</string>
<string name="route_surface_stat_container">Подлога</string>
<string name="route_smoothness_stat_container">Углачаност</string>
<string name="route_steepness_stat_container">Нагиб</string>
<string name="routeInfo_roadClass_name">Класа</string>
<string name="routeInfo_surface_name">Подлога</string>
<string name="routeInfo_smoothness_name">Углачаност</string>
<string name="routeInfo_steepness_name">Нагиб</string>
<string name="routing_attr_avoid_tram_name">Избегавај трамваје</string>
<string name="routing_attr_avoid_tram_description">Избегавање трамваја</string>
<string name="routing_attr_avoid_bus_name">Избегавај аутобусе</string>
@ -2983,7 +2983,7 @@
<string name="time_of_day">Доба дана</string>
<string name="by_transport_type">До %1$s</string>
<string name="step_by_step">Корак по корак</string>
<string name="road_types">Типови путева</string>
<string name="routeInfo_road_types_name">Типови путева</string>
<string name="exit_at">Излаз на</string>
<string name="shared_string_swap">Замени</string>
<string name="show_more">Прикажи још</string>

View file

@ -2368,7 +2368,7 @@
<string name="rendering_attr_highway_class_track_name">Tarım yolu</string>
<string name="rendering_attr_highway_class_cycleway_name">Bisiklet yolu</string>
<string name="rendering_attr_undefined_name">Belirtilmemiş</string>
<string name="road_types">Yol tipleri</string>
<string name="routeInfo_road_types_name">Yol tipleri</string>
<string name="shared_string_swap">Takas</string>
<string name="show_more">Daha fazla görüntüle</string>
<string name="quick_action_show_hide_gpx_tracks">Gps izlerini göster/gizle</string>

View file

@ -2863,7 +2863,7 @@
<string name="use_osm_live_public_transport_description">Увімкнути громадський транспорт із врахуванням авто-оновлень OsmAnd Live.</string>
<string name="use_osm_live_public_transport">Громадський транспорт OsmAnd Live</string>
<string name="step_by_step">Крок за кроком</string>
<string name="road_types">Типи доріг</string>
<string name="routeInfo_road_types_name">Типи доріг</string>
<string name="exit_at">Вихід на</string>
<string name="sit_on_the_stop">Посадка на зупинці</string>
<string name="shared_string_swap">Поміняти</string>
@ -2902,10 +2902,10 @@
<string name="quick_action_switch_day_mode">Денний режим</string>
<string name="quick_action_switch_night_mode">Нічний режим</string>
<string name="quick_action_day_night_switch_mode">Перемкнути Денний/Нічний режим</string>
<string name="route_class_stat_container">Клас</string>
<string name="route_surface_stat_container">Поверхня</string>
<string name="route_smoothness_stat_container">Рівність</string>
<string name="route_steepness_stat_container">Крутість</string>
<string name="routeInfo_roadClass_name">Клас</string>
<string name="routeInfo_surface_name">Поверхня</string>
<string name="routeInfo_smoothness_name">Рівність</string>
<string name="routeInfo_steepness_name">Крутість</string>
<string name="run_full_osmand_header">Запустити OsmAnd\?</string>
<string name="shared_string_walk">Пішки</string>
<string name="save_poi_value_exceed_length">Довжина тегу \"%s\" не може перевищувати 255 символів.

View file

@ -2579,8 +2579,8 @@
<string name="quick_action_edit_actions">编辑活动</string>
<string name="coord_input_save_as_track_descr">你增加了%1$s 个目标。输入文件名后点击\"保存\"。</string>
<string name="ask_for_location_permission">请在允许OsmAnd获取定位信息后继续。</string>
<string name="route_smoothness_stat_container">光滑度</string>
<string name="route_steepness_stat_container">坡度</string>
<string name="routeInfo_smoothness_name">光滑度</string>
<string name="routeInfo_steepness_name">坡度</string>
<string name="unirs_render_descr">更改默认风格以突出显示人行道和非机动车道使用旧版Mapnik配色。</string>
<string name="run_full_osmand_msg">你正在使用基于 OsmAnd 的 {0}。是否启动完整版 OsmAnd</string>
<string name="transfers_size">%1$d 次中转</string>
@ -2631,7 +2631,7 @@
<string name="time_of_day">当前时间</string>
<string name="by_transport_type">乘坐 %1$s</string>
<string name="step_by_step">逐步</string>
<string name="road_types">道路类型</string>
<string name="routeInfo_road_types_name">道路类型</string>
<string name="exit_at">退出于</string>
<string name="quick_action_show_hide_gpx_tracks">显示/隐藏GPX路径</string>
<string name="quick_action_show_hide_gpx_tracks_descr">点按此按钮以在地图中显示或隐藏已选中的GPX路径</string>

View file

@ -2891,10 +2891,10 @@
<string name="quick_action_switch_day_mode">日間模式</string>
<string name="quick_action_switch_night_mode">夜間模式</string>
<string name="quick_action_day_night_switch_mode">切換日間/夜間模式</string>
<string name="route_class_stat_container">級別</string>
<string name="route_surface_stat_container">路面</string>
<string name="route_smoothness_stat_container">平坦</string>
<string name="route_steepness_stat_container">坡度</string>
<string name="routeInfo_roadClass_name">級別</string>
<string name="routeInfo_surface_name">路面</string>
<string name="routeInfo_smoothness_name">平坦</string>
<string name="routeInfo_steepness_name">坡度</string>
<string name="add_home">新增首頁</string>
<string name="add_work">新增工作</string>
<string name="work_button">工作</string>
@ -2906,7 +2906,7 @@
<string name="time_of_day">一天中的時間</string>
<string name="by_transport_type">由 %1$s</string>
<string name="step_by_step">按步驟</string>
<string name="road_types">道路類型</string>
<string name="routeInfo_road_types_name">道路類型</string>
<string name="exit_at">出口於</string>
<string name="sit_on_the_stop">站點的座位</string>
<string name="quick_action_show_hide_gpx_tracks">顯示/隱藏 GPX 軌跡</string>

View file

@ -229,7 +229,7 @@
<string name="time_of_day">Time of day</string>
<string name="by_transport_type">By %1$s</string>
<string name="step_by_step">Step by step</string>
<string name="road_types">Road types</string>
<string name="routeInfo_road_types_name">Road types</string>
<string name="exit_at">Exit at</string>
<string name="sit_on_the_stop">Board at stop</string>
<string name="shared_string_swap">Swap</string>
@ -3225,10 +3225,10 @@
<string name="wiki_article_not_found">Article not found</string>
<string name="how_to_open_wiki_title">How to open Wikipedia articles?</string>
<string name="test_voice_desrc">Tap a button and listen to the corresponding voice prompt to identify missing or faulty prompts.</string>
<string name="route_class_stat_container">Class</string>
<string name="route_surface_stat_container">Surface</string>
<string name="route_smoothness_stat_container">Smoothness</string>
<string name="route_steepness_stat_container">Steepness</string>
<string name="routeInfo_roadClass_name">Class</string>
<string name="routeInfo_surface_name">Surface</string>
<string name="routeInfo_smoothness_name">Smoothness</string>
<string name="routeInfo_steepness_name">Steepness</string>
<string name="run_full_osmand_msg">You are using {0} Map which is powered by OsmAnd. Do you want to launch OsmAnd full version?</string>
<string name="run_full_osmand_header">Launch OsmAnd?</string>
<string name="routing_attr_avoid_sett_name">Avoid cobblestone and sett</string>

View file

@ -90,6 +90,7 @@ import net.osmand.aidl.contextmenu.ContextMenuButtonsParams;
import net.osmand.aidl.contextmenu.UpdateContextMenuButtonsParams;
import net.osmand.aidl.contextmenu.RemoveContextMenuButtonsParams;
import net.osmand.aidl.mapmarker.RemoveMapMarkersParams;
// NOTE: Add new methods at the end of file!!!
@ -105,16 +106,23 @@ interface IOsmAndAidlInterface {
boolean addMapMarker(in AddMapMarkerParams params);
/**
* Add map marker at given location.
* Remove map marker.
*
* If ignoreCoordinates is false the marker is only removed if lat/lon match the currently set values of the marker.
* If ignoreCoordinates is true the marker is removed if the name matches, the values of lat/lon are ignored.
*
* @param lat (double) - latitude.
* @param lon (double) - longitude.
* @param name (String)- name of marker.
* @param ignoreCoordinates (boolean) - flag to determine whether lat/lon shall be ignored
*/
boolean removeMapMarker(in RemoveMapMarkerParams params);
/**
* Update map marker at given location with name.
* Update map marker.
*
* If ignoreCoordinates is false the marker gets updated only if latPrev/lonPrev match the currently set values of the marker.
* If ignoreCoordinates is true the marker gets updated if the name matches, the values of latPrev/lonPrev are ignored.
*
* @param latPrev (double) - latitude (current marker).
* @param lonPrev (double) - longitude (current marker).
@ -122,6 +130,7 @@ interface IOsmAndAidlInterface {
* @param latNew (double) - latitude (new marker).
* @param lonNew (double) - longitude (new marker).
* @param nameNew (String) - name (new marker).
* @param ignoreCoordinates (boolean) - flag to determine whether latPrev/lonPrev shall be ignored
*/
boolean updateMapMarker(in UpdateMapMarkerParams params);
@ -816,4 +825,10 @@ interface IOsmAndAidlInterface {
* @params callback (IOsmAndAidlCallback) - callback to notify user on voice message
*/
long registerForVoiceRouterMessages(in ANavigationVoiceRouterMessageParams params, IOsmAndAidlCallback callback);
/**
* Removes all active map markers (marks them as passed and moves to history)
* Empty class of params
*/
boolean removeAllActiveMapMarkers(in RemoveMapMarkersParams params);
}

View file

@ -1037,16 +1037,18 @@ public class OsmandAidlApi {
}
}
boolean removeMapMarker(AMapMarker marker) {
boolean removeMapMarker(AMapMarker marker, boolean ignoreCoordinates) {
if (marker != null) {
LatLon latLon = new LatLon(marker.getLatLon().getLatitude(), marker.getLatLon().getLongitude());
MapMarkersHelper markersHelper = app.getMapMarkersHelper();
List<MapMarker> mapMarkers = markersHelper.getMapMarkers();
for (MapMarker m : mapMarkers) {
if (m.getOnlyName().equals(marker.getName()) && latLon.equals(new LatLon(m.getLatitude(), m.getLongitude()))) {
markersHelper.moveMapMarkerToHistory(m);
refreshMap();
return true;
if (m.getOnlyName().equals(marker.getName())) {
if (ignoreCoordinates || latLon.equals(new LatLon(m.getLatitude(), m.getLongitude()))) {
markersHelper.moveMapMarkerToHistory(m);
refreshMap();
return true;
}
}
}
return false;
@ -1055,23 +1057,40 @@ public class OsmandAidlApi {
}
}
boolean updateMapMarker(AMapMarker markerPrev, AMapMarker markerNew) {
boolean removeAllActiveMapMarkers() {
boolean refreshNeeded = false;
MapMarkersHelper markersHelper = app.getMapMarkersHelper();
List<MapMarker> mapMarkers = markersHelper.getMapMarkers();
for (MapMarker m : mapMarkers) {
markersHelper.moveMapMarkerToHistory(m);
refreshNeeded = true;
}
if (refreshNeeded) {
refreshMap();
}
return true;
}
boolean updateMapMarker(AMapMarker markerPrev, AMapMarker markerNew, boolean ignoreCoordinates) {
if (markerPrev != null && markerNew != null) {
LatLon latLon = new LatLon(markerPrev.getLatLon().getLatitude(), markerPrev.getLatLon().getLongitude());
LatLon latLonNew = new LatLon(markerNew.getLatLon().getLatitude(), markerNew.getLatLon().getLongitude());
MapMarkersHelper markersHelper = app.getMapMarkersHelper();
List<MapMarker> mapMarkers = markersHelper.getMapMarkers();
for (MapMarker m : mapMarkers) {
if (m.getOnlyName().equals(markerPrev.getName()) && latLon.equals(new LatLon(m.getLatitude(), m.getLongitude()))) {
PointDescription pd = new PointDescription(
PointDescription.POINT_TYPE_MAP_MARKER, markerNew.getName() != null ? markerNew.getName() : "");
MapMarker marker = new MapMarker(m.point, pd, m.colorIndex, m.selected, m.index);
marker.id = m.id;
marker.creationDate = m.creationDate;
marker.visitedDate = m.visitedDate;
markersHelper.moveMapMarker(marker, latLonNew);
refreshMap();
return true;
if (m.getOnlyName().equals(markerPrev.getName())) {
if (ignoreCoordinates || latLon.equals(new LatLon(m.getLatitude(), m.getLongitude()))) {
PointDescription pd = new PointDescription(
PointDescription.POINT_TYPE_MAP_MARKER, markerNew.getName() != null ? markerNew.getName() : "");
MapMarker marker = new MapMarker(m.point, pd, m.colorIndex, m.selected, m.index);
marker.id = m.id;
marker.creationDate = m.creationDate;
marker.visitedDate = m.visitedDate;
markersHelper.moveMapMarker(marker, latLonNew);
refreshMap();
return true;
}
}
}
return false;

View file

@ -49,6 +49,7 @@ import net.osmand.aidl.maplayer.point.ShowMapPointParams;
import net.osmand.aidl.maplayer.point.UpdateMapPointParams;
import net.osmand.aidl.mapmarker.AddMapMarkerParams;
import net.osmand.aidl.mapmarker.RemoveMapMarkerParams;
import net.osmand.aidl.mapmarker.RemoveMapMarkersParams;
import net.osmand.aidl.mapmarker.UpdateMapMarkerParams;
import net.osmand.aidl.mapwidget.AddMapWidgetParams;
import net.osmand.aidl.mapwidget.RemoveMapWidgetParams;
@ -75,7 +76,6 @@ import net.osmand.aidl.search.SearchParams;
import net.osmand.aidl.search.SearchResult;
import net.osmand.aidl.tiles.ASqliteDbFile;
import net.osmand.plus.OsmandApplication;
import net.osmand.plus.routing.VoiceRouter;
import net.osmand.util.Algorithms;
import org.apache.commons.logging.Log;
@ -282,7 +282,7 @@ public class OsmandAidlService extends Service implements AidlCallbackListener {
public boolean removeMapMarker(RemoveMapMarkerParams params) {
try {
OsmandAidlApi api = getApi("removeMapMarker");
return params != null && api != null && api.removeMapMarker(params.getMarker());
return params != null && api != null && api.removeMapMarker(params.getMarker(), params.getIgnoreCoordinates());
} catch (Exception e) {
handleException(e);
return false;
@ -293,7 +293,7 @@ public class OsmandAidlService extends Service implements AidlCallbackListener {
public boolean updateMapMarker(UpdateMapMarkerParams params) {
try {
OsmandAidlApi api = getApi("updateMapMarker");
return params != null && api != null && api.updateMapMarker(params.getMarkerPrev(), params.getMarkerNew());
return params != null && api != null && api.updateMapMarker(params.getMarkerPrev(), params.getMarkerNew(), params.getIgnoreCoordinates());
} catch (Exception e) {
handleException(e);
return false;
@ -1163,6 +1163,17 @@ public class OsmandAidlService extends Service implements AidlCallbackListener {
return UNKNOWN_API_ERROR;
}
}
@Override
public boolean removeAllActiveMapMarkers(RemoveMapMarkersParams params) {
try {
OsmandAidlApi api = getApi("removeAllActiveMapMarkers");
return api != null && api.removeAllActiveMapMarkers();
} catch (Exception e) {
handleException(e);
return false;
}
}
};
public static class AidlCallbackParams {

View file

@ -6,9 +6,16 @@ import android.os.Parcelable;
public class RemoveMapMarkerParams implements Parcelable {
private AMapMarker marker;
private boolean ignoreCoordinates;
public RemoveMapMarkerParams(AMapMarker marker) {
this.marker = marker;
this.ignoreCoordinates = false;
}
public RemoveMapMarkerParams(AMapMarker marker, boolean ignoreCoordinates) {
this.marker = marker;
this.ignoreCoordinates = ignoreCoordinates;
}
public RemoveMapMarkerParams(Parcel in) {
@ -30,12 +37,18 @@ public class RemoveMapMarkerParams implements Parcelable {
return marker;
}
public boolean getIgnoreCoordinates() {
return ignoreCoordinates;
}
public void writeToParcel(Parcel out, int flags) {
out.writeParcelable(marker, flags);
out.writeInt(ignoreCoordinates ? 1 : 0);
}
private void readFromParcel(Parcel in) {
marker = in.readParcelable(AMapMarker.class.getClassLoader());
ignoreCoordinates = in.readInt() != 0;
}
public int describeContents() {

View file

@ -0,0 +1,3 @@
package net.osmand.aidl.mapmarker;
parcelable RemoveMapMarkersParams;

View file

@ -0,0 +1,37 @@
package net.osmand.aidl.mapmarker;
import android.os.Parcel;
import android.os.Parcelable;
public class RemoveMapMarkersParams implements Parcelable {
public RemoveMapMarkersParams() {
}
public RemoveMapMarkersParams(Parcel in) {
readFromParcel(in);
}
public static final Creator<RemoveMapMarkersParams> CREATOR = new
Creator<RemoveMapMarkersParams>() {
public RemoveMapMarkersParams createFromParcel(Parcel in) {
return new RemoveMapMarkersParams(in);
}
public RemoveMapMarkersParams[] newArray(int size) {
return new RemoveMapMarkersParams[size];
}
};
public void writeToParcel(Parcel out, int flags) {
}
private void readFromParcel(Parcel in) {
}
public int describeContents() {
return 0;
}
}

View file

@ -7,10 +7,18 @@ public class UpdateMapMarkerParams implements Parcelable {
private AMapMarker markerPrev;
private AMapMarker markerNew;
private boolean ignoreCoordinates;
public UpdateMapMarkerParams(AMapMarker markerPrev, AMapMarker markerNew) {
this.markerPrev = markerPrev;
this.markerNew = markerNew;
this.ignoreCoordinates = false;
}
public UpdateMapMarkerParams(AMapMarker markerPrev, AMapMarker markerNew, boolean ignoreCoordinates) {
this.markerPrev = markerPrev;
this.markerNew = markerNew;
this.ignoreCoordinates = ignoreCoordinates;
}
public UpdateMapMarkerParams(Parcel in) {
@ -36,14 +44,20 @@ public class UpdateMapMarkerParams implements Parcelable {
return markerNew;
}
public boolean getIgnoreCoordinates() {
return ignoreCoordinates;
}
public void writeToParcel(Parcel out, int flags) {
out.writeParcelable(markerPrev, flags);
out.writeParcelable(markerNew, flags);
out.writeInt(ignoreCoordinates ? 1 : 0);
}
private void readFromParcel(Parcel in) {
markerPrev = in.readParcelable(AMapMarker.class.getClassLoader());
markerNew = in.readParcelable(AMapMarker.class.getClassLoader());
ignoreCoordinates = in.readInt() != 0;
}
public int describeContents() {

View file

@ -468,9 +468,9 @@ public class OsmAndFormatter {
return "Unknown Output Format!";
}
DecimalFormat degDf = new DecimalFormat("##0.00000",new DecimalFormatSymbols(Locale.US));
DecimalFormat minDf = new DecimalFormat("00.0000",new DecimalFormatSymbols(Locale.US));
DecimalFormat secDf = new DecimalFormat("00.000",new DecimalFormatSymbols(Locale.US));
DecimalFormat degDf = new DecimalFormat("##0.00000", new DecimalFormatSymbols(Locale.US));
DecimalFormat minDf = new DecimalFormat("00.000", new DecimalFormatSymbols(Locale.US));
DecimalFormat secDf = new DecimalFormat("00.0", new DecimalFormatSymbols(Locale.US));
StringBuilder sb = new StringBuilder();

View file

@ -190,6 +190,23 @@ public abstract class SettingsBaseActivity extends ActionBarPreferenceActivity
return propertyValue;
}
public static String getStringRouteInfoPropertyValue(Context ctx, String propertyValue) {
try {
if(propertyValue == null) {
return "";
}
final String propertyValueReplaced = propertyValue.replaceAll("\\s+","_");
Field f = R.string.class.getField("routeInfo_" + propertyValueReplaced + "_name");
if (f != null) {
Integer in = (Integer) f.get(null);
return ctx.getString(in);
}
} catch (Exception e) {
System.err.println(e.getMessage());
}
return propertyValue;
}
public SeekBarPreference createSeekBarPreference(OsmandPreference<Integer> b, int title, int summary, int dialogTextId, int defValue,
int maxValue) {
SeekBarPreference p = new SeekBarPreference(this, dialogTextId, defValue, maxValue);

View file

@ -92,7 +92,8 @@ import net.osmand.plus.monitoring.OsmandMonitoringPlugin;
import net.osmand.plus.routing.RouteCalculationResult;
import net.osmand.render.RenderingRuleProperty;
import net.osmand.render.RenderingRulesStorage;
import net.osmand.router.RouteStatistics;
import net.osmand.router.RouteStatisticsHelper;
import net.osmand.router.RouteStatisticsHelper.RouteSegmentAttribute;
import net.osmand.util.Algorithms;
import net.osmand.util.MapUtils;
@ -1269,7 +1270,7 @@ public class GpxUiHelper {
public static <E> BarData buildStatisticChart(@NonNull OsmandApplication app,
@NonNull HorizontalBarChart mChart,
@NonNull RouteStatistics.Statistics<E> routeStatistics,
@NonNull RouteStatisticsHelper.RouteStatistics routeStatistics,
@NonNull GPXTrackAnalysis analysis,
boolean useRightAxis,
boolean nightMode) {
@ -1286,12 +1287,12 @@ public class GpxUiHelper {
}
float divX = setupAxisDistance(app, yAxis, analysis.totalDistance);
List<RouteStatistics.RouteSegmentAttribute<E>> segments = routeStatistics.getElements();
List<RouteSegmentAttribute> segments = routeStatistics.elements;
List<BarEntry> entries = new ArrayList<>();
float[] stacks = new float[segments.size()];
int[] colors = new int[segments.size()];
for (int i = 0; i < stacks.length; i++) {
RouteStatistics.RouteSegmentAttribute segment = segments.get(i);
RouteSegmentAttribute segment = segments.get(i);
stacks[i] = segment.getDistance() / divX;
colors[i] = segment.getColor();
}

View file

@ -88,8 +88,8 @@ import net.osmand.plus.widgets.style.CustomTypefaceSpan;
import net.osmand.render.RenderingRuleSearchRequest;
import net.osmand.render.RenderingRulesStorage;
import net.osmand.router.RouteSegmentResult;
import net.osmand.router.RouteStatistics;
import net.osmand.router.RouteStatistics.Incline;
import net.osmand.router.RouteStatisticsHelper;
import net.osmand.router.RouteStatisticsHelper.RouteStatistics;
import net.osmand.router.TransportRoutePlanner.TransportRouteResult;
import net.osmand.router.TransportRoutePlanner.TransportRouteResultSegment;
import net.osmand.util.Algorithms;
@ -362,33 +362,24 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
buildRowDivider(cardsContainer, false);
slopeDataSet = statisticCard.getSlopeDataSet();
elevationDataSet = statisticCard.getElevationDataSet();
if (gpx.hasAltitude) {
List<RouteSegmentResult> route = app.getRoutingHelper().getRoute().getOriginalRoute();
if (route != null) {
RenderingRulesStorage currentRenderer = app.getRendererRegistry().getCurrentSelectedRenderer();
RenderingRulesStorage defaultRender = app.getRendererRegistry().defaultRender();
MapRenderRepositories maps = app.getResourceManager().getRenderer();
RenderingRuleSearchRequest currentSearchRequest = maps.getSearchRequestWithAppliedCustomRules(currentRenderer, isNightMode());
RenderingRuleSearchRequest defaultSearchRequest = maps.getSearchRequestWithAppliedCustomRules(defaultRender, isNightMode());
List<RouteSegmentResult> route = app.getRoutingHelper().getRoute().getOriginalRoute();
if (route != null) {
RenderingRulesStorage currentRenderer = app.getRendererRegistry().getCurrentSelectedRenderer();
RenderingRulesStorage defaultRender = app.getRendererRegistry().defaultRender();
RouteStatistics routeStatistics = RouteStatistics.newRouteStatistic(route, currentRenderer, defaultRender, currentSearchRequest, defaultSearchRequest);
GPXTrackAnalysis analysis = gpx.getAnalysis(0);
MapRenderRepositories maps = app.getResourceManager().getRenderer();
RenderingRuleSearchRequest currentSearchRequest = maps.getSearchRequestWithAppliedCustomRules(currentRenderer, isNightMode());
RenderingRuleSearchRequest defaultSearchRequest = maps.getSearchRequestWithAppliedCustomRules(defaultRender, isNightMode());
RouteInfoCard routeClassCard = new RouteInfoCard(mapActivity, routeStatistics.getRouteClassStatistic(), analysis);
List<RouteStatistics> routeStatistics = RouteStatisticsHelper.calculateRouteStatistic(route,
currentRenderer, defaultRender, currentSearchRequest, defaultSearchRequest);
GPXTrackAnalysis analysis = gpx.getAnalysis(0);
for (RouteStatistics statistic : routeStatistics) {
RouteInfoCard routeClassCard = new RouteInfoCard(mapActivity, statistic, analysis);
addRouteCard(cardsContainer, routeClassCard);
RouteInfoCard routeSurfaceCard = new RouteInfoCard(mapActivity, routeStatistics.getRouteSurfaceStatistic(), analysis);
addRouteCard(cardsContainer, routeSurfaceCard);
if (slopeDataSet != null) {
List<Incline> inclines = createInclinesAndAdd100MetersWith0Incline(slopeDataSet.getValues(), slopeDataSet.getDivX());
RouteInfoCard routeSteepnessCard = new RouteInfoCard(mapActivity, routeStatistics.getRouteSteepnessStatistic(inclines), analysis);
addRouteCard(cardsContainer, routeSteepnessCard);
}
RouteInfoCard routeSmoothnessCard = new RouteInfoCard(mapActivity, routeStatistics.getRouteSmoothnessStatistic(), analysis);
addRouteCard(cardsContainer, routeSmoothnessCard);
}
}
routeDetailsMenu = new RouteDetailsMenu();
@ -1517,36 +1508,6 @@ public class RouteDetailsFragment extends ContextMenuFragment implements PublicT
((LinearLayout) view).addView(horizontalLine);
}
private List<Incline> createInclinesAndAdd100MetersWith0Incline(List<Entry> entries, float divX) {
float minIncline = 0;
float maxIncline = 0;
int size = entries.size();
List<Incline> inclines = new ArrayList<>();
for (Entry entry : entries) {
float inclineValue = entry.getY();
maxIncline = Math.max(inclineValue, maxIncline);
minIncline = Math.min(inclineValue, minIncline);
Incline incline = new Incline(inclineValue, entry.getX() * divX);
inclines.add(incline);
}
for (int i = 0; i < 10; i++) {
float distance = i * 5;
inclines.add(i, new Incline(0f, distance));
}
if (slopeDataSet != null) {
float lastDistance = slopeDataSet.getEntryForIndex(size - 1).getX();
for (int i = 1; i <= 10; i++) {
float distance = lastDistance * divX + i * 5f;
inclines.add(new Incline(0f, distance));
}
}
for (Incline incline : inclines) {
incline.computeBoundaries(minIncline, maxIncline);
}
return inclines;
}
private void makeGpx() {
OsmandApplication app = requireMyApplication();
gpx = GpxUiHelper.makeGpxFromRoute(app.getRoutingHelper().getRoute(), app);

View file

@ -25,32 +25,28 @@ import net.osmand.GPXUtilities.GPXTrackAnalysis;
import net.osmand.plus.OsmAndFormatter;
import net.osmand.plus.R;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.activities.SettingsBaseActivity;
import net.osmand.plus.activities.SettingsNavigationActivity;
import net.osmand.plus.helpers.GpxUiHelper;
import net.osmand.router.RouteStatistics.Boundaries;
import net.osmand.router.RouteStatistics.RouteSegmentAttribute;
import net.osmand.router.RouteStatistics.Statistics;
import net.osmand.router.RouteStatisticsHelper.RouteSegmentAttribute;
import net.osmand.router.RouteStatisticsHelper.RouteStatistics;
import net.osmand.util.Algorithms;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.Map;
import static net.osmand.router.RouteStatistics.UNDEFINED_ATTR;
public class RouteInfoCard extends BaseCard {
private static final int MINIMUM_CONTRAST_RATIO = 3;
private Statistics routeStatistics;
private RouteStatistics routeStatistics;
private GPXTrackAnalysis analysis;
private String selectedPropertyName;
private boolean showLegend;
public RouteInfoCard(MapActivity mapActivity, Statistics routeStatistics, GPXTrackAnalysis analysis) {
public RouteInfoCard(MapActivity mapActivity, RouteStatistics routeStatistics, GPXTrackAnalysis analysis) {
super(mapActivity);
this.routeStatistics = routeStatistics;
this.analysis = analysis;
@ -71,7 +67,7 @@ public class RouteInfoCard extends BaseCard {
return (HorizontalBarChart) view.findViewById(R.id.chart);
}
private <E> void updateContent(final Statistics<E> routeStatistics) {
private void updateContent(final RouteStatistics routeStatistics) {
updateHeader();
final HorizontalBarChart chart = (HorizontalBarChart) view.findViewById(R.id.chart);
GpxUiHelper.setupHorizontalGPXChart(app, chart, 5, 9, 24, true, nightMode);
@ -82,7 +78,7 @@ public class RouteInfoCard extends BaseCard {
chart.setOnChartValueSelectedListener(new OnChartValueSelectedListener() {
@Override
public void onValueSelected(Entry e, Highlight h) {
List<RouteSegmentAttribute<E>> elems = routeStatistics.getElements();
List<RouteSegmentAttribute> elems = routeStatistics.elements;
int i = h.getStackIndex();
if (i >= 0 && elems.size() > i) {
selectedPropertyName = elems.get(i).getPropertyName();
@ -117,7 +113,7 @@ public class RouteInfoCard extends BaseCard {
});
}
protected <E> void updateLegend(Statistics<E> routeStatistics) {
protected void updateLegend(RouteStatistics routeStatistics) {
LinearLayout container = (LinearLayout) view.findViewById(R.id.route_items);
container.removeAllViews();
attachLegend(container, routeStatistics);
@ -130,33 +126,17 @@ public class RouteInfoCard extends BaseCard {
private void updateHeader() {
TextView title = (TextView) view.findViewById(R.id.info_type_title);
String name = getInfoType();
String name = SettingsBaseActivity.getStringRouteInfoPropertyValue(app, routeStatistics.name);
title.setText(name);
}
private String getInfoType() {
switch (routeStatistics.getStatisticType()) {
case CLASS:
return app.getString(R.string.road_types);
case STEEPNESS:
return app.getString(R.string.route_steepness_stat_container);
case SMOOTHNESS:
return app.getString(R.string.route_smoothness_stat_container);
case SURFACE:
return app.getString(R.string.route_surface_stat_container);
default:
return "";
}
}
private <E> void attachLegend(ViewGroup container, Statistics<E> routeStatistics) {
Map<E, RouteSegmentAttribute<E>> partition = routeStatistics.getPartition();
List<Map.Entry<E, RouteSegmentAttribute<E>>> list = new ArrayList<>(partition.entrySet());
sortRouteSegmentAttributes(list);
private void attachLegend(ViewGroup container, RouteStatistics routeStatistics) {
Map<String, RouteSegmentAttribute> partition = routeStatistics.partition;
List<Map.Entry<String, RouteSegmentAttribute>> list = new ArrayList<>(partition.entrySet());
ContextThemeWrapper ctx = new ContextThemeWrapper(mapActivity, !nightMode ? R.style.OsmandLightTheme : R.style.OsmandDarkTheme);
LayoutInflater inflater = LayoutInflater.from(ctx);
for (Map.Entry<E, RouteSegmentAttribute<E>> entry : list) {
RouteSegmentAttribute<E> segment = entry.getValue();
for (Map.Entry<String, RouteSegmentAttribute> entry : list) {
RouteSegmentAttribute segment = entry.getValue();
View view = inflater.inflate(R.layout.route_details_legend, container, false);
int segmentColor = segment.getColor();
Drawable circle = app.getUIUtilities().getPaintedIcon(R.drawable.ic_action_circle, segmentColor);
@ -166,9 +146,9 @@ public class RouteInfoCard extends BaseCard {
if (contrastRatio < MINIMUM_CONTRAST_RATIO) {
legendIcon.setBackgroundResource(nightMode ? R.drawable.circle_contour_bg_dark : R.drawable.circle_contour_bg_light);
}
String propertyName = segment.getPropertyName();
String propertyName = segment.getUserPropertyName();
String name = SettingsNavigationActivity.getStringPropertyName(app, propertyName, propertyName.replaceAll("_", " "));
Spannable text = getSpanLegend(name, segment, segment.getPropertyName().equals(selectedPropertyName));
Spannable text = getSpanLegend(name, segment, segment.getUserPropertyName().equals(selectedPropertyName));
TextView legend = (TextView) view.findViewById(R.id.legend_text);
legend.setText(text);
@ -176,30 +156,6 @@ public class RouteInfoCard extends BaseCard {
}
}
private <E> void sortRouteSegmentAttributes(List<Map.Entry<E, RouteSegmentAttribute<E>>> list) {
Collections.sort(list, new Comparator<Map.Entry<E, RouteSegmentAttribute<E>>>() {
@Override
public int compare(Map.Entry<E, RouteSegmentAttribute<E>> o1, Map.Entry<E, RouteSegmentAttribute<E>> o2) {
Object key1 = o1.getKey();
Object key2 = o2.getKey();
if (key1 instanceof String && key2 instanceof String) {
float distance1 = o1.getValue().getDistance();
float distance2 = o2.getValue().getDistance();
if (((String) key1).equalsIgnoreCase(UNDEFINED_ATTR) || distance1 < distance2) {
return 1;
}
if (((String) key2).equalsIgnoreCase(UNDEFINED_ATTR) || distance1 > distance2) {
return -1;
}
} else if (key1 instanceof Boundaries && key2 instanceof Boundaries) {
return ((Boundaries) key1).compareTo((Boundaries) key2);
}
return 0;
}
});
}
private Spannable getSpanLegend(String title, RouteSegmentAttribute segment, boolean selected) {
String formattedDistance = OsmAndFormatter.getFormattedDistance(segment.getDistance(), getMyApplication());
title = Algorithms.capitalizeFirstLetter(title);

View file

@ -60,6 +60,7 @@ import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import javax.xml.parsers.FactoryConfigurationError;
import javax.xml.parsers.ParserConfigurationException;
@ -1145,6 +1146,22 @@ public class RouteProvider {
}
lats[index] = params.end.getLatitude();
lons[index] = params.end.getLongitude();
Set<LatLon> impassableRoads = params.ctx.getAvoidSpecificRoads().getImpassableRoads().keySet();
double[] nogoLats = new double[impassableRoads.size()];
double[] nogoLons = new double[impassableRoads.size()];
double[] nogoRadi = new double[impassableRoads.size()];
if(impassableRoads.size() != 0) {
int nogoindex = 0;
for (LatLon nogos : impassableRoads) {
nogoLats[nogoindex] = nogos.getLatitude();
nogoLons[nogoindex] = nogos.getLongitude();
nogoRadi[nogoindex] = 10;
nogoindex++;
}
}
if (params.mode.isDerivedRoutingFrom(ApplicationMode.PEDESTRIAN)) {
mode = "foot"; //$NON-NLS-1$
} else if (params.mode.isDerivedRoutingFrom(ApplicationMode.BICYCLE)) {
@ -1155,6 +1172,9 @@ public class RouteProvider {
Bundle bpars = new Bundle();
bpars.putDoubleArray("lats", lats);
bpars.putDoubleArray("lons", lons);
bpars.putDoubleArray("nogoLats", nogoLats);
bpars.putDoubleArray("nogoLons", nogoLons);
bpars.putDoubleArray("nogoRadi", nogoRadi);
bpars.putString("fast", params.fast ? "1" : "0");
bpars.putString("v", mode);
bpars.putString("trackFormat", "gpx");

View file

@ -1,9 +1,7 @@
package net.osmand.plus.views;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.support.v4.content.ContextCompat;
import android.view.View;
import android.view.View.OnClickListener;
@ -11,7 +9,6 @@ import android.widget.ImageButton;
import android.widget.LinearLayout;
import net.osmand.data.RotatedTileBox;
import net.osmand.plus.ApplicationMode;
import net.osmand.plus.OsmandApplication;
import net.osmand.plus.OsmandSettings;
import net.osmand.plus.R;
@ -38,7 +35,6 @@ import net.osmand.plus.views.mapwidgets.RouteInfoWidgetsFactory.RulerWidget;
import net.osmand.plus.views.mapwidgets.RouteInfoWidgetsFactory.TimeControlWidgetState;
import net.osmand.plus.views.mapwidgets.TextInfoWidget;
import java.lang.reflect.Field;
import static net.osmand.plus.views.mapwidgets.MapWidgetRegistry.*;
public class MapInfoLayer extends OsmandMapLayer {
@ -360,32 +356,4 @@ public class MapInfoLayer extends OsmandMapLayer {
public boolean drawInScreenPixels() {
return true;
}
public static String getStringPropertyName(Context ctx, String propertyName, String defValue) {
try {
Field f = R.string.class.getField("rendering_attr_" + propertyName + "_name");
if (f != null) {
Integer in = (Integer) f.get(null);
return ctx.getString(in);
}
} catch (Exception e) {
System.err.println(e.getMessage());
}
return defValue;
}
public static String getStringPropertyDescription(Context ctx, String propertyName, String defValue) {
try {
Field f = R.string.class.getField("rendering_attr_" + propertyName + "_description");
if (f != null) {
Integer in = (Integer) f.get(null);
return ctx.getString(in);
}
} catch (Exception e) {
//e.printStackTrace();
System.err.println(e.getMessage());
}
return defValue;
}
}
}