Pages Menu
Categories Menu

Posted by on Mar 30, 2015 in R Spatial, Resources, Spatial Analysis, Visualisation | 9 comments

Mapping Flows in R


Last year I published the above graphic, which then got converted into the below for the book London: The Information Capital. I have had many requests for the code I used to create the plot so here it is!

The data shown is the Office for National Statistics flow data. See here for the latest version. The file I used for the above can be downloaded here (it is >109 mb uncompressed so you need a decent computer to load/plot it all at once in R). You will also need this file of area (MSOA) codes and their co-ordinates. The code used is pasted below with comments above each segment. Good luck!


Load the flow data required – origin and destination points are needed. See above for where you can get the table used here.

input<-read.table("wu03ew_v1.csv", sep=",", header=T)

We only need the first 3 columns of the above

input names(input)

The UK Census file above didn’t have coordinates just area codes. Here is a lookup that provides those. See above for download.


Lots of joining to get the xy coordinates joined to the origin and then the destination points.

or.xy names(or.xy) dest.xy names(dest.xy)

Now for plotting with ggplot2.This first step removes the axes in the resulting plot.

xquiet yquiet<-scale_y_continuous("", breaks=NULL)
quiet<-list(xquiet, yquiet)

Let’s build the plot. First we specify the dataframe we need, with a filter excluding flows of <10

ggplot(dest.xy[which(dest.xy$trips>10),], aes(oX, oY))+

The next line tells ggplot that we wish to plot line segments. The “alpha=” is line transparency and used below

geom_segment(aes(x=oX, y=oY,xend=dX, yend=dY, alpha=trips), col="white")+

Here is the magic bit that sets line transparency – essential to make the plot readable

scale_alpha_continuous(range = c(0.03, 0.3))+

Set black background, remove axes and fix aspect ratio

theme(panel.background = element_rect(fill='black',colour='black'))+quiet+coord_equal()

We used ggave() to export from R and then we imported the pdf into Illustrator to produce the final graphic for print…



  1. Hey, loving the article, but I can’t read the ONS link. Is it missing a value for the subcomp parameter?

  2. rather than mouse-clicking to obtain the data, just do:



    thanx for the script,

  3. James,

    Thanks for being open in the same spirit as R and contributing to the community. I reproduced your map on my I7 quad machine and it sourced in less than 2 mins. Only change I made was saving to SVG.

    This map illustrates the city islands imho. If we had more transport connections between our cities we’d probably see a whiter image.


  4. Nice work! What is the spec of the machine you used to generate this graphic and how long did it take to render? My R session freezes over when I try to reproduce this example. I have a Core i7 machine too with 16 gigs of ram…

    • I have a 2014 rMBP (i7, 2.2GHz, 16 GB) and it had no problems whatsoever.

      • I got mine to work too. Had to wait for about 10 minutes though… The R session just froze for those 10 minutes.

  5. It’s strange, but most of the code is missing when I view this page on this particular site. if I got to this site, I can see all the code.

  6. Finally got this awesome map to work (the missing code is strange as noted by the earlier commentator as well). But, how long does one have to wait for the map to show in the plot window of RStudio? I got it once in 5 mins, but this run I am yet waiting (10 mins already)…R Studio is showing that the script has run successfully and I can continue with other commands in R, but no map as yet…:(

  7. Any advice on how to overlay shapefiles over such a map? Thanks a ton in advance


  1. Distilled News | Data Analytics & R - […] Mapping Flows in R Last year I published the above graphic, which then got converted into the below for…
  2. Mapping Flows in R … with data.table and lattice | Omnia sunt Communia! - […] days ago James Cheshire published the post Mapping Flows in R. I have implemented an alternative (faster) version using…

Post a Reply

Your email address will not be published. Required fields are marked *