Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Short moveVis example on how to overlay frames with additional transparent rasters changing over time
library(moveVis)
library(move)
library(ggplot2)
data("move_data", "basemap_data")
m <- align_move(move_data, res = 4, unit = "mins")
## create frames using mapbox base map
frames <- frames_spatial(m, map_type = "satellite", map_service = "mapbox", map_token = "YOUR_VERY_LONG_TOKEN",
path_legend = T)
r_list <- basemap_data[[1]]
r_times <- basemap_data[[2]]
# crop to plot extent
r_list <- lapply(r_list, raster::crop, y = extent(m), snap = "out")
# here I fake a 3 class categorical raster
r_list <- lapply(r_list, function(x){
y <- setValues(x, round(getValues(x)*3))
y[y == 0] <- 3
return(y)
})
## first, we need a list of rasters with the same length as frames
## and with each raster at the correct time in that list. For this:
# create timestamps of m
ts <- sort(unique(timestamps(m)))
# ts has same length as frames, since frames were created from the timestamps of m
# caclulate difftime for each time stamp to all time stamps of your rasters and get minimum absolute diff
r_pos <- sapply(ts, function(x) which.min(abs(difftime(x, r_times))))
# the subscript with min abs time difference between the raster time and the times of m
# is what we used to assign the rasters per time:
r_list <- lapply(r_pos, function(i) r_list[[i]])
# now, rasters are assigned per frame time
## just call add_gg with a ggplot2 raster drawing command,
# for example the ggR function in RStoolbox in the layer mode with 30 % opacity:
frames_overlayed <- add_gg(frames, gg = expr(RStoolbox::ggR(data, alpha = 0.8, forceCat = T, ggLayer = T)), data = r_list)
# iterates over all frames and over r_list (same lengths) and applies the ggR function
# instead of ggR, you could use any ggplot2 expression you like to create a raster layer
frames_overlayed[[100]]
# or if you want so specify colours and alpha per class ( e.g. make a class be completely transparent),
# you can use geom_raster.
# turn r_list into data.frames for ggplot2 and define colours and alphas per value (here we have 3 classes)
r_df <- lapply(r_list, function(x) data.frame(coordinates(x),
vals = values(x),
cols = plyr::mapvalues(values(x), 1:3, c("darkgreen", "green", "blue")),
alpha = plyr::mapvalues(values(x), 1:3, c(0, 0.4, 1))))
# and use geom_raster with r_df to get colours and alpha per class
frames_overlayed <- add_gg(frames, gg = expr(geom_raster(data = r_df[[100]], mapping = aes(x = x, y = y, fill = cols, alpha = alpha), show.legend = F)), data = r_df)
frames_overlayed[[100]]
# additional note:
# With geom_raster, plot extents are changed, while with ggR using annotation_raster, plot extents remain
# so either crop to the correct extent or fixate the ggplot axis limits of frames before adding geom_raster
# I did not manage to display a legend for fill of geom_raster and do not know why, but had no time to investigate.
# alpha legend is displayed though, if show.legend = T
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.