Giter Site home page Giter Site logo

opentracksapp / opentracks Goto Github PK

View Code? Open in Web Editor NEW
907.0 20.0 180.0 91.7 MB

OpenTracks is a sport tracking application that completely respects your privacy.

Home Page: https://OpenTracksApp.com

License: Apache License 2.0

Java 99.71% Ruby 0.05% Shell 0.25%
android sport tracking heartrate bluetooth-low-energy outdoor offline gps privacy

opentracks's Introduction

OpenTracks logo OpenTracks: a sport tracker

OpenTracks is a sport tracking application that completely respects your privacy.

Awesome Humane Tech

Free (F-Droid) Free (Nightly for F-Droid) Donations
Get it on F-Droid Nightly builds (for F-Droid client) Donate using Liberapay
OpenTracks version published on F-Droid Get it on Google Play

Translations are hosted on hosted.weblate.org. Translation status

Screenshots

Features

  • Tracking: track your sport and outdoor activities

  • Voice announcements

  • Photos and Markers: mark interesting locations while tracking

  • Export:

    • export tracks either as KMZ 2.3 (incl. photos), KML 2.3, or GPX 1.1
    • export automatically after each recording (e.g., to sync via Nextcloud)
    • avoid duplication: each exported file contain a random unique identifier (i.e., opentracks:trackid)
  • Altitude:

    • gain/loss via barometric sensor (if present)
    • shown in EGM2008 (above mean sea level); exported as WGS84
  • Bluetooth LE sensors:

    • heart rate
    • cycling: speed and distance
    • cycling: cadence
    • cycling: power meter
    • running: speed and cadence
    • support for BLE sensor training only (i.e., without GPS) for indoor training

    An overview of tested sensors: README_TESTED_SENSORS.md

Gadgetbridge integration

OpenTracks can be used with Gadgetbridge:

  • shows statistics via notification on smart watches (requires Gadgetbridge 0.56.1 or later), and
  • Gadgetbridge's GPX exporter generates opentracks:trackid to avoid duplication (Gadgetbridge 0.53.0 or later).

Privacy

  • No Internet access: Internet is not used
  • No advertising
  • No in-app analytics
  • No use of Google Play Services

Only required permissions:

  • ACCESS_FINE_LOCATION: required to use the GPS.
  • ACCESS_BACKGROUND_LOCATION: required to start recording with GPS while phone is in standby. (e.g. when triggered by Public API from an external device)

Public API

OpenTracks includes an API for starting/stopping recording by another installed application (e.g., Automate, Tasker, or Easer). The API can be invoked by sending an explicit Intent to start an activity.

Package (depends on the variant installed):

  • F-Droid: de.dennisguse.opentracks
  • GooglePlay: de.dennisguse.opentracks.playStore
  • Debug: de.dennisguse.opentracks.debug
  • Nightly: de.dennisguse.opentracks.nightly

Class:

  • Start a recording: de.dennisguse.opentracks.publicapi.StartRecording
  • Stop a recording: de.dennisguse.opentracks.publicapi.StopRecording

For testing via adb: adb shell am start -e someParameter someValue -n "package/class"

StartRecording supports the following parameters:

  • Set track data: TRACK_NAME, TRACK_DESCRIPTION, TRACK_CATEGORY, and TRACK_ICON (non-localized identifier see /src/main/java/de/dennisguse/opentracks/util/TrackIconUtils.java#L38). NOTE: if TRACK_ICON is not present, TRACK_CATEGORY will be used to determine the icon (localized).
  • Send recorded data to another application via Dashboard API: STATS_TARGET_PACKAGE and STATS_TARGET_CLASS

The Public API is disabled by default to protect the user's privacy, but it can easily be enabled in the settings.

File formats compatibility with open-source software

GPX 1.1 KML 2.3 KMZ 2.3
OpenLayers 7.1.0 ? no no
Golden Cheetah 3.5 ? no no
GpxPod ? ? ?
OsmAnd ? no no
FitTrackee yes n/a n/a
SportsTracker yes, single tracks only no no
ExifTool yes no no

Dashboard API (incl. map)

As of v3.3.1, OpenTracks supports custom dashboards for displaying previously recorded and live tracks.

The reference implementation is OSMDashboard, which presents an OpenStreetMap map (showing the current track, incl. updates). The Dashboard API is also used by Gadgetbridge for displaying live track statistics on supported wearables.

Alternatively, recorded tracks can be shared as KMZ/GPX with installed applications ( e.g., OsmAnd). However, this is rather slow and does not provide updates while recording.

The developer documentation is in README_API.md.

Project history

OpenTracks is based upon Google My Tracks app (code). My Tracks was initially released by Google in 2010 as open-source software. In 2016, Google decided to discontinue My Tracks and stopped distributing it via the Google Play store in April 2016. Then Plonk42 conducted some maintenance work until 2016, so My Tracks could still be used (based upon version Google's MyTracks version 2.0.6). Plonk42's version is available here. In 2019, OpenTracks was forked from Plonk42's My Tracks and major rework was conducted.

Rework of OpenTracks included:

  • removing Google's analytics code,
  • removing integration into Google Drive,
  • removing Google Maps integration,
  • removing Google Earth integration,
  • removing use of Google Play service,
  • removing calorie estimation and activity estimation,
  • removing support for ANT+ and Classic Bluetooth,
  • adding support for Bluetooth LE heart rate sensors,
  • removing Protobuf (store sensor data in SQLite columns directly), and
  • removing Android Service API for other apps.

Artwork, logos and user interface remained more or less unchanged.

More information about Google My Tracks:

opentracks's People

Contributors

anom-human avatar ch3thanhs avatar comradekingu avatar dennisguse avatar dependabot[bot] avatar fjuro avatar ftno avatar hercek avatar jaredcasper avatar jkasten2 avatar jrgert avatar lmarz avatar mm4c avatar nclmde avatar plonk42 avatar plum7x avatar pstorch avatar rdamazio avatar rgmf avatar simmonmt avatar steffenhorlacher avatar stephan-p avatar suburbanno avatar tea-nt avatar thrillfall avatar transifex-integration[bot] avatar unbiaseduser avatar vsevjednom-cz avatar weblate avatar xmgz avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

opentracks's Issues

Move keys.xml into code

For some reason preference keys were extracted to keys.xml.
Moving them back into the code (e.g., PreferenceUtils) would make the code more readable.

Rework stats_layout

The stats_layout (used by TrackDetailActivity) has highly nested layout.
This should be simplified to make maintenance easier as well as the layout faster.

Using GridLayout would an option.

Continuous integration

Enable Continuous integration (TravisCI?) to format the code as well as execute tests.

  • configure CI (build)
  • setup CI
  • configure CI (test)

Blocked by #5.

[FR] GadgetBridge data fetching

As the app supports heart rate then it's easier getting it from a fitness tracker. And subj is one open platform which can provide this info from a number of fitness trackers. Gpx available from some trackers too.

Bug: does not reconnect sensor?

It seems that reconnecting to the heart rate sensor is not working resulting in such diagrams.
Workaround: Stopping and starting a new track works.

Screenshot_20191013-094812_OpenTracks

ShareOnMap: make amount of data configurable

At the moment, the whole track as KMZ without sensor data is transferred.
However, this does also includes track name as well as timestamps.

It would be great to make this configurable of the user.

Share track with map application

OpenTracks cannot (and will not be able) to show tracks directly on a map.
However, sharing the record track data with an installed map application should be available.
Then, the user can select in which application the data should be shown.

Implement it so that only location information is transferred (e.g., no sensors, no timestamps, no images, no description, no activity).

Migrate to androidx Preferences

Migration to androidx Preferences (deprecated) was done in v3.2.1
Next step is to migrate to androidx Preferences (most recent API).

This also includes fixing the summary of the default activity preference.
And check if the workaround for ´stats_rate_key´ is still needed.

Fix string resource to be plurals (if needed)

<issue id="PluralsCandidate" severity="Warning" message="Formatting %d followed by words (&quot;hours&quot;): This should probably be a plural rather than a string" category="Correctness:Messages" priority="5" summary="Potential Plurals" explanation="...." url="http://developer.android.com/guide/topics/resources/string-resource.html#Plurals" errorLine1=" &lt;string name=&quot;voice_hours_few&quot;>%1$d hours&lt;/string>" errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> </issue>

See LINT warnings for a complete list of entries.

Bug: heart rate is not shown although being recorded

While recording (and being connected to a heart rate sensor), the heart rate is properly shown.

When going to the chart view and back, the heart rate is not shown anymore although the connection to the sensor is still ok.
However, StatsFragment complains that it connect to the TrackRecordingService and thus does not show any data.

https://github.com/dennisguse/OpenTracks/blob/a413a4c4981caaa6b8346d00832e7ce064e03b43/src/main/java/de/dennisguse/opentracks/fragments/StatsFragment.java#L306

Workaround: go back to the list view showing all tracks and open the currently recording track.

Continue a stopped track

At the moment, after stopping a track it cannot be continued.
This behavior, however, is quite annoying if you stopped tracking by mistake.

Present elevation gain (via barometer)

GPS data is usually to imprecise to record the elevation gain (therefore it was disabled in OpenTracks).
Use the barometer to record the elevation gain.

Export to KML

At the moment, export (via menu->export all) does not allow to export as KML.
If KML is chosen, the data is exported as zipped KML (i.e., KMZ).

TrackListActivity: gps not yet fixed

In TrackListActivity the user can start the gps - it would be great to show an icon saying "gps online, but no fix yet".
Currently, the "gps got a fix"-icon is shown immediately.

Use ic_gps_not_fixed.

Share track: incl. actual track data

At the moment, only a summary (as text) is shared while not sharing the actual data.
Needs to be done in ShareActionProvider while the actual data needs to be stored in a temporary file.

Add a FAQ/help section

It would be great to have a FAQ/help section in the app.
For example:

  • steps to connect to a heart rate sensor
  • what can go wrong with a heart rate sensor
    • what is required
    • what does not work (e.g., devices)
  • limitations of GPS sensors (in terms of precision and startup time)
  • how to export and import tracks (amount of data varies by file type; KMZ being the most complete)
  • how to show recorded data (other app that can do that, e.g., OsmAND~, MapsMe)

Show direction via compass while recording

While recording, showing the direction via compass (if available) would be very helpful.
UI needs to be added to TrackDetailActivity.

Gathered data must not (yet) be stored.

PS: Add a new task to store the compass direction if not yet implemented.

Crash when opening Settings activity

Thanks for this great app!

I have searched open issues but didn't find this one, sorry if i have missed it.

For some reason, after a while, settings stopped working - when i try to open settings screen, app crashes.

Version V3.2.1, from F-Droid.
Samsung S7 Edge, Android 8.

Below is adb shell logcat

thank you

10-21 19:04:03.697  3671 14055 D ActivityManager: isScaleDownAnimationEnabled() : false
10-21 19:04:03.698  3671 14055 V WindowManager: rotationForOrientationLw(orient=-1, last=0); user=0  sensorRotation=-1 mLidState=-1 mDockMode=0 mHdmiPlugged=false
10-21 19:04:03.702  3671 14055 D PersonaManagerService: Current focused persona service handled id set to : 0
10-21 19:04:03.702  3671 14055 D InputDispatcher: Focused application set to: xxxx
10-21 19:04:03.705  3671 14055 D InputDispatcher: Focus left window: 18097
10-21 19:04:03.707  3671  3962 D GameManagerService: handleForegroundChange(). pkgName: de.dennisguse.opentracks, clsName: de.dennisguse.opentracks.settings.SettingsActivity,FgActivityName:de.dennisguse.opentracks/.settings.SettingsActivity
10-21 19:04:03.707  3671  3962 D GameManagerService:   handleForegroundChange(). same package with Prev KILL_YOURSELF. ignore
10-21 19:04:03.708  3671 14055 D MARsPolicyManager: onPackageResumedFG pkgName = de.dennisguse.opentracks, userId = 0
10-21 19:04:03.716 18097 18097 D ViewRootImpl@4a19370[TrackDetailActivity]: MSG_WINDOW_FOCUS_CHANGED 1
10-21 19:04:03.717  3671 14055 D InputMethodManagerService: startInputOrWindowGainedFocus : windowGainedFocus 
10-21 19:04:03.717  3671 14055 D InputMethodManagerService: windowGainedFocus: destinationUserId (getCallingUid) = 0
10-21 19:04:03.717  3671 14055 D InputMethodManagerService: windowGainedFocus: currentUserId=0
10-21 19:04:03.717  3671 14055 D InputMethodManagerService: windowGainedFocus: mCurrentFocusedUserId=0
10-21 19:04:03.718  3671 14055 D InputMethodManagerService: windowGainedFocus : lock - currentUserId = 0 destinationUserId = 0
10-21 19:04:03.718  3671 14055 D InputMethodManagerService: windowGainedFocus : mCurrentFocusedUserId - 0 and mSecureKeypadEnabled - false, userSwitched - false
10-21 19:04:03.718  3671 14055 W InputMethodManagerService: Focus gain on non-focused client com.android.internal.view.IInputMethodClient$Stub$Proxy@cba9bf4 (uid=10041 pid=18097)
10-21 19:04:03.718  3671 14055 W InputMethodManagerService: calledFromValidUser : true, (mCurFocusedWindow == windowToken) : true, (attribute != null) : false
10-21 19:04:03.718  3671 14055 W InputMethodManagerService: (mCurClient != cs) : false, mCurFocusedWindow : android.os.BinderProxy@4c83c2, windowToken : android.os.BinderProxy@4c83c2
10-21 19:04:03.718 18097 18097 E ViewRootImpl: sendUserActionEvent() returned.
10-21 19:04:03.730 18097 18097 D AndroidRuntime: Shutting down VM
10-21 19:04:03.731 18097 18097 E AndroidRuntime: FATAL EXCEPTION: main
10-21 19:04:03.731 18097 18097 E AndroidRuntime: Process: de.dennisguse.opentracks, PID: 18097
10-21 19:04:03.731 18097 18097 E AndroidRuntime: java.lang.RuntimeException: Unable to start activity ComponentInfo{de.dennisguse.opentracks/de.dennisguse.opentracks.settings.SettingsActivity}: java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2957)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3032)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.ActivityThread.-wrap11(Unknown Source:0)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1696)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.os.Handler.dispatchMessage(Handler.java:105)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.os.Looper.loop(Looper.java:164)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.ActivityThread.main(ActivityThread.java:6944)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at java.lang.reflect.Method.invoke(Native Method)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at com.android.internal.os.Zygote$MethodAndArgsCaller.run(Zygote.java:327)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1374)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: Caused by: java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.SharedPreferencesImpl.getString(SharedPreferencesImpl.java:255)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.Preference.getPersistedString(Preference.java:1686)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.ListPreference.onSetInitialValue(ListPreference.java:255)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.Preference.onSetInitialValue(Preference.java:1614)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.Preference.dispatchSetInitialValue(Preference.java:1587)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.Preference.onAttachedToHierarchy(Preference.java:1311)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.Preference.onAttachedToHierarchy(Preference.java:1326)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceGroup.addPreference(PreferenceGroup.java:249)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceGroup.addItemFromInflater(PreferenceGroup.java:170)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceInflater.rInflate(PreferenceInflater.java:345)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceInflater.rInflate(PreferenceInflater.java:346)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceInflater.inflate(PreferenceInflater.java:157)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceInflater.inflate(PreferenceInflater.java:109)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceManager.inflateFromResource(PreferenceManager.java:216)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceFragment.addPreferencesFromResource(PreferenceFragment.java:386)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at de.dennisguse.opentracks.settings.SettingsActivity$PrefsFragment.onCreatePreferences(SettingsActivity.java:65)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at androidx.preference.PreferenceFragment.onCreate(PreferenceFragment.java:167)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.Fragment.performCreate(Fragment.java:2593)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:1234)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentManagerImpl.addAddedFragments(FragmentManager.java:2421)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentManagerImpl.executeOpsTogether(FragmentManager.java:2200)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentManagerImpl.removeRedundantOperationsAndExecute(FragmentManager.java:2154)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:2055)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentManagerImpl.dispatchMoveToState(FragmentManager.java:3050)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentManagerImpl.dispatchActivityCreated(FragmentManager.java:2997)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.FragmentController.dispatchActivityCreated(FragmentController.java:179)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.Activity.performCreateCommon(Activity.java:7177)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.Activity.performCreate(Activity.java:7185)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1220)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2910)
10-21 19:04:03.731 18097 18097 E AndroidRuntime: 	... 9 more
10-21 19:04:03.737  3671 14055 D Debug   : !@DumpState : SHIP
10-21 19:04:03.738  3671 14055 D Debug   : !@DumpState : debug level:0x4f4c
10-21 19:04:03.738  3671 14055 D Debug   : !@Dumpstate : Finally, system will skip dumpstate
10-21 19:04:03.738  3671 14055 W ActivityManager: crash : de.dennisguse.opentracks,0
10-21 19:04:03.739  3671 14055 W ActivityManager:   Force finishing activity de.dennisguse.opentracks/.settings.SettingsActivity
10-21 19:04:03.748  3671 14055 W ActivityManager:   Force finishing activity de.dennisguse.opentracks/.TrackDetailActivity

Bluetooth sensors: add multiple sensors

Add support for recording the speed via a Bluetooth LE Speed Sensor and use this to show the current speed while recording.
Especially for cycling GPS based speed is to imprecise.

Speed data should also be recorded in the database.

Remove default preferences from code

The defaults for preferences are defined in code as well as in the xml-files.
This duplicates this information and will lead to problems if both get out of sync.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.