各地网友 GPS art 作品

GPX 是 GPS exchange 文件格式,被运动跟踪类的软硬件广泛使用。本篇做一个快速指南,帮助大家玩转 GPX。

动机
—

很多刚入门耐力运动的朋友,会有打卡需求。好不容易走了几十公里,在地图上画条线出来,放到朋友圈特别有面子。不过,只要跑得够多,就一定会遇到记录不完美的状况。

比如我第一次穿越港岛,走了差不多 25 K,结果在离终点 200m 的地方,手机停电了,于是打卡失败。

第一次穿越港岛,手机没电

另外一种情况,就是忘记停表/ 关App 了,结果关闭的时候,一瞬间飞了回去,在地图上划出一道长长直线。这个状况在用 Trail Watch 的时候,经常出现。

忘记关表的情况

第三类翻车,就是中途停下来休息,结果再出发时,别人开了表而自己忘了…… 等到想起来的时候,又是一条飞线,把最重要的山头给略过了。

休息后忘记开表的情况

第四类翻车,是由于各种意外,中途停表了(Apple Watch 很容易出现),结果本来一段 20K 的记录变成两段 10K 的。

出现以上情况,就问你难不难受?

所以,我们要学习 GPX。

基础
—

数据导出

Strava 上可以方便地导出 GPX 文件。

Strava 数据导出位置

Strava 还可以使用 API  来获取数据,对于开发者很有好。

Python 用户可以使用一个叫做 stravalib 的库,虽然上手方便,但不推荐。有一些主要问题:

•该库一个 activity 一个 HTTP request,很快会用完 quota。像我两年的记录,就无法在一天内获取完。

•由于 Strava 的升级,出现了一些新的 activity 类型,但该库的维护并不是很及时,loop 中遇到数据错误的时候,可能会前功尽弃。

推荐使用 request,直接调用 HTTP endpoint,一行可以搞定。

r = requests.get(
    'https://www.strava.com/api/v3/athlete/activities',
    params={
        'page': 1,
        'per_page': 100,
    },
    headers={
        'Authorization': 'Bearer {}'.format(access_token),
    }
)

一次 100 条,几秒钟就可以把一个人的记录给拉完了。

数据导入

还是以 Strava 为例。

先 upload activity。

在这里选择文件。上传 GPX 即可。

GPX

GPX 本质上是一种 XML 格式的文件。

它有三个层级,上一层可以包含多个下层元素:

•Track

•Segment

•Point

我们最关心的是 Point。

Point 的必要数据为:

•lat, lon, ele

•time

根据这些,可以推算时间、距离、爬升、速度等,基本的运动参数就有了。

另外,还有一些非标准的拓展数据,通常会被跑表记录,比如 Garmin 的表会录入这些数据:

•Temperature

•Heart rate

•Cadence

一个实际的 GPX 文件,长成这样。它是纯文本文件,所以可以用任何编辑器来编辑。

GPX 文件样例

裁剪
—

最简单的一个操作,在 Strava 上默认支持。如果是活动的首尾想去掉,那就非常简单了。

Strava 裁剪活动示例

如果想去掉的部分,位于活动的中间,那就只能约化(reduction)一下这个问题:

•Duplicate 该活动

•分别裁剪第一段和第二段

•转化为一个拼接问题

拼接
—

如果知道 GPX 文件的原理,自然拼接就很简单。

拿文本编辑器打开两个 GPX 文件。

其中一组 <trkpt ...> ...</trkpt> 中间的内容,就是一个记录点。所以你要做的,就是把一个文件中的这些  <trkpt ...> ...</trkpt> ,全部都拷贝到另一个文件中  <trkpt ...> ...</trkpt>  的后面即可。

GPX 文件样例

创造
—

这是用来解决手表完全停电的情况。可能你只能根据自己对路线的理解,把没记录的部分给画出来,再和已经记录的部分进行拼接。

画地图有很多工具,我个人比较喜欢的是:https://geojson.io/[1]

https://geojson.io/

GeoJSON 是一个流行的地理信息格式,深受 web 开发、可视化从业者的喜爱。所以,其对应的工具链也比较丰富。

在网站上用 polyline 画好地图后,下载成 geojson 格式。

转化为 gpx 的方式也很简单,模仿前面的文件格式,写一个模板,然后用 jinja2 给填上去就行。

GPX 文件模板

除了填模板外,这里有一些细节需要注意:

•Geojson 里面是没有时间的,但运动记录一定有时间。如果没有时间,会被报告格式非法。

•Strava 接受的时间格式是 “%Y-%m-%dT%H:%M:%S+08:00” ,其他字符串格式的时间表达,可能不会通过。

•第一个记录点的时间,需要比运动开始的时间晚一点(不知道为什么),否则可能报错。

•Strava 使用运动开始的时间来去重。所以如果多次创造轨迹的话,需要采用不同的时间。

当然,这些细节已经包括在我写的脚本里了,已经开源,大家可以直接用: https://github.com/hupili/geojson-to-gpx-with-time[2]

寄语
—

从此以后,妈妈再也不用担心你的表没电了。

REF
—

•[1] https://geojson.io/: https://geojson.io/

•[2] https://github.com/hupili/geojson-to-gpx-with-time: https://github.com/hupili/geojson-to-gpx-with-time

•[3] Have fun with GPX File : https://docs.google.com/presentation/d/1bYXCX1LiHKYHE7ADZyFckhjJFrieoH3horXawBaigVs/edit#slide=id.p

完
—

博闻 | 明察 | 躬行
心法 | 手艺 | 随想