Search code examples
rlatticer-sp

spplot/lattice: objects not drawn/overdrawn


I have a grid and I want to produce a map out of this grid with some map elements (scale, north arrow, etc). I have no problem drawing the grid and the coloring I need, but the additional map elements won't show on the map. I tried putting first=TRUE to the sp.layout argument according to the sp manual, but still no success.

I reproduced the issue with the integrated meuse dataset, so you may just copy&paste that code. I use those package versions: lattice_0.20-33 and sp_1.2-0

library(sp)
library(lattice) # required for trellis.par.set():
trellis.par.set(sp.theme()) # sets color ramp to bpy.colors()

alphaChannelSupported = function() { 
  !is.na(match(names(dev.cur()), c("pdf")))
}

data(meuse)
coordinates(meuse)=~x+y
data(meuse.riv)


library(gstat, pos = match(paste("package", "sp", sep=":"), search()) + 1)
data(meuse.grid)
coordinates(meuse.grid) = ~x+y
gridded(meuse.grid) = TRUE
v.uk = variogram(log(zinc)~sqrt(dist), meuse)
uk.model = fit.variogram(v.uk, vgm(1, "Exp", 300, 1))
meuse[["ff"]] = factor(meuse[["ffreq"]])
meuse.grid[["ff"]] = factor(meuse.grid[["ffreq"]])
zn.uk = krige(log(zinc)~sqrt(dist), meuse, meuse.grid, model = uk.model)
zn.uk[["se"]] = sqrt(zn.uk[["var1.var"]])

meuse.sr = SpatialPolygons(list(Polygons(list(Polygon(meuse.riv)),"meuse.riv")))
rv = list("sp.polygons", meuse.sr, fill = "lightblue")
sampling = list("sp.points", meuse.riv, color = "black")
scale = list("SpatialPolygonsRescale", layout.scale.bar(), 
             offset = c(180500,329800), scale = 500, fill=c("transparent","black"), which = 4)
text1 = list("sp.text", c(180500,329900), "0", cex = .5, which = 4)
text2 = list("sp.text", c(181000,329900), "500 m", cex = .5, which = 4)
arrow = list("SpatialPolygonsRescale", layout.north.arrow(), 
             offset = c(181300,329800), 
             scale = 400, which = 4)

library(RColorBrewer)
library(lattice)
trellis.par.set(sp.theme())
precip.pal <- colorRampPalette(brewer.pal(7, name="Blues"))

spplot(zn.uk, "var1.pred",
       sp.layout = list(rv, sampling, scale, text1, text2),
       main = "log(zinc); universal kriging standard errors",
       col.regions=precip.pal,
       contour=TRUE, 
       col='black',
       pretty=TRUE,
       scales=list(draw = TRUE),
       labels=TRUE)

And that's how it looks...all naked: enter image description here So my questions:

  1. Where is the scale bar, north arrow, etc hiding? Did I miss something? Every example I could find on the internet looks similar to that. On my own dataset I can see the scale bar and north arrow being drawn at first, but as soon as the grid is rendered, it superimposes the additional map elements (except for the scale text, that is shown on the map - not the bar and north arrow for some reason I don't seem to comprehend).
  2. The error message appearing on the map just shows when I try to add the sampling locations sampling = list("sp.points", meuse.riv, color = "black"). Without this entry, the map shows without error, but also without additional map elements. How can I show the sampling points on the map (e.g. in circles whose size depends on the absolute value of this sampling point)?

This bothered me for many, many hours by now and I can't find any solution to this. In Bivand et al's textbook (2013) "Applied Spatial Data Analysis with R" I could read the following entry:

The order of items in the sp.layout argument matters; in principle objects are drawn in the order they appear. By default, when the object of spplot has points or lines, sp.layout items are drawn before the points to allow grids and polygons drawn as a background. For grids and polygons, sp.layout items are drawn afterwards (so the item will not be overdrawn by the grid and/or polygon). For grids, adding a list element first = TRUE ensures that the item is drawn before the grid is drawn (e.g. when filled polygons are added). Transparency may help when combining layers; it is available for the PDF device and several other devices. Function sp.theme returns a lattice theme that can be useful for plots made by spplot; use trellis.par.set(sp.theme()) after a device is opened or changed to make this effective.

However, also with this additional information I wasn't able to solve this problem. Glad for any hint!


Solution

  • The elements you miss are being drawn in panel four, which does not exist, so are not being drawn. Try removing the which = 4.

    meuse.riv in your example is a matrix, which causes the error message, but should be a SpatialPoints object, so create sampling by:

    sampling = list("sp.points", SpatialPoints(meuse.riv), color = "black")
    

    When working from examples, my advice is to choose examples as close as possible to what you need, and only change one thing at a time.