TopoJSON: calculate scale and offset
Question:
Given the absolute coordinates, how do I calculate the ideal value for the
scale and translate for topojson topology transform?
I want to go from this:
absolute = [
[-69.9009900990099, 12.451814888520133],
[-69.9009900990099, 12.417091709170947],
[-69.97299729972997, 12.43445329884554],
[-70.00900090009, 12.486538067869319],
[-70.08100810081008, 12.538622836893097],
[-70.08100810081008, 12.590707605916876],
[-70.04500450045005, 12.608069195591469],
[-70.00900090009, 12.55598442656769],
[-69.93699369936994, 12.469176478194726],
[-69.9009900990099, 12.451814888520133],
]
To this:
scale = [0.036003600360036005, 0.017361589674592462]
translate = [-180, -89.99892578124998]
relative = [[3058, 5901], [0, -2], [-2, 1], [-1, 3], [-2, 3], [0, 3], [1, 1],
[1, -3], [2, -5], [1, -1]]
I got the relative-to-absolute conversion working:
def arc_to_coordinates(topology, arc):
scale = topology['transform']['scale']
translate = topology['transform']['translate']
x = 0
y = 0
coordinates = []
for point in arc:
x += point[0]
y += point[1]
coordinates.append([
x * scale[0] + translate[0],
y * scale[1] + translate[1]
])
return coordinates
Now I need to write the absolute-to-relative conversion. In order to to
this, it is necessary to get the values for scale and translate, where I'm
stuck.
About topojson
topojson is a format for storing geographic features much like geojson.
In order to save space (among other tricks), the format uses relative
integer offsets from the previous point. For example, this is the topojson
file for Aruba:
{
"type": "Topology",
"transform": {
"scale": [0.036003600360036005, 0.017361589674592462],
"translate": [-180, -89.99892578124998]
},
"objects": {
"aruba": {
"type": "Polygon",
"arcs": [[0]],
"id": 533
}
},
"arcs": [
[[3058, 5901], [0, -2], [-2, 1], [-1, 3], [-2, 3], [0, 3], [1, 1],
[1, -3], [2, -5], [1, -1]]
]
}
The same information as a GeoJSON feature looks like this:
{
"type" : "Feature",
"id" : 533,
"properties" : {},
"geometry" : {
"type" : "Polygon",
"coordinates" : [[
[-69.9009900990099, 12.451814888520133],
[-69.9009900990099, 12.417091709170947],
[-69.97299729972997, 12.43445329884554],
[-70.00900090009, 12.486538067869319],
[-70.08100810081008, 12.538622836893097],
[-70.08100810081008, 12.590707605916876],
[-70.04500450045005, 12.608069195591469],
[-70.00900090009, 12.55598442656769],
[-69.93699369936994, 12.469176478194726],
[-69.9009900990099, 12.451814888520133]
]]
}
}
It is easy to see how the former is more compact than the later. My
absolute to relative function is working:
>>> arc_to_coordinates(topology, topology['arcs'][0])
[[-69.9009900990099, 12.451814888520133],
[-69.9009900990099, 12.417091709170947],
[-69.97299729972997, 12.43445329884554],
[-70.00900090009, 12.486538067869319],
[-70.08100810081008, 12.538622836893097],
[-70.08100810081008, 12.590707605916876],
[-70.04500450045005, 12.608069195591469],
[-70.00900090009, 12.55598442656769],
[-69.93699369936994, 12.469176478194726],
[-69.9009900990099, 12.451814888520133]]
No comments:
Post a Comment