|
(function () { |
|
const API_KEY = '3p0t5s6b5g4g0e8k3c1j3w7y5c3m4t8i'; |
|
const URL = 'https://www.alltrails.com/api/alltrails/trails/'; |
|
const DETAILS_LEVEL = 'medium'; |
|
|
|
function decoded_objects_from_polyline(t) { |
|
var e = [5, 5]; |
|
length = t.length, |
|
dimensions = e.length; |
|
var i = 0 |
|
, n = 0 |
|
, a = 0 |
|
, r = 0; |
|
for (buffer = new Array(dimensions * length,0), |
|
bufferCount = 0; i < length; ) { |
|
r = null; |
|
for (var s = 0; s < dimensions; s++) { |
|
a = 0, |
|
n = 0; |
|
do { |
|
if (i >= length) |
|
break; |
|
r = t.charCodeAt(i++) - 63, |
|
a |= (31 & r) << n, |
|
n += 5 |
|
} while (r >= 32);delta = 0 != (1 & a) ? ~(a >> 1) : a >> 1, |
|
lastValue = 0 == bufferCount ? 0 : buffer[(bufferCount - 1) * dimensions + s], |
|
buffer[bufferCount * dimensions + s] = Math.round((lastValue + Math.pow(10, -e[s]) * delta) * Math.pow(10, e[s])) / Math.pow(10, e[s]) |
|
} |
|
bufferCount += 1 |
|
} |
|
return buffer = buffer, |
|
rows = bufferCount, |
|
res = [], |
|
buffer.each_slice(dimensions, function(t) { |
|
res.push(t) |
|
}), |
|
res |
|
} |
|
|
|
function download(obj) { |
|
var a = window.document.createElement('a'); |
|
a.href = window.URL.createObjectURL(new Blob([obj.text], {type: 'text/xml'})); |
|
a.download = obj.name; |
|
document.body.appendChild(a); |
|
a.click(); |
|
document.body.removeChild(a); |
|
} |
|
|
|
function createKml(obj) { |
|
var kml = '<?xml version="1.0" encoding="UTF-8"?><kml xmlns="http://www.opengis.net/kml/2.2"><Document><name>' + obj.name + '</name><Placemark><name>' + obj.name + '</name><LineString><altitudeMode>relativeToGround</altitudeMode><coordinates>'; |
|
kml += obj.pointsData.map(function (p) { |
|
return p.reverse().join() + ',0'; |
|
}).join(' '); |
|
kml += '</coordinates></LineString></Placemark></Document></kml>'; |
|
return {name:obj.name.replace(/[^\w]/ig,'')+'.kml', text:kml}; |
|
} |
|
|
|
function processResponse(response) { |
|
var trail = response.trails[0]; |
|
var pointsData = decoded_objects_from_polyline(trail.defaultMap.routes[0].lineSegments[0].polyline.pointsData); |
|
return {name:trail.name, url:document.location.href, pointsData:pointsData}; |
|
} |
|
|
|
function getTrailsData(trailId) { |
|
return $.ajax({ |
|
url: URL + trailId + '?detail=' + DETAILS_LEVEL, |
|
type: "GET", |
|
beforeSend: function (xhr) { |
|
xhr.setRequestHeader('x-at-key', API_KEY); |
|
} |
|
}); |
|
} |
|
|
|
function getTrailId() { |
|
var dfd = jQuery.Deferred(); |
|
var alternateEl = $('link[rel="alternate"]')[0]; |
|
var data = $('li.favorite-menu').attr('data-react-props'); |
|
if (alternateEl) { |
|
dfd.resolve($('link[rel="alternate"]')[0].href.split('/').pop()); |
|
} else if (data) { |
|
dfd.resolve(JSON.parse(data).trailId); |
|
} else { |
|
dfd.reject('Could not identify the trail ID. Please enter a trail specific page.'); |
|
} |
|
return dfd.promise(); |
|
} |
|
|
|
function init() { |
|
getTrailId().then(getTrailsData, console.error) |
|
.then(processResponse) |
|
.then(createKml) |
|
.then(download); |
|
} |
|
|
|
Array.prototype.each_slice = function(t, e) { |
|
for (var i = 0, n = this.length; i < n; i += t) e.call(this, this.slice(i, i + t)); |
|
} |
|
|
|
init(); |
|
|
|
})(); |