Skip to content

alexcojocaru/geo-data-exchange

Repository files navigation

geo-data-exchange

Node.js CI , coverage: 99%

Transform a GPX or Leaflet track to GeoJSON

A Javascript UMD module to transform a GPX track or a Leaflet track (given as an array of LatLng points) to a GeoJSON feature collection. The given points are grouped into features based on the elevation grade change between subsequent points in the track. Each feature is of type LineString and has an attributeType property set to its elevation grade level. The FeatureCollection element itself has a records property set to the feature count, as well as a summary property set to gradient. See the example below for details.

The elevation grade levels are defined here.

Since it is quite possible that some points on the GPX track do not have an elevation coordinate, the track grades are calculated using only the points with elevation.

After this, the elevation interpolation and the grade normalization are applied (if enabled via options) as follows:

  • elevation interpolation: Given a point B without elevation between two points A and C with elevation, the algorithm calculates the gradient GR between A and C, and interpolates the elevation for B, so that the gradient between A and B is GR and between B and C is also GR. This is not an accurate technique, and its results could be far from reality.
  • grade normalization: Given a track with many elevation changes within a short distance, the gradient might change very often. Plotting it on a chart will result in gradient changes every few pixels, which makes the chart look very busy. The normalization algorithm takes 2 parameters: the chart width (in pixels) and the minimum gradient length (in pixel). As the algorithm parses the track and finds a new gradient, it will merge a short one (i.e. shorter than min length when rendered) with the subsequent one(s), so that the resulting gradient is longer than min length.

This is an example of how such a FeatureCollection looks like. More examples of such feature collections can be found in the unit tests.

[{
    "features": [
        {
            "geometry": {
                "coordinates": [
                    [2.218, 1.108, 8],
                    [2.2185, 1.1085, 8],
                    [2.220, 1.110, 10]
                ],
                "type": "LineString"
            },
            "properties": {
                "attributeType": 0
            },
            "type": "Feature"
        },
        {
            "geometry": {
                "coordinates": [
                    [2.220, 1.110, 10],
                    [2.222, 1.112, 20]
                ],
                "type": "LineString"
            },
            "properties": {
                "attributeType": 1
            },
            "type": "Feature"
        }
    ],
    "properties": {
        "Creator": "github.com/alexcojocaru/geo-data-exchange",
        "records": 2,
        "summary": "gradient"
    },
    "type": "FeatureCollection"
}]

The initial goal of this project was to enable the generation of feature collections, using the elevation grade level for grouping. Here is an example of using such a feature collection to mark various grade levels on an elevation graph:

heightgraph

NB: The GPX track to GeoJSON transformation is WIP.

Usage

The module is not published to the npm registry because of its leaking users' email addresses. Instead, it can be referenced via it's Github URL).

First, add this module as a dependency to your project:

$ npm install alexcojocaru/geo-data-exchange

or, if you want a specific version/commit/branch (e.g. v2.1.0):

$ npm install alexcojocaru/geo-data-exchange#v2.1.0

The main function is buildGeojsonFeatures(latLngs, options) (documentation here), exposed externally as exports.buildGeojsonFeatures, which takes an array of Leaflet LatLng objects, as well as an optional options object.

There is a set of default transformation options (documentation here), exposed externally as exports.defaultOptions, which could be used as prototype for creating custom options to pass to the transformation function.

There are more functions, not documented, exposed externally via the internal namespace, mainly for visibility for unit testing; since they are internal, they might change at any time, even between patch versions.

Dependencies

  • Leaflet: for the LatLng type usage, for distance calculations, etc

Build

The artifact is generated in the dist directory. The code is not minified; that is because after minification with uglify-js, even with the mangle and compress options disabled, the IIFE did not work as expected.

Build a package

$ npm run build

Test

Run the unit tests with:

$ npm run test

or, even better, run them with coverage reporting enabled:

$ npm run test-coverage

Test coverage

Every time the tests are ran with coverage reporting enabled, the overall coverage at the top of the README is updated, along with the summary below.

Current test coverage

  % Statements: 99
  %   Branches: 97
  %  Functions: 100
  %      Lines: 99

Release

Build a release

First, build the package: npm run build, then commit the changes.

Then use one of the following commands, depending on what kind of release you need to build:

  • major release: npm version major
  • minor release: npm version minor
  • patch release: npm version patch

NB: If the version bump script fails to run, check that there are no files modified locally, in which case commit them or clean them up before running the process again.

Publish

To publish a release, first build it - that creates the dist file(s), increments the version number, commits and creates the git tag. After, push the newer commit(s), along with the new tag, to the server:

git push origin HEAD
git push origin <tag_name>

About

Transform a GPX or Leaflet track to GeoJSON

Resources

License

Stars

Watchers

Forks

Packages

No packages published