EmV
EmV

Reputation: 11

map inset in MarMap / including a marmap file in ggplot2

I have a marmap plot of a marine sanctuary, but as it's very zoomed in, i'm trying to include an inset of the US state it's in (Massachusetts).

currently, my code is as follows:

library(marmap)
stellie <- getNOAA.bathy(lon1 = -70.8, lon2 = -69.9,
                         lat1 = 42.8, lat2 = 41.7, resolution = 1) 
#area for marine sanctuary

blues <- colorRampPalette(c("purple","blue","cadetblue1","white"))
greens <- colorRampPalette(c("#00CC00", "#33CC33", "#009900", "#006633"))

#custom colours

plot(stellie, image = TRUE, land = TRUE, lwd = 0.4,
     bpal = list(c(0, max(stellie), greens(100)),
                     c(min(stellie),0,blues(100))),
     drawlabel = c(TRUE, FALSE, FALSE))
scaleBathy(stellie, deg = 0.17, x = "bottomleft", inset = 5)

#final plot

and i want to have this larger area of Boston included as an inset, or alongside the first map

boston <- getNOAA.bathy(lon1 = -72, lon2 = -69.7,
                        lat1 = 43, lat2 = 41.3, resolution = 1)
plot(boston, image = TRUE, land = TRUE, lwd = 0.4,
     bpal = list(c(0, max(boston), greens(100)),
             c(min(boston),0,blues(100))),
     drawlabel = c(TRUE, FALSE, FALSE))

I figure this is probably best done in ggplot, so I can include city names, but I'm not sure how to import a marmap file into ggplot.

Upvotes: 1

Views: 787

Answers (1)

Benoit
Benoit

Reputation: 1234

In this paper from Marine Biology, I think Fig. 1 is exactly what you are trying to achieve. So here is the script I used to produce this map, or at least the relevant lines of the script (careful: datasets are pretty heavy). The key here is to use packages grid and gridBase to create viewports. Each viewport can host a distinct plot, with distinct sets of coordinates.

# Load appropriate packages
library(raster) ; library(marmap) ; library(gridBase) ; library(grid)

# Get bathy for the world with a decent resolution (careful: ca. 21 Mo)
world <- getNOAA.bathy(-180, 180, -90, 90, res = 15, keep = TRUE)

# Get bathy for the study area with a 1 min resolution (careful: ca. 75 Mo)
bath <- getNOAA.bathy(35, 60, -25, 0, res = 1, keep = TRUE)

# Switch to raster, project, and go back to bathy object for the world map (rgdal needed)
world.ras <- marmap::as.raster(world)
ma.proj <-   "+proj=ortho
              +lat_0=0
              +lon_0=50
              +x_0=0
              +y_0=0"
world.ras.proj <- projectRaster(world.ras,crs = ma.proj)
world.proj <- as.bathy(world.ras.proj)

# Prepare color palettes
blues <- c(grey(.98))
greys <- c(grey(0.6), grey(0.93), grey(0.99))


# Make a nice plot...

    ### First, plot the study area
    plot.new()
    pushViewport(viewport())

    par(mar = c(4, 4, 1, 1))
    plot(bath, image = TRUE, land = TRUE, lwd = 0.05, bpal = list(c(0, max(bath), greys), c(min(bath),0,blues)),asp=1, las=1)
    plot(bath, deep = 0, shallow = 0, step = 0, lwd = 0.7, add = TRUE) # Coastline
    plot(bath, deep = -200, shallow = -200, step = 0, lwd = 0.5, draw=FALSE, add = TRUE) # -200m isobath
    plot(bath, deep = -1000, shallow = -1000, step = 0, lwd = 0.5, draw=FALSE, add = TRUE) # -1000m isobath
    scaleBathy(bath, deg=4.91, x=37, y=-24)

    ### Then, insert a world map on the top right corner
    pushViewport(viewport(x = 0.67, y = 0.97, width = 0.3, height = 0.3, just = c("left", "top")))
    grid.rect(gp = gpar(fill = "white", lwd = 0.5))
    par(plt = gridPLT(), bg = "white", new = TRUE)

    blues <- grey(.95)

    ### Plot worldmap: needs the "fixed" palette.bathy from v0.9 (na.rm=TRUE added in several places)
    plot(world.proj, image = TRUE, land = TRUE, n=0, lwd = 0.01, las = 1, bpal = list(c(0, max(world.proj, na.rm = T), grey(0.6), grey(0.99)), c(min(world.proj, na.rm = T), 0, blues)), asp = 1, axes = FALSE, xlab = "", ylab = "")
    plot(world.proj, deep = 0, shallow = 0, step = 0, lwd = 0.4, add = TRUE)

    ### add a frame with shadow
    n <- -30000 ; m <- -50000  # Shadow offset
    rect(-1290466 + n, -2648928.4 + m, 768012 + n, -590145.2 + m, border = col2alpha(1, .08), lwd = 7)
    rect(-1290466 + n, -2648928.4 + m, 768012 + n, -590145.2 + m, border = col2alpha(1, .08), lwd = 6)
    rect(-1290466 + n, -2648928.4 + m, 768012 + n, -590145.2 + m, border = col2alpha(1, .08), lwd = 5)
    rect(-1290466 + n, -2648928.4 + m, 768012 + n, -590145.2 + m, border = col2alpha(1, .08), lwd = 4)
    rect(-1290466 + n, -2648928.4 + m, 768012 + n, -590145.2 + m, border = col2alpha(1, .08), lwd = 3)
    rect(-1290466, -2648928.4, 768012, -590145.2, border = 1, lwd = 2)

And here is the result: enter image description here

In a future version of marmap, I plan to make this more straightforward. But for now, it's all I've got!

Upvotes: 1

Related Questions