feat(train): routes out and in as GPX (ADR 0030, D45)

A route's page shares it as GPX 1.1 (Android's share sheet, else saved
where the person chooses): its way a track with elevations, its
waypoints and turns as named points. A GPX file comes in from the Routes
tab or, on Android, opened with Train or shared to it; it is planned
along the paths through its points or kept as drawn, then named and
saved as a new route.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Signed-off-by: Tizian 「ティツィアーン」 <raisondetredev@pm.me>
This commit is contained in:
Tizian 「ティツィアーン」 2026-10-29 10:44:47 +01:00
commit 5ff9b2e053
Signed by: raisondetredev
GPG key ID: 07F6FCF405488B64
5 changed files with 1190 additions and 5 deletions

View file

@ -405,6 +405,15 @@
"routeAscent": "{metres} m bergauf",
"routeDescent": "{metres} m bergab",
"routeSummary": "{distance} · {ascent}",
"routesBringIn": "GPX-Datei hereinholen",
"routeBringInTitle": "{name} hereinholen",
"routeBringInSnap": "Entlang der Wege planen",
"routeBringInSnapHint": "Durch ihre Punkte, mit dem Profil deiner Wahl; ihre Abzweigungen angesagt",
"routeBringInDrawn": "So lassen, wie sie ist",
"routeBringInDrawnHint": "Ihr Weg, wie ihn die Datei hat, ohne Ansagen",
"routeNotGpx": "In dieser Datei steckt keine Route, die Train lesen kann",
"routeShareGpx": "Als GPX teilen",
"routeSaveGpx": "Als GPX speichern",
"routeOffline": "Karte offline behalten",
"routeOfflineOff": "Die Karte entlang des Wegs, 2 km zu beiden Seiten, auf diesem Gerät für unterwegs ohne Netz",
"routeOfflineLoading": "Karte wird gespeichert: {done} von {total} Kacheln",

View file

@ -513,6 +513,17 @@
"@routeDescent": {"placeholders": {"metres": {"type": "int"}}},
"routeSummary": "{distance} · {ascent}",
"@routeSummary": {"description": "A route in the list: its distance and climb.", "placeholders": {"distance": {"type": "String", "example": "12.3 km"}, "ascent": {"type": "String", "example": "120 m up"}}},
"routesBringIn": "Bring in a GPX file",
"@routesBringIn": {"description": "In the Routes tab: a route brought in from a GPX file (ADR 0030, D45)."},
"routeBringInTitle": "Bring in {name}",
"@routeBringInTitle": {"placeholders": {"name": {"type": "String", "example": "Isar loop"}}},
"routeBringInSnap": "Plan it along the paths",
"routeBringInSnapHint": "Through its points, with the profile you choose; its turns told",
"routeBringInDrawn": "Keep it as drawn",
"routeBringInDrawnHint": "Its way as the file has it, no turns told",
"routeNotGpx": "This file holds no route Train can read",
"routeShareGpx": "Share as GPX",
"routeSaveGpx": "Save as GPX",
"routeOffline": "Keep the map offline",
"@routeOffline": {"description": "A switch on a saved route: its map kept on this device (ADR 0030, D45)."},
"routeOfflineOff": "Its map along the way, 2 km either side, on this device for when there's no network",

View file

@ -2452,6 +2452,60 @@ abstract class AppLocalizations {
/// **'{distance} · {ascent}'**
String routeSummary(String distance, String ascent);
/// In the Routes tab: a route brought in from a GPX file (ADR 0030, D45).
///
/// In en, this message translates to:
/// **'Bring in a GPX file'**
String get routesBringIn;
/// No description provided for @routeBringInTitle.
///
/// In en, this message translates to:
/// **'Bring in {name}'**
String routeBringInTitle(String name);
/// No description provided for @routeBringInSnap.
///
/// In en, this message translates to:
/// **'Plan it along the paths'**
String get routeBringInSnap;
/// No description provided for @routeBringInSnapHint.
///
/// In en, this message translates to:
/// **'Through its points, with the profile you choose; its turns told'**
String get routeBringInSnapHint;
/// No description provided for @routeBringInDrawn.
///
/// In en, this message translates to:
/// **'Keep it as drawn'**
String get routeBringInDrawn;
/// No description provided for @routeBringInDrawnHint.
///
/// In en, this message translates to:
/// **'Its way as the file has it, no turns told'**
String get routeBringInDrawnHint;
/// No description provided for @routeNotGpx.
///
/// In en, this message translates to:
/// **'This file holds no route Train can read'**
String get routeNotGpx;
/// No description provided for @routeShareGpx.
///
/// In en, this message translates to:
/// **'Share as GPX'**
String get routeShareGpx;
/// No description provided for @routeSaveGpx.
///
/// In en, this message translates to:
/// **'Save as GPX'**
String get routeSaveGpx;
/// A switch on a saved route: its map kept on this device (ADR 0030, D45).
///
/// In en, this message translates to:

View file

@ -1464,6 +1464,38 @@ class AppLocalizationsDe extends AppLocalizations {
return '$distance · $ascent';
}
@override
String get routesBringIn => 'GPX-Datei hereinholen';
@override
String routeBringInTitle(String name) {
return '$name hereinholen';
}
@override
String get routeBringInSnap => 'Entlang der Wege planen';
@override
String get routeBringInSnapHint =>
'Durch ihre Punkte, mit dem Profil deiner Wahl; ihre Abzweigungen angesagt';
@override
String get routeBringInDrawn => 'So lassen, wie sie ist';
@override
String get routeBringInDrawnHint =>
'Ihr Weg, wie ihn die Datei hat, ohne Ansagen';
@override
String get routeNotGpx =>
'In dieser Datei steckt keine Route, die Train lesen kann';
@override
String get routeShareGpx => 'Als GPX teilen';
@override
String get routeSaveGpx => 'Als GPX speichern';
@override
String get routeOffline => 'Karte offline behalten';

View file

@ -1456,6 +1456,37 @@ class AppLocalizationsEn extends AppLocalizations {
return '$distance · $ascent';
}
@override
String get routesBringIn => 'Bring in a GPX file';
@override
String routeBringInTitle(String name) {
return 'Bring in $name';
}
@override
String get routeBringInSnap => 'Plan it along the paths';
@override
String get routeBringInSnapHint =>
'Through its points, with the profile you choose; its turns told';
@override
String get routeBringInDrawn => 'Keep it as drawn';
@override
String get routeBringInDrawnHint =>
'Its way as the file has it, no turns told';
@override
String get routeNotGpx => 'This file holds no route Train can read';
@override
String get routeShareGpx => 'Share as GPX';
@override
String get routeSaveGpx => 'Save as GPX';
@override
String get routeOffline => 'Keep the map offline';