UWA logoMaterial to support teaching in Environmental Science at The University of Western Australia

Units ENVT3361, ENVT4461, and ENVT5503

Maps / spatial pages: Maps | Spatial statistics | Spatial interpolation

 

UWA Students: Go here for Learning Objectives and suggested activities on this page

 

Introduction

We prepare maps for environmental reporting for two main reasons:

  1. To show the site being investigated in its context, such as site boundaries, surrounding land use, potential broader sources of contamination, proximity to receiving environments, and so on. This is called a “Locality Map”.

  2. To show the relevant details of the site being investigated: relevant infrastructure, specific suspected sources of contamination, sample types and locations, samples with contaminant conentrations exceeding guideline values, etc. This is called a “Site Plan map”.

This page presents a simple workflow to prepare both Locality and Site Plan maps using relevant packages in R.

Load the R packages we need for plotting maps (install first if needed)

Install the required packages to your device if you don't have them already (only do this once, not every R session):

if(!require(sf)) install.packages("sf")
if(!require(maptiles)) install.packages("maptiles")
if(!require(prettymapr)) install.packages("prettymapr")
if(!require(TeachingDemos)) install.packages("TeachingDemos")
if(!require(viridis)) install.packages("viridis")
if(!require(ggmap)) install.packages("ggmap")
if(!require(ggplot2)) install.packages("ggplot2")
if(!require(ggspatial)) install.packages("ggspatial")

You will need to load the installed packages each time you start RStudio.

library(sf)            # essential for maps and spatial analysis in R
library(maptiles)      # for downloading map tile images
library(prettymapr)    # for making north arrow and scale bar
library(TeachingDemos) # for shadowtext() function (outlined text)
library(viridis)       # for accessible colour palettes
palette(c("black", viridis(8), "royalblue", 
          "white", "transparent", "firebrick", "grey44")) # custom colours
library(ggmap)
library(ggplot2)
library(ggspatial)

Read some external data for adding info to maps

This code uses some functions from the sf R package( )Pebesma, 2018) to import some data from .kml files (Google Earth format), and transform the resulting spatial sf objects to the projection we are using. For more detail on the sf package, map projections, etc., look at the Introduction to Maps in R page.

The st_read() function can import data from numerous formats such as ESRI shapefiles and Google Earth .kml files. The st_transform function converts the longitude-latitude coordinates in the .kml files (units of degrees) to the coordinate reference system (CRS) specified by the function st_crs() called within st_transform. The CRS is specified by the EPSG code, where 32750 indicates UTM Zone 50 S based on the WGS84 datum, with units of metres.

git <- "https://github.com/Ratey-AtUWA/Learn-R-web/raw/refs/heads/main/"

LC_site <- st_read(paste0(git, "LC_UWA_study_area.kml"))
LC_site <- st_transform(LC_site, crs=st_crs(32750)) # convert to UTM Zone 50S

Claremont_drains <- st_read(paste0(git, "Town-of-Claremont-Drains.kml"))
(Claremont_drains <- st_transform(Claremont_drains, 
                                 crs=st_crs(32750))) # convert to UTM Zone 50S

 

LOCALITY MAP

Australian guidelines for reporting on contaminated site investigations (NEPC 2011, DWER 2021) specify including a locality map "...showing site location, site boundary, cadastral boundary or boundaries, surrounding area and any key nearby features..." (DWER, 2021).

The first part of this code shows a method for producing a locality map in R, relying on the sf spatial R package (Pebesma and Bivand, 2023) together with the packages maptiles (Giraud, 2024) and prettymapr (Dunnington, 2024).

next define a rectangle for a locality map

Find coordinates by:

  • locating the bottom-left and top-right corners of the desired rectangle using the maps at the EPSG site (https://epsg.io/map – make sure the Coordinate system at the bottom is changed to EPSG:32750).
  • using Google Earth with ⊙ Universal Transverse Mercator selected under Show Lat/Long after clicking Tools/Options... , then Add Placemark 📌

 

⚠ THESE COORDINATES 👇 ARE NOT REAL! - PLEASE FIND YOUR OWN!

locality <- st_as_sf(data.frame(x=c(123456,123456), y=c(1234567,1234567)),
                     coords=c("x","y"), crs=st_ evalcrs(32750))
locality # check it worked: should include 'Projected CRS: WGS 84 / UTM zone 50S'

 

Use the get_tiles() function with options to download map tiles

The code above made an object locality which defined our map rectangle in our chosen coordinate system. The locality object then becomes an input for the get_tiles() function from the maptiles R package. We specify some other options as well: provider= sets the map tile style, and zoom= sets the level of detail. At each zoom level, map tiles are squares, so we use crop=TRUE to trim any unneeded parts of the map tile images.

## claremontMap <- get_tiles(locality, provider="OpenStreetMap", crop=TRUE,
##                           zoom=15)

 

Then plot the map

The best option for plotting seems to be to:

  1. Plot an empty map frame based on the extent object (locality), adding axis labels and specifying xaxs="i", yaxs="i" to suppress axis padding.

  2. Use the plot_tiles() function from the maptiles R package to add the map tile layer. We include the option add=TRUE to plot on top of the previous plot.

# first setting graphics parameters with par()
par(mar=c(3,3,1,1), mgp=c(1.5,0.3,0), font.lab=2)
# first an empty plot frame based on the map extent
plot(st_coordinates(locality), type="n", asp=1, xaxs="i", yaxs="i",
     xlab="Easting", ylab="Northing")
plot_tiles(claremontMap, add=TRUE)
box() # redraw plot frame
Figure 1: Georeferenced map tile image obtained with the `maptiles` R package to use as a base locality map.

Figure 1: Georeferenced map tile image obtained with the maptiles R package to use as a base locality map.

 

After plotting the map in RStudio, you will probably need to adjust the size and proportions of your plot area manually, so that the map tiles fill the whole plot frame.

Next, add the necessary map and plot features and annotations

The guidelines state that a North arrow and scale bar should be included on maps, as well as the locations of significant geographical features (natural or anthropogenic).

# ...continuing code from above
addnortharrow()
addscalebar(plotepsg = 32750, pos="bottomleft", label.col = 1, linecol = 1,
            label.cex = 1.2, htin=0.15, widthhint=0.3, padin=c(0.15,0.25))
mtext("CRS:UTM Zone 50S, WGS84 (EPSG:32750)", side=1, line=-1.2, 
      font=2, col=14, cex=0.75, adj=0.02)
shadowtext(384350,6461820, labels="Lake\nClaremont", col=3, bg=11, cex=0.85, font=2)
shadowtext(385000,6461120, labels="Fremantle Railway", col=5, bg=11, cex=0.85, srt=25)
shadowtext(382900, 6462250, labels="Military\nFacility", col=5, bg=11, cex=0.85)
shadowtext(382100, 6462200, labels="Indian Ocean", col=3, bg=11, font=3, srt=90, cex=0.85)
Figure 2: Georeferenced map tile image obtained with `maptiles`, with `prettymapr` north arrow and scale bar, and text annotations using the `shadowtext()` funtion from the `TeachingDemos` package.

Figure 2: Georeferenced map tile image obtained with maptiles, with prettymapr north arrow and scale bar, and text annotations using the shadowtext() funtion from the TeachingDemos package.

 

Finally add the data we imported earlier, and a legend

We should always indicate the location of the site under investigation on our Locality Map. We also include stormwater drains on this map, since stormwater may affect water quality in Lake Claremont. Adding a legend helps readers with map interpretation.

# ...continuing code from above
plot(Claremont_drains[1], add=TRUE, type="l", col=10, lwd=2)

plot(LC_site[1], add=T, type="l", col=13, lwd=3)

legend("topleft", bg="#ffffffa0", box.col=12, inset=0.02,
       legend=c("Lake Claremont study site",
                "Town of Claremont stormwater drains"),
       lwd=c(3,2), col=c(13,10))
Figure 3: Georeferenced map tile image obtained with `maptiles`, with annotations as in Figure 2, and third-party data used to plot stormwater drain locations and show the extent of the study area.

Figure 3: Georeferenced map tile image obtained with maptiles, with annotations as in Figure 2, and third-party data used to plot stormwater drain locations and show the extent of the study area.

 

Alternative: plotting using ggmap/ggplot2

The ggplot2 R package is a popular alternative to base-R plotting (when using maptiles and sf we are still essentiall using base R graphics). The relevant functions for ggplot2 are geom_sf() and annotation_raster(), as the code below shows. We also make use of:

  • get_map() and related functions in the ggmap package, to obtain georeferenced raster images based on tiles from map servers;
  • annotation_scale() and annotation_north_arrow() functions in the ggspatial package to add essential map annotations.

As with maptiles maps, we need to specify a rectangle for our map background raster. In this example we're going to use the object locality that we made previously, and convert it to WGS84 Long-Lat (EPSG:4326) using st_transform(), as this is the CRS required by ggmap.

cat("Find long-lat bounding coordinates for ggmap raster background:\n")
## Find long-lat bounding coordinates for ggmap raster background:
(ll <- st_transform(locality, crs=st_crs(4326)) |> st_bbox() |> as.numeric())
## [1] 115.75097 -31.98604 115.79889 -31.96359
# transform the site boundary data to new CRS 
LC_siteLL <- st_transform(LC_site, crs=st_crs(4326))
# convert to sf:: object of class `polygon`
study <- st_polygon(list(as.matrix(st_coordinates(LC_siteLL)))) |> 
  st_sfc(crs=st_crs(4326)) 

This example uses stamen_terrain map tiles from Stadia. In ggmap, the Stadia maps can be specified from a user-defined rectangle (which is usually what we want), but other map tiles (e.g. google) yield square maps around a central coordinate. The get_stadiamap() function creates a georeferenced raster image from Stadia Stamen map tiles, which can be plotted directly using ggmap(). We're going to use ggplot() instead, as it is then easier to add additional map layers such as the investigation site boundary, stormwater drains, land use polygons, and so on. In this case we use annotation_raster to add the ggmap raster to our map plot.

You will need to register for a (free) API key if you want to use Stadia Stamen map tiles.

register_stadiamaps(key = smapskey) # do this before getting Stadia Stamen maps
localgg <- 
  get_stadiamap(bbox=c(left=ll[1], bottom=ll[2], right=ll[3], top=ll[4]),
                     maptype = "stamen_terrain", zoom=15)

Here's how we plot the map background, additional map layers, and annotations (Figure 4).

# make an object to contain custom plot colours
cols <- c("Storm_Drains"="darkcyan", "Study_Area"="#800080b0")
# plot the `ggmap` raster starting with an empty `ggplot()`
ggplot() +
  annotation_raster(localgg, xmin=ll[1], ymin=ll[2], xmax=ll[3], ymax=ll[4]) +
  scale_x_continuous(expand = c(0,0), limits=c(ll[1],ll[3])) + 
  scale_y_continuous(expand = c(0,0), limits=c(ll[2],ll[4])) +
  # xlim(c(ll[1],ll[3])) + ylim(c(ll[2], ll[4])) + 
  geom_sf(data=study, mapping=aes(col="Study_Area"), fill=NA, lwd=1.3) +
  geom_sf(data=Claremont_drains, mapping=aes(col="Storm_Drains"), 
          lwd=0.8, lty="21") +
  geom_text(aes(x = c(115.76,115.778), y = c(-31.968,-31.973), 
                label = c("Military\nFacility","Study\nArea"),
                fontface="italic", family="sans"), 
            size=12, vjust=0.5, hjust=0.5, color="steelblue4", size.unit="pt") + 
  geom_text(aes(x = 115.771, y = -31.9818, 
                label = c("Fremantle Railway"),
                fontface="italic", family="sans"), angle=18, 
            size=10, vjust=0.5, hjust=0.5, color="steelblue4", size.unit="pt") + 
  geom_text(aes(x = c(115.752), y = c(-31.9725), 
                label = c("Indian Ocean"),
                fontface="italic", family="sans"), angle=90,
            size=12, vjust=0.5, hjust=0.5, color="navy", size.unit="pt") + 
  labs(x="Longitude", y="Latitude") + 
  scale_color_manual(name="", values=cols, 
                     guide=guide_legend()) +
  annotation_scale(location="tl", width_hint=0.25, text_cex=1, 
                   pad_x=unit(2, "cm")) +
  annotation_north_arrow(location = "tl", which_north = "true", 
                         pad_x = unit(0.2, "cm"), pad_y = unit(0.2, "cm"),
                         style = north_arrow_fancy_orienteering) +
  theme_bw() +
  theme(axis.title = element_text(face="bold", size=14),
        axis.text = element_text(size=12),
        legend.text = element_text(size=12))
Figure 4: Locality map for Lake Claremont made using `ggplot2` and `ggmap`.

Figure 4: Locality map for Lake Claremont made using ggplot2 and ggmap.

Some additional notes on this code:

  • scale_x_continuous(expand = c(0,0), limits=c(ll[1],ll[3])) (and scale_y_continuous()) allow us to have axis limits that exactly fit the ggmap raster
  • geom_sf() allows us to add layers. The layer information eeds to be in a sf object
  • we can add text annotations using geom_text()
  • we set axis labels using labs()
  • scale_color_manual() creates the legend to the right of the map
  • annotation_scale() adds a scale bar (based on the CRS of the raster)
  • annotation_north_arrow() adds a north arrow
  • theme_bw is a good choice for maps
  • we often want to customise the appearance further by calling theme() directly and setting some additional options.

 

SITE PLAN MAP

Australian guidelines for reporting on preliminary (PSI) and detailed (DSI) site investigations (NEPC, 2011) also specify including a Site Plan drawn to a scale appropriate to project size and required detail. This plan is essentially a map showing features such as site boundary, sample locations, actual installed locations of monitoring wells, boreholes and/or pits, and so on (DWER, 2021). The Site Plan should also be used for reporting results, including “… a clear representation of contamination issues associated with the site…” (NEPC, 2011).

This section will explain the creation of such a more detailed Site map in R, including information on potential contamination at discrete sampling points.

We already have an object LC_site that defines the boundaries of the site so we can use that to specify the area of map tiles to download. Note that we are choosing a different map tile style - the CartoDB tiles have lighter colours, so are good for showing data on.

LC_siteMap <- get_tiles(LC_site, provider="CartoDB.Voyager", crop=TRUE,
                          zoom=16)
par(mar=c(3,3,1,1), mgp=c(1.5,0.3,0), font.lab=2)
plot(st_coordinates(LC_site), type="n", asp=1, xaxs="i", yaxs="i", 
     xlab="Easting", ylab="Northing")
plot_tiles(LC_siteMap, add=TRUE)
box()
addnortharrow()
addscalebar(plotepsg = 32750, pos="bottomright", label.col = 1, linecol = 1,
            label.cex = 1.2, htin=0.15, widthhint=0.3, padin=c(0.15,0.2))
mtext("UTM Zone 50S, WGS84 (EPSG:32750)", side=1, line=-1.1, 
      font=2, col=14, cex=0.7, adj=0.98)
shadowtext(c(384450), c(6462180), labels=c("Rehabilitated bushland"),
           bg=11, col=6, srt=30)
shadowtext(c(384300,384650,384680), c(6461500,6461850,6461440), 
           labels=c("Scotch College\nsports fields","Grassed\nParkland",
                    "Golf\ncourse"), bg=11, col=c(14,6,6), font=3)
plot(Claremont_drains[2], add=T, type="l", col=4, lwd=1.5, lty=3)
Figure f: Site Plan map made with georeferenced tiles obtained with `maptiles`, with `prettymapr` north arrow and scale bar, and stormwater drains.

Figure f: Site Plan map made with georeferenced tiles obtained with maptiles, with prettymapr north arrow and scale bar, and stormwater drains.

 

We need to read-in our data:
(this is the same one used for the regression assignment – save it to your working directory in RStudio!)

## lcw24 <- read.csv("lcw24edit.csv")
str(lcw24) # check it
## 'data.frame':    51 obs. of  11 variables:
##  $ Lab.Field.Group: chr  "Group-01" "Group-01" "Group-01" "Group-01" ...
##  $ Sample_ID      : chr  "LCW24_01" "LCW24_02" "LCW24_03" "LCW24_04" ...
##  $ Location       : chr  "North-west lake" "North-west lake" "North-west lake" "North-west lake" ...
##  $ Easting        : int  384411 384405 384402 384411 384415 384346 384559 384568 384576 384585 ...
##  $ Northing       : int  6462067 6462067 6462065 6462075 6462080 6461978 6461907 6461927 6461947 6461967 ...
##  $ Zone           : chr  "NW" "NW" "NW" "NW" ...
##  $ pH             : num  7.43 7.51 7.57 7.46 7.46 8.56 7.76 7.4 7.72 7.64 ...
##  $ As             : num  0.166 0.158 0.148 0.182 0.14 0.158 NA NA 0.043 NA ...
##  $ Fe             : num  0.283 0.168 0.109 0.073 0.054 0.021 0.174 0.065 0.699 0.334 ...
##  $ P              : num  0.353 0.295 0.292 0.461 0.359 0.043 0.028 0.014 0.061 0.056 ...
##  $ Pb             : num  NA NA NA 0.0246 NA NA NA NA NA NA ...

We can optionally check sample locations (small + symbols):

# ...continuing previous code for Figure 4...
with(lcw24, points(Easting, Northing, pch=3, col=14, cex=0.7))
legend("topleft", bg="#ffffffb0", box.col=12, 
       legend=c("Storm drains","Water samples"), lty=c(3,NA), pch=c(NA,3),
       col=c(4,14), pt.cex=c(NA,0.7))
Figure 6: Site Plan map made with georeferenced tiles obtained with `maptiles`, with `prettymapr` north arrow and scale bar, stormwater drains, and locations of water samples.

Figure 6: Site Plan map made with georeferenced tiles obtained with maptiles, with prettymapr north arrow and scale bar, stormwater drains, and locations of water samples.

 

Plot the P (phosphorus) concentrations as ‘bubbles’ using the symbols() function

The base-R symbols() function allows us to add the scaled circle symbols ("bubbles"). Note that we make bubble radius proportional to square root concentration – this makes bubble area proportional to concentration, since human perception considers size as area rather than diameter or radius.

Make sure you use these option in the symbols() function: add=TRUE, inches=FALSE.

We also identify and plot the samples with P concentrations greater than the threshold for total P in wetlands in SW Australia (ANZECC, 2000), which is 60 µg/L = 0.06 mg/L

# ...continuing previous code...
  # first use a simple algorithm to estimate a scale factor `s0` for the bubbles
  axrg <- par("usr")[2]-par("usr")[1]
  # first make small legend bubble, checking if it's zero 
  if (pretty(lcw24$P)[1] < 0.001) {
    bublo <- pretty(lcw24$P)[2]/2
  } else {
    bublo <- pretty(lcw24$P)[1]
  }
  bubhi <- pretty(lcw24$P)[length(pretty(lcw24$P))]
  s0 <- signif(0.05*axrg/sqrt(bubhi),2)
  
# add the scaled symbols ("bubbles")
# note we make bubble radius proportional to square root concentration
# this makes bubble area proportional to concentration, since human perception
# considers size as area rather than diameter or radius
with(lcw24, symbols(Easting, Northing, add=TRUE, circles=sqrt(P)*s0, 
                    inches=FALSE, fg=2, bg="#A020F080"))

# next we identify and plot the samples with P concentrations greater than 
# the ANZECC threshold for total P in wetlands in SW Australia, which is
# 60µg/L = 0.06mg/L
with(lcw24[which(lcw24$P>=0.06),c("Easting","Northing","P")],
     points(Easting, Northing, pch=3, col=1, lwd=2.5))
# manual legend
rect(384400, 6462190, 384620, 6462330, lwd=2, 
     col="#ffffffb0", border="#80808080")
symbols(c(384450,384550),c(6462250,6462250), circles=s0*sqrt(c(bublo,bubhi)), add=T,
        lwd=1, inches=F, fg = "purple", bg = "#8000FF40")
text(c(384500,384450,384550),c(6462320,6462230,6462250), cex=0.85, 
     labels=c("P (mg/L)",bublo,bubhi), pos = c(1,1,1), font=c(2,1,1),
     offset=0)

# "normal" legend
legend("topleft", inset=0.01, bg="#ffffffa0", box.col=12, y.intersp=1.75,
       legend=c("Water\nsamples", "Samples\nP ≥ 0.06mg/L", "Stormwater\ndrains"),
       pch=c(21,3,NA), lty=c(NA,NA,3), col=c(2,1,4), lwd=c(NA,NA,1.5),
       pt.cex=c(3,1,NA), pt.lwd=c(1,2.5,NA), pt.bg="#A020F080", cex=0.85)
Figure 7: Site Plan map made with georeferenced tiles obtained with `maptiles`, with `prettymapr` north arrow and scale bar, and stormwater drains. Phosphorus concentrations in water are shown are area-proportional circle symbols at sample locations, with samples having phosphorus concentrations exceeding the Water Quality Australia guideline shown by bold plus (+) symbols.

Figure 7: Site Plan map made with georeferenced tiles obtained with maptiles, with prettymapr north arrow and scale bar, and stormwater drains. Phosphorus concentrations in water are shown are area-proportional circle symbols at sample locations, with samples having phosphorus concentrations exceeding the Water Quality Australia guideline shown by bold plus (+) symbols.

 

This final map could be included in an environmental investigation report.

To plot a different element (e.g. Al) you would need to

  1. Replace 'P' with 'Al' in ALL the right places in the code
  2. Change the guideline concentration from 0.06 to the relevant value for the next element (see Water Quality Australia, 2024)

Site plan map using ggplot2 and ggmap

We have already converted our site polygon to the correct CRS (i.e. Long-Lat WGS84), storing it in LC_siteLL. To make a background map we add some space around the site polygon – we could do this manually, but I've made a custom function pad_bbox() to do this simply (pad_bbox() expands the bounding box by 5% in all directions by default; we can change the expansion factor).

#    (pad_bbox() is a custom function to expand a sf:: object in 
#     all directions by a specified proportion)
source("https://github.com/Ratey-AtUWA/Learn-R-web/raw/refs/heads/main/FUNCTION-pad_bbox.R")
l2 <- st_bbox(pad_bbox(LC_siteLL)) |> as.numeric()
sitegg <- 
  get_stadiamap(bbox=c(left=l2[1], bottom=l2[2], right=l2[3], top=l2[4]),
                     maptype = "stamen_terrain", zoom=16)

We need our data in the right format, so we need to do some conversions (data frame to sf data frame, and UTM Zone 50 (EPSG 32750) to Longitude-Latitude WGS 84 (EPSG:4326):

lcw24LL <- st_as_sf(lcw24, coords=c("Easting", "Northing"),
                    crs=st_crs(32750), remove=FALSE) |> 
  st_transform(crs=st_crs(4326))

Here's how we use ggplot to plot the map background, additional map layers, annotations, and data (Figure 8).

# make an object to contain custom plot colours
cols <- c("Storm_Drains"="darkcyan", "Study_Area"="#800080b0")
# plot the `ggmap` raster starting with an empty `ggplot()`
ggplot(LC_siteLL) +
  annotation_raster(sitegg, xmin=l2[1], ymin=l2[2], xmax=l2[3], ymax=l2[4]) +
  scale_x_continuous(expand = c(0,0), limits=c(l2[1],l2[3])) + 
  scale_y_continuous(expand = c(0,0), limits=c(l2[2],l2[4])) +
  geom_sf(data=study, fill=NA, lwd=1.3, color="#800080b0") +
  geom_sf(data=Claremont_drains, lwd=0.8, lty="21", col="darkcyan") +
  geom_sf(data=lcw24LL, mapping=aes(size=P, fill=P), pch=21, color="#00000080") +
  geom_sf(data=subset(lcw24LL, lcw24LL$P>=0.06), pch=3, col="#ffffff40", stroke=2) +
  geom_sf(data=subset(lcw24LL, lcw24LL$P>=0.06), pch=3) +
  scale_fill_viridis_c(alpha=0.7, option="plasma", 
                       breaks=c(0.01,0.02, 0.05,0.1,0.2,0.4), 
                       guide="legend", name="P (mg/L)") +
  scale_size_continuous(range=c(0,12), breaks=c(0.01,0.02, 0.05,0.1,0.2,0.4), 
                        name="P (mg/L)") +
  labs(x="Longitude", y="Latitude") + 
  geom_text(aes(x=115.7755, y=-31.9765, label = "Sports\nFields"),
            fontface="italic", family="sans", color="#205000", 
            size.unit="pt", size=10, vjust=0.5, hjust=0.5) + 
  geom_text(aes(x=115.78, y=-31.9775, label = "Golf and\nSwimming\nComplex"),
            fontface="italic", family="sans", color="#205000", 
            size.unit="pt", size=10, vjust=0.5, hjust=0.5) + 
  annotation_scale(location="bl", width_hint=0.25, text_cex=0.9, 
                   height = unit(0.25, "cm")) +
  annotation_north_arrow(location="tl", which_north="true", 
                         pad_x=unit(0.2, "cm"), pad_y=unit(0.2, "cm"), 
                         width=unit(1, "cm"), height=unit(1.2, "cm")) +
  theme_bw() +
  theme(axis.title = element_text(face="bold", size=11),
        axis.text = element_text(size=9),
        legend.text = element_text(size=9))
Figure 8: Site Plan map for Lake Claremont made using `ggplot2` and `ggmap`, showing concentration of P as area-proportional symbols. Samples for which total P concentration exceed the stressor value (ANZECC/ARMCANZ 2000) are identified with + symbols.

Figure 8: Site Plan map for Lake Claremont made using ggplot2 and ggmap, showing concentration of P as area-proportional symbols. Samples for which total P concentration exceed the stressor value (ANZECC/ARMCANZ 2000) are identified with + symbols.

Notes on the ggplot Site Plan map code:

  • some code features perform the same function as for trhe locality map in Figure 4
  • to make a "bubble" plot we include aes(size=P, fill=P) within geom_sf(data=lcw24LL, ...)
  • we plot the symbols twice for the subset of data where our variable (P) exceeds the guideline concentration – this is to improve visibility, since the underlying symbol has a thicker line width (stroke) and contrasting semitransparent colour
  • we have done some careful matching of scale_fill_viridis_c() and scale_size_continuous() so that we just get a single legend instead of one for size and one for fill colour

 

References and R packages

ANZECC/ARMCANZ. (2000). Australian and New Zealand Guidelines for Fresh and Marine Water Quality (Volume 1, The guidelines). Australian and New Zealand Environment and Conservation Council, Agriculture and Resource Management Council of Australia and New Zealand https://www.waterquality.gov.au/sites/default/files/documents/anzecc-armcanz-2000-guidelines-vol1.pdfsee Table 3.3.6.

Dunnington, Dewey (2017). prettymapr: Scale Bar, North Arrow, and Pretty Margins in R. R package version 0.2.2. https://CRAN.R-project.org/package=prettymapr.

Dunnington, D. (2023). ggspatial: Spatial Data Framework for ggplot2. R package version 1.1.9, https://CRAN.R-project.org/package=ggspatial.

DWER (2021). Assessment and management of contaminated sites. Department of Water and Environment Regulation, Government of Western Australia, Joondalup. https://www.wa.gov.au/system/files/2023-05/guideline-assessment-and-management-of-contaminated-sites.pdf.

Giraud T (2021). maptiles: Download and Display Map Tiles. R package version 0.3.0, https://CRAN.R-project.org/package=maptiles.

Garnier S, Ross N, Rudis R, Camargo AP, Sciaini M, Scherer C (2024). viridis(Lite) - Colorblind-Friendly Color Maps for R. viridis package version 0.6.5. https://sjmgarnier.github.io/viridis/.

Kahle, D. and Wickham, H. ggmap: Spatial Visualization with ggplot2. The R Journal, 5(1), 144-161. http://journal.r-project.org/archive/2013-1/kahle-wickham.pdf.

NEPC (National Environment Protection Council). (2011). Schedule B2: Guideline on Site Characterisation, National Environment Protection (Assessment of Site Contamination) Measure (Amended). Commonwealth of Australia, Canberra. https://www.nepc.gov.au/.../schedule-b2-guideline-site-characterisation-sep10.pdf.

Pebesma, E., 2018. Simple Features for R: Standardized Support for Spatial VectorData. The R Journal 10 (1), 439-446, https://doi.org/10.32614/RJ-2018-009 . (package sf)

Water Quality Australia. (2024). Search for toxicant default guideline values for the protection of aquatic ecosystems. Department of Climate Change, Energy, the Environment and Water, Government of Australia. https://www.waterquality.gov.au/anz-guidelines/guideline-values/default/water-quality-toxicants/search.

Wickham, H. (2016). ggplot2: Elegant Graphics for Data Analysis. Springer-Verlag New York, 2016. https://ggplot2.tidyverse.org.


 

For UWA students

Activities for this Workshop class

There are a few items available on the UWA LMS as learning materials for this session on using R + packages to make maps: two short videos, and two annotated pdfs based on

  1. the R code and
  2. a PowerPoint presentation.

We suggest going through the first video first, and then trying the code, and finally viewing the second video and trying some different things. The material in the PowerPoint presentation on interpolation of point data is completely optional.

For activities today we suggest:
  1. Try to make a map of our field site area which covers all our sample locations. A good place to start after watching the video/reading the annotated code PDF would be with modifying and running the R code.

Good luck!

 

Bonus material

 (Currently on another Github site) 

R code file icon R code to use georeferenced images (e.g. from NearMap) as map backgrounds
 

R code file icon Digitising map features from Google Earth, and R code for a function to convert Google Earth .kml files for use in R

Advanced Spatial Analysis (spatial autocorrelation, variograms, and kriging interpolations)
 

 (Currently on UWA LMS, so you will need to be logged in) 

 


CC-BY-SA • All content by Ratey-AtUWA. My employer does not necessarily know about or endorse the content of this website.
Created with rmarkdown in RStudio. Currently using the free yeti theme from Bootswatch.