I want to create an offline library of
USGS
Topo maps that
will
serve as a navigational backup for my local area.
Whether I find myself at a trail head without downloaded maps, or
some cataclysmic event has disabled mobile data access,
I want a reliable source of high quality maps.
Using my
usgsassist script and newly implemented
map compression, I can easily grab and store large swaths of maps on
a single SD card. So creating this repository should be a breeze.
The first question is, what's my local area? I'm located in Northern
Virginia, and for this exercise I decided to cast a (very) wide net.
I opted to grab all the topo maps from the
northern
boundary of Pennsylvania
to the
southern
boundary of Virginia.
That's almost 6 hours of driving in any direction. Surely that's
overkill for my 'local area,' but having a broader area adds to
the likelihood that this repository will save the day.
You can grab the latest version of usgsassist from
github.
OK, let's build this!
Building the Library
# Grab a list of maps in the area of interest
$ usgsassist -a topos -l "PA, USA; VA, USA" > area.maps
# Spot check the list
# Looks like we got them all, from: Abilene to Zelienople.
$ wc -l area.maps
3363 area.maps
$ head -3 area.maps
Abilene, VA|2022-09-14|https://prd-tnm.s3.amazonaws.com/StagedProducts/Maps/USTopo/PDF/VA/VA_Abilene_20220914_TM_geo.pdf|-78.625|37.125|-78.5|37.25
Abingdon, VA|2022-09-16|https://prd-tnm.s3.amazonaws.com/StagedProducts/Maps/USTopo/PDF/VA/VA_Abingdon_20220916_TM_geo.pdf|-82|36.625|-81.875|36.75
Accomac, VA|2022-08-31|https://prd-tnm.s3.amazonaws.com/StagedProducts/Maps/USTopo/PDF/VA/VA_Accomac_20220831_TM_geo.pdf|-75.75|37.625|-75.625|37.75
$ tail -3 area.maps
Zanesville East, OH 2019|2019-12-02|https://prd-tnm.s3.amazonaws.com/StagedProducts/Maps/USTopo/PDF/OH/OH_Zanesville_East_20191202_TM_geo.pdf|-82|39.875|-81.875|40
Zanesville West, OH 2019|2019-12-03|https://prd-tnm.s3.amazonaws.com/StagedProducts/Maps/USTopo/PDF/OH/OH_Zanesville_West_20191203_TM_geo.pdf|-82.125|39.875|-82|40
Zelienople, PA 2019|2019-09-04|https://prd-tnm.s3.amazonaws.com/StagedProducts/Maps/USTopo/PDF/PA/PA_Zelienople_20190904_TM_geo.pdf|-80.25|40.75|-80.125|40.875
# Download and compress each map
# Download each map to map.pdf
# Then store the compressed map as the name provided by the USGS
$ cat area.maps | cut -d'|' -f3 | \
while read url ; do \
name=$(basename $url) ; \
echo $name ; \
curl -s $url > map.pdf ; \
pdfimages -a remove -i map.pdf -o $name ; \
done
VA_Abilene_20220914_TM_geo.pdf
VA_Abingdon_20220916_TM_geo.pdf
...
# Copy to an SD Card
$ sudo mount -t drvfs 'D:' /mnt/d
$ cp -Rv area/ /mnt/d/
'area/' -> '/mnt/d/area'
'area/NY_Port_Jervis_North_20190923_TM_geo.pdf' -> '/mnt/d/area/NY_Port_Jervis_North_20190923_TM_geo.pdf'
'area/WV_Porters_Falls_20191210_TM_geo.pdf' -> '/mnt/d/area/WV_Porters_Falls_20191210_TM_geo.pdf'
'area/WV_Romance_20191209_TM_geo.pdf' -> '/mnt/d/area/WV_Romance_20191209_TM_geo.pdf'
...
After a lengthy, but thankfully unattended downloading process, all
3,363 maps downloaded to my laptop. I was able to put these maps on
a single 128GB SD card with
space to spare. I confirmed that I can access the map files from my
cell phone via an SD card reader:
So now what?
While it's comforting that I have this repository, there are
issues with it. The most glaring one being: how would I actually use
it? More specifically, how would I find the few maps of interest out
of the 3,000+ that are on the SD card?
I'll be answering that question in a future post. For now, I want to
tackle a simpler question: what area
does this library cover?
I'm confident that the maps from 'northern Pennsylvania' to
'southern Virginia' has me covered, but what does that area include?
I searched for web services that would let me visualize this,
and ultimately landed on a delightfully simple option:
the
Google Static Maps API.
This API is allows you to craft a URL that
describes the map you're looking for and Google will serve up an
image of said map. How have I never used this
capability before?
I implemented
usgsassist
-a preview
by creating a Static Maps URL that includes a
path
definition which outlines the area of interest in purple. The
path coordinates are made up of the bounding box returned by
usgsassist -a geobox. This sounds complex, but it turned
out to be straightforward to implement.
Here's the URL generated by my map library's bounding box (minus my
Google Maps key):
$ usgsassist -a preview -l "PA, USA; VA, USA" | sed 's/key=[^&]*/key=XXX/'
https://maps.googleapis.com/maps/api/staticmap?size=500x500&key=XXX&path=color:purple|42.5141658,-74.6895018|42.5141658,-83.675415|36.5407589,-83.675415|36.5407589,-74.6895018|42.5141658,-74.6895018
Here's the corresponding image Google generated:
Sweet, right? This URL can be trivially passed to curl to download the
image. I've stored the image on the SD card with the maps to provide
additional context.
$ curl -s $(usgsassist -a preview -l "PA, USA; VA, USA") > ~/dl/area.png
In general, this preview command takes the guess work out of figuring out what
area usgsassist -a topos is going to include.
Next up I'll tackle the challenge of actually using this map library.