diff --git a/GPX.md b/GPX.md new file mode 100644 index 0000000000..8ab3640620 --- /dev/null +++ b/GPX.md @@ -0,0 +1,158 @@ +The OsmAnd's GPX file format conforms to GPX 1.1 specification with additional data written as extensions. There are few sections of such data: + +## Track appearance +These parameters are used to customize the appearance of a track on the map. Used inside "gpx" tag and applies to all tracks inside gpx. +#### Parameters +* **show_arrows** [*true, false*] - show / hide arrows along the path line. +* **width** [*thin, medium, bold, 1-24*] - width of a track line on the map. The thin, medium and bold are style depended values (should be defined as currentTrackWidth attribute). +* **color** [*#AARRGGBB, #RRGGBB*] - color of a track line on the map. Hex values. +* **split_type** [*no_split, distance, time*] - split type for a track. +* **split_interval** [*double*] - split interval for a track. Distance (meters), time (seconds). + +#### Example: +```xml + +... + + true + #4e4eff + distance + 2000.0 + bold + + +``` +## Details of a track point (trkpt) +Written to a gpx file while recording a track. +* **speed** (meters per second) +* **heading** (0-359 degrees) + +#### Example: +```xml + + 203 + + 3 + + 273 + 5.02 + + +``` + +## Calculated route(s) +This data contains information about a route built with **OsmAnd** (route segments, turns, road names and types, restrictions, etc.). With their help, route can be restored completely as if it had just been built even without the currently installed offline maps. + +There can be several routes in one gpx file. Each of them is contained in a specific segment (**trkseg** / **extensions**). In this form, a gpx file is saved when exporting a constructed route or when saving a track that consists of several separate segments via the **Plan route**. +When using the **Plan route** tool, route key points (**rtept**) are additionally written to the gpx file. There can also be several **rte** blocks (according to a number of separate segments / tracks in a gpx file). + +#### Gpx structure: +```xml + + + + + + + + + + + + + + + + + + + + + + + + + + ... + + ... + + + +``` + +#### Example: +```xml + + + Fri 06 Nov 2020 + + + Fri 06 Nov 2020 + + + 0.801 + + + 0.998 + + + 1 + + + 0.963 + + + 0.899 + + + .... + + + + + + + + ... + + + + + + + + ... + + + + + + + + + pedestrian + 0 + + + + + pedestrian + 24 + + + + + pedestrian + 89 + + + + + pedestrian + 121 + + + + +``` diff --git a/OsmAnd/src/net/osmand/plus/audionotes/AudioNotesLayer.java b/OsmAnd/src/net/osmand/plus/audionotes/AudioNotesLayer.java index 20b9ac2d93..ea0694aa8d 100644 --- a/OsmAnd/src/net/osmand/plus/audionotes/AudioNotesLayer.java +++ b/OsmAnd/src/net/osmand/plus/audionotes/AudioNotesLayer.java @@ -13,6 +13,7 @@ import net.osmand.data.PointDescription; import net.osmand.data.QuadRect; import net.osmand.data.QuadTree; import net.osmand.data.RotatedTileBox; +import net.osmand.plus.OsmandApplication; import net.osmand.plus.R; import net.osmand.plus.activities.MapActivity; import net.osmand.plus.audionotes.AudioVideoNotesPlugin.Recording; @@ -69,8 +70,9 @@ public class AudioNotesLayer extends OsmandMapLayer implements @Override public void onPrepareBufferImage(Canvas canvas, RotatedTileBox tileBox, DrawSettings settings) { if (tileBox.getZoom() >= startZoom) { - float textScale = activity.getMyApplication().getSettings().TEXT_SCALE.get(); - float iconSize = getIconSize(activity) * 3 / 2.5f * textScale; + OsmandApplication app = activity.getMyApplication(); + float textScale = app.getSettings().TEXT_SCALE.get(); + float iconSize = getIconSize(app); QuadTree boundIntersections = initBoundIntersections(tileBox); DataTileManager recs = plugin.getRecordings(); diff --git a/OsmAnd/src/net/osmand/plus/osmedit/OsmBugsLayer.java b/OsmAnd/src/net/osmand/plus/osmedit/OsmBugsLayer.java index da6dd2bdd3..ff2554dfe6 100644 --- a/OsmAnd/src/net/osmand/plus/osmedit/OsmBugsLayer.java +++ b/OsmAnd/src/net/osmand/plus/osmedit/OsmBugsLayer.java @@ -104,20 +104,21 @@ public class OsmBugsLayer extends OsmandMapLayer implements IContextMenuProvider @Override public void onPrepareBufferImage(Canvas canvas, RotatedTileBox tileBox, DrawSettings settings) { - startZoom = activity.getMyApplication().getSettings().SHOW_OSM_BUGS_MIN_ZOOM.get(); + OsmandApplication app = activity.getMyApplication(); + startZoom = app.getSettings().SHOW_OSM_BUGS_MIN_ZOOM.get(); if (tileBox.getZoom() >= startZoom) { // request to load data.queryNewData(tileBox); List objects = data.getResults(); if (objects != null) { - float textScale = activity.getMyApplication().getSettings().TEXT_SCALE.get(); - float iconSize = getIconSize(activity) * 3 / 2.5f * textScale; + float textScale = app.getSettings().TEXT_SCALE.get(); + float iconSize = getIconSize(app); QuadTree boundIntersections = initBoundIntersections(tileBox); List fullObjects = new ArrayList<>(); List fullObjectsLatLon = new ArrayList<>(); List smallObjectsLatLon = new ArrayList<>(); - boolean showClosed = activity.getMyApplication().getSettings().SHOW_CLOSED_OSM_BUGS.get(); + boolean showClosed = app.getSettings().SHOW_CLOSED_OSM_BUGS.get(); for (OpenStreetNote o : objects) { if (!o.isOpened() && !showClosed) { continue; diff --git a/OsmAnd/src/net/osmand/plus/views/OsmandMapLayer.java b/OsmAnd/src/net/osmand/plus/views/OsmandMapLayer.java index 2b00b9f498..67e046c1de 100644 --- a/OsmAnd/src/net/osmand/plus/views/OsmandMapLayer.java +++ b/OsmAnd/src/net/osmand/plus/views/OsmandMapLayer.java @@ -1,6 +1,5 @@ package net.osmand.plus.views; -import android.content.Context; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.ColorFilter; @@ -44,6 +43,7 @@ import java.util.Map; public abstract class OsmandMapLayer { + public static final float ICON_VISIBLE_PART_RATIO = 0.45f; protected List fullObjectsLatLon; protected List smallObjectsLatLon; @@ -235,8 +235,8 @@ public abstract class OsmandMapLayer { return (int) (r * tb.getDensity()); } - protected int getIconSize(Context ctx) { - return ctx.getResources().getDimensionPixelSize(R.dimen.favorites_icon_outline_size); + protected float getIconSize(OsmandApplication app) { + return app.getResources().getDimensionPixelSize(R.dimen.favorites_icon_outline_size) * ICON_VISIBLE_PART_RATIO * app.getSettings().TEXT_SCALE.get(); } public Rect getIconDestinationRect(float x, float y, int width, int height, float scale) { diff --git a/OsmAnd/src/net/osmand/plus/views/layers/FavouritesLayer.java b/OsmAnd/src/net/osmand/plus/views/layers/FavouritesLayer.java index d0a1b91d8b..8cfc3025dd 100644 --- a/OsmAnd/src/net/osmand/plus/views/layers/FavouritesLayer.java +++ b/OsmAnd/src/net/osmand/plus/views/layers/FavouritesLayer.java @@ -95,7 +95,7 @@ public class FavouritesLayer extends OsmandMapLayer implements ContextMenuLayer. if (this.settings.SHOW_FAVORITES.get() && favorites.isFavoritesLoaded()) { if (tileBox.getZoom() >= startZoom) { float textScale = this.settings.TEXT_SCALE.get(); - float iconSize = getIconSize(view.getContext()) * 3 / 2.5f * textScale; + float iconSize = getIconSize(view.getApplication()); QuadTree boundIntersections = initBoundIntersections(tileBox); // request to load diff --git a/OsmAnd/src/net/osmand/plus/views/layers/GPXLayer.java b/OsmAnd/src/net/osmand/plus/views/layers/GPXLayer.java index 46d51bca33..b960b643bf 100644 --- a/OsmAnd/src/net/osmand/plus/views/layers/GPXLayer.java +++ b/OsmAnd/src/net/osmand/plus/views/layers/GPXLayer.java @@ -494,7 +494,7 @@ public class GPXLayer extends OsmandMapLayer implements IContextMenuProvider, IM private void drawSelectedFilesPoints(Canvas canvas, RotatedTileBox tileBox, List selectedGPXFiles) { if (tileBox.getZoom() >= START_ZOOM) { float textScale = view.getSettings().TEXT_SCALE.get(); - float iconSize = getIconSize(view.getContext()) * 3 / 2.5f * textScale; + float iconSize = getIconSize(view.getApplication()); QuadTree boundIntersections = initBoundIntersections(tileBox); List fullObjectsLatLon = new ArrayList<>(); diff --git a/OsmAnd/src/net/osmand/plus/views/layers/POIMapLayer.java b/OsmAnd/src/net/osmand/plus/views/layers/POIMapLayer.java index ed0f2cc45d..13352a81ee 100644 --- a/OsmAnd/src/net/osmand/plus/views/layers/POIMapLayer.java +++ b/OsmAnd/src/net/osmand/plus/views/layers/POIMapLayer.java @@ -200,7 +200,7 @@ public class POIMapLayer extends OsmandMapLayer implements ContextMenuLayer.ICon objects = data.getResults(); if (objects != null) { float textScale = app.getSettings().TEXT_SCALE.get(); - float iconSize = getIconSize(app) * 1.5f * textScale; + float iconSize = getIconSize(app); QuadTree boundIntersections = initBoundIntersections(tileBox); WaypointHelper wph = app.getWaypointHelper(); PointImageDrawable pointImageDrawable = PointImageDrawable.getOrCreate(view.getContext(), @@ -394,7 +394,8 @@ public class POIMapLayer extends OsmandMapLayer implements ContextMenuLayer.ICon public int getTextShift(Amenity amenity, RotatedTileBox rb) { int radiusPoi = getRadiusPoi(rb); if (isPresentInFullObjects(amenity.getLocation())) { - radiusPoi += (getIconSize(app) - app.getResources().getDimensionPixelSize(R.dimen.favorites_icon_size_small)) / 2; + radiusPoi += (app.getResources().getDimensionPixelSize(R.dimen.favorites_icon_outline_size) + - app.getResources().getDimensionPixelSize(R.dimen.favorites_icon_size_small)) / 2; } return radiusPoi; } diff --git a/OsmAnd/src/net/osmand/plus/views/layers/TransportStopsLayer.java b/OsmAnd/src/net/osmand/plus/views/layers/TransportStopsLayer.java index 2eb4f27956..ba219f26b6 100644 --- a/OsmAnd/src/net/osmand/plus/views/layers/TransportStopsLayer.java +++ b/OsmAnd/src/net/osmand/plus/views/layers/TransportStopsLayer.java @@ -20,6 +20,7 @@ import net.osmand.data.RotatedTileBox; import net.osmand.data.TransportStop; import net.osmand.osm.edit.Node; import net.osmand.osm.edit.Way; +import net.osmand.plus.OsmandApplication; import net.osmand.plus.base.PointImageDrawable; import net.osmand.plus.settings.backend.CommonPreference; import net.osmand.plus.settings.backend.OsmandSettings; @@ -181,10 +182,11 @@ public class TransportStopsLayer extends OsmandMapLayer implements ContextMenuLa public void onPrepareBufferImage(Canvas canvas, RotatedTileBox tb, DrawSettings settings) { List objects = null; boolean nightMode = settings.isNightMode(); + OsmandApplication app = mapActivity.getMyApplication(); if (tb.getZoom() >= startZoomRoute) { if (stopRoute != null) { objects = stopRoute.route.getForwardStops(); - int color = stopRoute.getColor(mapActivity.getMyApplication(), nightMode); + int color = stopRoute.getColor(app, nightMode); attrs.paint.setColor(color); attrs.updatePaints(view.getApplication(), settings, tb); try { @@ -217,8 +219,8 @@ public class TransportStopsLayer extends OsmandMapLayer implements ContextMenuLa } if (objects != null) { - float textScale = mapActivity.getMyApplication().getSettings().TEXT_SCALE.get(); - float iconSize = getIconSize(mapActivity) * 3 / 2.5f * textScale; + float textScale = app.getSettings().TEXT_SCALE.get(); + float iconSize = getIconSize(app); QuadTree boundIntersections = initBoundIntersections(tb); List fullObjects = new ArrayList<>(); for (TransportStop o : objects) { @@ -228,7 +230,7 @@ public class TransportStopsLayer extends OsmandMapLayer implements ContextMenuLa if (intersects(boundIntersections, x, y, iconSize, iconSize)) { PointImageDrawable pointImageDrawable = PointImageDrawable.getOrCreate(mapActivity, ContextCompat.getColor(mapActivity, R.color.transport_stop_icon_background), - true,false ,0, BackgroundType.SQUARE); + true, false, 0, BackgroundType.SQUARE); pointImageDrawable.setAlpha(0.9f); pointImageDrawable.drawSmallPoint(canvas, x, y, textScale); } else {