Read files into R from the Spatial Hub
2024-04-29
Introduction
You can map data from the Improvement Service Spatial Hub using R. Below are examples showing how this can be achieved using WFS pathways and shapefiles.
Web Feature Services (WFS) are a means of accessing geographic data via a file pathway, drawing directly from the Spatial Hub. The advantage of utilising WFS files lies in their ability to fetch data in real-time from the Spatial Hub each time you refresh your map. This approach is more dynamic compared to using static file types that are downloaded and stored on your local device (such as those in your downloads folder). Static files risk becoming outdated unless you frequently check the source data and manually update your files with the latest data versions.
Reading Spatial Data
You can read shapefiles and WFS files from the Spatial Hub using the sf library in R: https://r-spatial.github.io/sf/
Spatial data in the Spatial Hub is stored with the British National Grid projection. For web mapping, re-project these to WGS84, as shown in the code snippets below.
R Code snippets for reading in and mapping shapefile data from the Spatial Hub
# add packages to R
if (!require(dplyr)) install.packages(dplyr)
if (!require(sf)) install.packages(sf)
if (!require(leaflet)) install.packages(leaflet)
#load packages
library(dplyr) # a package for data wrangling
library(sf) # a package for handling GIS data
library(leaflet) # a package for mapping GIS data
# once I have downloaded my shapefile from the spatial hub, I can read it into R using st_read.
town_centre <- st_read("C:/Users/kirkland.aline/OneDrive - IS/Documents/pub_townc.shp")
## Reading layer `pub_townc' from data source
## `C:\Users\kirkland.aline\OneDrive - IS\Documents\pub_townc.shp'
## using driver `ESRI Shapefile'
## Simple feature collection with 397 features and 9 fields
## Geometry type: MULTIPOLYGON
## Dimension: XY
## Bounding box: xmin: 124603.3 ymin: 540130.3 xmax: 413642.6 ymax: 1011389
## Projected CRS: OSGB36 / British National Grid
# I now want to change the projection so I can map the data. Transform to WGS84 (EPSG:4326)
town_centre <- st_transform(town_centre, crs = 4326)
# I want to check the geometry type. For mapping, I need a simple geometry type like point or polygon
st_geometry_type(town_centre, by_geometry = FALSE)
## [1] MULTIPOLYGON
## 18 Levels: GEOMETRY POINT LINESTRING POLYGON MULTIPOINT ... TRIANGLE
# The shapefile has multipolygon geometry, so I need to change that to polygon so I can map the data.
town_centre <- st_cast(town_centre, "POLYGON")
# Leaflet library allows you to create maps from the shapefile.
leaflet()%>%
addProviderTiles('Esri.WorldImagery', options = providerTileOptions(), group = "Imagery Basemap") %>% # add an ESRI imagery basemap.
addPolygons(data = town_centre, # add a polygon of the shapefile to the map
color = "pink")
Reading WFS pathways
R Code snippets for reading in and mapping WFS data from the Spatial Hub
# add packages to R
if (!require(dplyr)) install.packages(dplyr)
if (!require(sf)) install.packages(sf)
if (!require(leaflet)) install.packages(leaflet)
#load packages
library(dplyr) # a package for data wrangling
library(sf) # a package for handling GIS data
library(leaflet) # a package for mapping GIS data
# read in the WFS from the Spatial Hub by navigating to the data you want, clicking download, choosing Web Services and copying the WFS that appears. Include WFS: before the file path that you add in R, as in the example below
tc_wfs <- st_read("WFS:https://geo.spatialhub.scot/geoserver/sh_townc/wfs?service=WFS&authkey=your_auth_key_here")
## Reading layer `sh_townc:pub_townc' from data source
## `WFS:https://geo.spatialhub.scot/geoserver/sh_townc/wfs?service=WFS&authkey=your_auth_key_here'
## using driver `WFS'
## Simple feature collection with 397 features and 10 fields
## Geometry type: MULTISURFACE
## Dimension: XY
## Bounding box: xmin: 124603.3 ymin: 540130.3 xmax: 413642.6 ymax: 1011389
## Projected CRS: OSGB36 / British National Grid
# I want to check the geometry type. For mapping, I need a simple geometry type like point or polygon
st_geometry_type(tc_wfs, by_geometry = FALSE)
## [1] MULTISURFACE
## 18 Levels: GEOMETRY POINT LINESTRING POLYGON MULTIPOINT ... TRIANGLE
# the geometry type was multi-surface. I need to transform this first to a geometry collection and then to a simple polygon to make it mappable.
tc_wfs <- sf::st_cast(tc_wfs, "GEOMETRYCOLLECTION")
# extract polygon data from geometry collection
tc_wfs <- sf::st_collection_extract(tc_wfs, type = c("POLYGON"))
# re-project the data from British National Grid to WGS84 for web mapping
tc_wfs <- sf::st_transform(tc_wfs, crs = 4326)
# cast the data to a simple polygon for mapping
tc_wfs <- st_cast(tc_wfs, "POLYGON")
# Leaflet library allows you to create maps from the shapefile.
leaflet()%>%
addProviderTiles('Esri.WorldImagery', options = providerTileOptions(), group = "Imagery Basemap") %>% # add an ESRI imagery basemap.
addPolygons(data = tc_wfs, # add a polygon of the wfs to the map
color = "red")