{"id":845,"date":"2015-04-01T14:02:27","date_gmt":"2015-04-01T21:02:27","guid":{"rendered":"http:\/\/homepages.uc.edu\/~yaozo\/wordpress\/?p=845"},"modified":"2015-04-01T14:02:27","modified_gmt":"2015-04-01T21:02:27","slug":"maps-with-r","status":"publish","type":"post","link":"https:\/\/zhuoyao.net\/index.php\/2015\/04\/01\/maps-with-r\/","title":{"rendered":"Maps with R"},"content":{"rendered":"<p>This is the first post of a short series to show some code I have learnt to produce maps with R.<\/p>\n<p><strong>NOTE: Although the procedure described in this post is valid, there is a<a href=\"https:\/\/github.com\/oscarperpinan\/spacetime-vis\/blob\/master\/choropleth.R\">newer code version<\/a> in one of the chapters of the book \u201c<a href=\"http:\/\/oscarperpinan.github.io\/spacetime-vis\/\">Displaying time series, spatial and space-time data with R<\/a>\u201c<\/strong><\/p>\n<p>Some time ago I found <a href=\"http:\/\/www.nytimes.com\/interactive\/2009\/03\/10\/us\/20090310-immigration-explorer.html\">this infographic from The New York Times<\/a> (via <a href=\"http:\/\/www.smallmeans.com\/new-york-times-infographics\/\">this page<\/a>) and I wondered how a multivariate choropleth map could be produced with R. Here is the code I have arranged to show the <a>results of the last Spanish general elections<\/a> in a similar fashion.<\/p>\n<p>Some packages are needed:<\/p>\n<div>\n<div id=\"highlighter_78255\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(maps)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(maptools)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r comments\">## EDITED: if you have rgeos installed you won't need<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r comments\">## gpclibPermit() below.<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(sp)<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(lattice)<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(latticeExtra)<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(colorspace)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Let\u2019s start with the data, which is available <a href=\"http:\/\/dl.dropbox.com\/u\/40293713\/spainVotes\/votos2011.rda\">here<\/a> (thanks to <a href=\"http:\/\/uce.uniovi.es\/~emilio\/\">Emilio Torres<\/a>, who \u201cmassaged\u201d the original dataset, available from <a href=\"http:\/\/www.infoelectoral.mir.es\/docxl\/04_201105_1.zip\">here<\/a>).<\/p>\n<p>Each region of the map will represent the percentage of votes obtained by the predominant political option. Besides, only four groups will be considered: the two main parties (\u201cPP\u201d and \u201cPSOE\u201d), the abstention results (\u201cABS\u201d), and the rest of parties (\u201cOTH\u201d).<\/p>\n<div>\n<div id=\"highlighter_45829\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<div class=\"line number13 index12 alt2\">13<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r functions\">load<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">url<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'<a href=\"http:\/\/dl.dropbox.com\/u\/40293713\/spainVotes\/votos2011.rda\">http:\/\/dl.dropbox.com\/u\/40293713\/spainVotes\/votos2011.rda<\/a>'<\/code><code class=\"r plain\">))<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">votesData &lt;- votos2011[, 12:1023] <\/code><code class=\"r comments\">##I don't need all the columns<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">votesData$ABS &lt;- <\/code><code class=\"r functions\">with<\/code><code class=\"r plain\">(votos2011, Total.censo.electoral - Votos.validos) <\/code><code class=\"r comments\">##abstention<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r plain\">Max &lt;- <\/code><code class=\"r functions\">apply<\/code><code class=\"r plain\">(votesData, 1, max)<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r plain\">whichMax &lt;- <\/code><code class=\"r functions\">apply<\/code><code class=\"r plain\">(votesData,\u00a0 1, <\/code><code class=\"r functions\">function<\/code><code class=\"r plain\">(x)<\/code><code class=\"r functions\">names<\/code><code class=\"r plain\">(votesData)[<\/code><code class=\"r functions\">which.max<\/code><code class=\"r plain\">(x)])<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r comments\">## OTH for everything but PP, PSOE and ABS<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r plain\">whichMax[!(whichMax %<\/code><code class=\"r keyword\">in<\/code><code class=\"r plain\">% <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'PP'<\/code><code class=\"r plain\">,\u00a0 <\/code><code class=\"r string\">'PSOE'<\/code><code class=\"r plain\">, <\/code><code class=\"r string\">'ABS'<\/code><code class=\"r plain\">))] &lt;- <\/code><code class=\"r string\">'OTH'<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><\/div>\n<div class=\"line number12 index11 alt1\"><code class=\"r comments\">## Finally, I calculate the percentage of votes with the electoral census<\/code><\/div>\n<div class=\"line number13 index12 alt2\"><code class=\"r plain\">pcMax &lt;- Max\/votos2011$Total.censo.electoral * 100<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>The Spanish administrative boundaries are available as shapefiles at the <a href=\"http:\/\/www.ine.es\/ss\/Satellite?c=Page&amp;p=1254735116596&amp;pagename=ProductosYServicios%2FPYSLayout&amp;cid=1254735116596&amp;L=1\">INE webpage<\/a> (~70Mb):<\/p>\n<div>\n<div id=\"highlighter_194780\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">espMap &lt;- <\/code><code class=\"r functions\">readShapePoly<\/code><code class=\"r plain\">(fn=<\/code><code class=\"r string\">\"mapas_completo_municipal\/esp_muni_0109\"<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r functions\">Encoding<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">levels<\/code><code class=\"r plain\">(espMap$NOMBRE)) &lt;- <\/code><code class=\"r string\">\"latin1\"<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r comments\">##There are some repeated polygons which can be dissolved with<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r comments\">## unionSpatialPolygons.<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r comments\">## EDITED: gpclibPermit() is needed for unionSpatialPolygons to work<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r comments\">## but can be ommited if you have rgeos installed<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r comments\">## (recommended, see comment of Roger Bivand below).<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r plain\">espPols &lt;- <\/code><code class=\"r functions\">unionSpatialPolygons<\/code><code class=\"r plain\">(espMap, espMap$PROVMUN)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>(EDITED, following the question of Sandra). Spanish maps are commonly displayed with the Canarian islands next to the peninsula. First we have to extract the polygons of the islands and the polygons of the peninsula.<\/p>\n<div>\n<div id=\"highlighter_867923\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">canarias &lt;-\u00a0 <\/code><code class=\"r functions\">sapply<\/code><code class=\"r plain\">(espPols@polygons, <\/code><code class=\"r keyword\">function<\/code><code class=\"r plain\">(x)<\/code><code class=\"r functions\">substr<\/code><code class=\"r plain\">(x@ID, 1, 2) %<\/code><code class=\"r keyword\">in<\/code><code class=\"r plain\">% <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">\"35\"<\/code><code class=\"r plain\">,\u00a0 <\/code><code class=\"r string\">\"38\"<\/code><code class=\"r plain\">))<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">peninsulaPols &lt;- espPols[!canarias]<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">islandPols &lt;- espPols[canarias]<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Then we shift the coordinates of the islands:<\/p>\n<div>\n<div id=\"highlighter_649770\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">dy &lt;- <\/code><code class=\"r functions\">bbox<\/code><code class=\"r plain\">(peninsulaPols)[2,1] - <\/code><code class=\"r functions\">bbox<\/code><code class=\"r plain\">(islandPols)[2,1]<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">dx &lt;- <\/code><code class=\"r functions\">bbox<\/code><code class=\"r plain\">(peninsulaPols)[1,2] - <\/code><code class=\"r functions\">bbox<\/code><code class=\"r plain\">(islandPols)[1,2]<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">islandPols2 &lt;- <\/code><code class=\"r functions\">elide<\/code><code class=\"r plain\">(islandPols, shift=<\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(dx, dy))<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r plain\">bbIslands &lt;- <\/code><code class=\"r functions\">bbox<\/code><code class=\"r plain\">(islandPols2)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>and finally construct a new object binding the shifted islands with the peninsula:<\/p>\n<div>\n<div id=\"highlighter_501985\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">espPols &lt;- <\/code><code class=\"r functions\">rbind<\/code><code class=\"r plain\">(peninsulaPols, islandPols2)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>The last step before drawing the map is to link the data with the polygons:<\/p>\n<div>\n<div id=\"highlighter_943845\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<div class=\"line number13 index12 alt2\">13<\/div>\n<div class=\"line number14 index13 alt1\">14<\/div>\n<div class=\"line number15 index14 alt2\">15<\/div>\n<div class=\"line number16 index15 alt1\">16<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">IDs &lt;- <\/code><code class=\"r functions\">sapply<\/code><code class=\"r plain\">(espPols@polygons, <\/code><code class=\"r functions\">function<\/code><code class=\"r plain\">(x)x@ID)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">idx &lt;- <\/code><code class=\"r functions\">match<\/code><code class=\"r plain\">(IDs, votos2011$PROVMUN)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r comments\">##Places without information<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r plain\">idxNA &lt;- <\/code><code class=\"r functions\">which<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">is.na<\/code><code class=\"r plain\">(idx))<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r comments\">##Information to be added to the SpatialPolygons object<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r plain\">dat2add &lt;- <\/code><code class=\"r functions\">data.frame<\/code><code class=\"r plain\">(prov = votos2011$PROV,<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r plain\">poblacion = votos2011$Nombre.de.Municipio,<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r plain\">Max = Max,\u00a0 pcMax = pcMax,\u00a0 who = whichMax)[idx, ]<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><\/div>\n<div class=\"line number12 index11 alt1\"><code class=\"r functions\">row.names<\/code><code class=\"r plain\">(dat2add) &lt;- IDs<\/code><\/div>\n<div class=\"line number13 index12 alt2\"><code class=\"r plain\">espMapVotes &lt;- <\/code><code class=\"r functions\">SpatialPolygonsDataFrame<\/code><code class=\"r plain\">(espPols, dat2add)<\/code><\/div>\n<div class=\"line number14 index13 alt1\"><\/div>\n<div class=\"line number15 index14 alt2\"><code class=\"r comments\">## Drop those places without information<\/code><\/div>\n<div class=\"line number16 index15 alt1\"><code class=\"r plain\">espMapVotes &lt;- espMapVotes[-idxNA, ]<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>So let\u2019s draw the map. I will produce a list of plots, one for each group. The<a href=\"http:\/\/latticeextra.r-forge.r-project.org\/#layer\">\u201c+.trellis\u201d method<\/a> of the <a href=\"http:\/\/latticeextra.r-forge.r-project.org\/#\">latticeExtra<\/a> package with <code>Reduce<\/code> superposes the elements of this list and produce a <code>trellis<\/code> object. I will use a set of sequential palettes from the <a href=\"http:\/\/cran.r-project.org\/web\/packages\/colorspace\/\">colorspace<\/a> package with a different <a href=\"http:\/\/en.wikipedia.org\/wiki\/Hue\">hue<\/a> for each group.<\/p>\n<div>\n<div id=\"highlighter_436219\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">classes &lt;- <\/code><code class=\"r functions\">levels<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">factor<\/code><code class=\"r plain\">(whichMax))<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">nClasses &lt;- <\/code><code class=\"r functions\">length<\/code><code class=\"r plain\">(classes)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">pList &lt;- <\/code><code class=\"r functions\">lapply<\/code><code class=\"r plain\">(1:nClasses, <\/code><code class=\"r functions\">function<\/code><code class=\"r plain\">(i){<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">mapClass &lt;- espMapVotes[espMapVotes$who==classes[i],]<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">step &lt;- 360\/nClasses <\/code><code class=\"r comments\">## distance between hues<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">pal &lt;- <\/code><code class=\"r functions\">rev<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">sequential_hcl<\/code><code class=\"r plain\">(16, h = (30 + step*(i-1))%%360)) <\/code><code class=\"r comments\">## hues equally spaced<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">pClass &lt;- <\/code><code class=\"r functions\">spplot<\/code><code class=\"r plain\">(mapClass[<\/code><code class=\"r string\">'pcMax'<\/code><code class=\"r plain\">], col.regions=pal, lwd=0.1,<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">at = <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(0, 20, 40, 60, 80, 100))<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">})<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><\/div>\n<div class=\"line number12 index11 alt1\"><code class=\"r plain\">p &lt;- <\/code><code class=\"r functions\">Reduce<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'+'<\/code><code class=\"r plain\">, pList)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>However, the legend of this <code>trellis<\/code> object is not valid.<\/p>\n<p>First, a title for the legend of each element <code>pList<\/code> will be<br \/>\nuseful. Unfortunately, the levelplot function (the engine under the<br \/>\nspplot method) does not allow for a title with its <code>colorkey<\/code><br \/>\nargument. The <code>frameGrob<\/code> and <code>packGrob<\/code> of the <code>grid<\/code> package will do the work.<\/p>\n<div>\n<div id=\"highlighter_274933\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<div class=\"line number13 index12 alt2\">13<\/div>\n<div class=\"line number14 index13 alt1\">14<\/div>\n<div class=\"line number15 index14 alt2\">15<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">addTitle &lt;- <\/code><code class=\"r keyword\">function<\/code><code class=\"r plain\">(legend, title){<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">titleGrob &lt;- <\/code><code class=\"r functions\">textGrob<\/code><code class=\"r plain\">(title, gp=<\/code><code class=\"r functions\">gpar<\/code><code class=\"r plain\">(fontsize=8), hjust=1, vjust=1)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">legendGrob &lt;- <\/code><code class=\"r functions\">eval<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">as.call<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">as.symbol<\/code><code class=\"r plain\">(legend$fun), legend$args)))<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">ly &lt;- <\/code><code class=\"r functions\">grid.layout<\/code><code class=\"r plain\">(ncol=1, nrow=2, widths=<\/code><code class=\"r functions\">unit<\/code><code class=\"r plain\">(0.9, <\/code><code class=\"r string\">'grobwidth'<\/code><code class=\"r plain\">, data=legendGrob))<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">fg &lt;- <\/code><code class=\"r functions\">frameGrob<\/code><code class=\"r plain\">(ly, name=<\/code><code class=\"r functions\">paste<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'legendTitle'<\/code><code class=\"r plain\">, title, sep=<\/code><code class=\"r string\">'_'<\/code><code class=\"r plain\">))<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">pg &lt;- <\/code><code class=\"r functions\">packGrob<\/code><code class=\"r plain\">(fg, titleGrob, row=2)<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">pg &lt;- <\/code><code class=\"r functions\">packGrob<\/code><code class=\"r plain\">(pg, legendGrob, row=1)<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">}<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r functions\">for <\/code><code class=\"r plain\">(i <\/code><code class=\"r keyword\">in<\/code> <code class=\"r functions\">seq_along<\/code><code class=\"r plain\">(classes)){<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">lg &lt;- pList[[i]]$legend$right<\/code><\/div>\n<div class=\"line number12 index11 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">lg$args$key$labels$cex=<\/code><code class=\"r functions\">ifelse<\/code><code class=\"r plain\">(i==nClasses, 0.8, 0) <\/code><code class=\"r comments\">##only the last legend needs labels<\/code><\/div>\n<div class=\"line number13 index12 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">pList[[i]]$legend$right &lt;- <\/code><code class=\"r functions\">list<\/code><code class=\"r plain\">(fun=<\/code><code class=\"r string\">'addTitle'<\/code><code class=\"r plain\">,<\/code><\/div>\n<div class=\"line number14 index13 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">args=<\/code><code class=\"r functions\">list<\/code><code class=\"r plain\">(legend=lg, title=classes[i]))<\/code><\/div>\n<div class=\"line number15 index14 alt2\"><code class=\"r plain\">}<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Now, every component of <code>pList<\/code> includes a legend with a title below. The last step is to modify the legend of the <code>p<\/code> trellis object in order to merge the legends from every component of <code>pList<\/code>.<\/p>\n<div>\n<div id=\"highlighter_884397\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<div class=\"line number13 index12 alt2\">13<\/div>\n<div class=\"line number14 index13 alt1\">14<\/div>\n<div class=\"line number15 index14 alt2\">15<\/div>\n<div class=\"line number16 index15 alt1\">16<\/div>\n<div class=\"line number17 index16 alt2\">17<\/div>\n<div class=\"line number18 index17 alt1\">18<\/div>\n<div class=\"line number19 index18 alt2\">19<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r comments\">## list of legends<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">legendList &lt;- <\/code><code class=\"r functions\">lapply<\/code><code class=\"r plain\">(pList, <\/code><code class=\"r functions\">function<\/code><code class=\"r plain\">(x){<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">lg &lt;- x$legend$right<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">clKey &lt;- <\/code><code class=\"r functions\">eval<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">as.call<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">as.symbol<\/code><code class=\"r plain\">(lg$fun), lg$args)))<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">clKey<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r plain\">})<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r comments\">##function to pack the list of legends in a unique legend<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r comments\">##adapted from latticeExtra::: mergedTrellisLegendGrob<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r plain\">packLegend &lt;- <\/code><code class=\"r keyword\">function<\/code><code class=\"r plain\">(legendList){<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">N &lt;- <\/code><code class=\"r functions\">length<\/code><code class=\"r plain\">(legendList)<\/code><\/div>\n<div class=\"line number12 index11 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">ly &lt;- <\/code><code class=\"r functions\">grid.layout<\/code><code class=\"r plain\">(nrow = 1,\u00a0 ncol = N)<\/code><\/div>\n<div class=\"line number13 index12 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">g &lt;- <\/code><code class=\"r functions\">frameGrob<\/code><code class=\"r plain\">(layout = ly, name = <\/code><code class=\"r string\">\"mergedLegend\"<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number14 index13 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r functions\">for <\/code><code class=\"r plain\">(i <\/code><code class=\"r keyword\">in<\/code> <code class=\"r plain\">1:N) g &lt;- <\/code><code class=\"r functions\">packGrob<\/code><code class=\"r plain\">(g, legendList[[i]], col = i)<\/code><\/div>\n<div class=\"line number15 index14 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">g<\/code><\/div>\n<div class=\"line number16 index15 alt1\"><code class=\"r plain\">}<\/code><\/div>\n<div class=\"line number17 index16 alt2\"><\/div>\n<div class=\"line number18 index17 alt1\"><code class=\"r comments\">## The legend of p will include all the legends<\/code><\/div>\n<div class=\"line number19 index18 alt2\"><code class=\"r plain\">p$legend$right &lt;- <\/code><code class=\"r functions\">list<\/code><code class=\"r plain\">(fun = <\/code><code class=\"r string\">'packLegend'<\/code><code class=\"r plain\">,\u00a0 args = <\/code><code class=\"r functions\">list<\/code><code class=\"r plain\">(legendList = legendList))<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Here is the result with the provinces boundaries superposed (only for the peninsula due to a problem with the definition of boundaries the Canarian islands in the file) and a rectangle to separate the Canarian islands from the<br \/>\nrest of the map (click on the image to get a SVG file):<\/p>\n<div>\n<div id=\"highlighter_521942\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">provinces &lt;- <\/code><code class=\"r functions\">readShapePoly<\/code><code class=\"r plain\">(fn=<\/code><code class=\"r string\">\"mapas_completo_municipal\/spain_provinces_ag_2\"<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">canarias &lt;- provinces$PROV %<\/code><code class=\"r keyword\">in<\/code><code class=\"r plain\">% <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(35, 38)<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">peninsulaLines &lt;- provinces[!canarias,]<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r plain\">p +<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r functions\">layer<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">sp.polygons<\/code><code class=\"r plain\">(peninsulaLines,\u00a0 lwd = 0.5)) +<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r functions\">layer<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">grid.rect<\/code><code class=\"r plain\">(x=bbIslands[1,1], y=bbIslands[2,1],<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">width=<\/code><code class=\"r functions\">diff<\/code><code class=\"r plain\">(bbIslands[1,]),<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">height=<\/code><code class=\"r functions\">diff<\/code><code class=\"r plain\">(bbIslands[2,]),<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">default.units=<\/code><code class=\"r string\">'native'<\/code><code class=\"r plain\">, just=<\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'left'<\/code><code class=\"r plain\">, <\/code><code class=\"r string\">'bottom'<\/code><code class=\"r plain\">),<\/code><\/div>\n<div class=\"line number12 index11 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">gp=<\/code><code class=\"r functions\">gpar<\/code><code class=\"r plain\">(lwd=0.5, fill=<\/code><code class=\"r string\">'transparent'<\/code><code class=\"r plain\">)))<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p><a href=\"http:\/\/dl.dropbox.com\/u\/40293713\/spainVotes\/spainVotes.svg\"><img loading=\"lazy\" decoding=\"async\" src=\"https:\/\/procomun.files.wordpress.com\/2012\/04\/spainvotes.jpeg?w=1280&amp;h=1064\" alt=\"https:\/\/procomun.files.wordpress.com\/2012\/04\/spainvotes.jpeg\" width=\"1280\" height=\"1064\" \/><\/a><\/p>\n<p>In my <a href=\"https:\/\/procomun.wordpress.com\/2012\/02\/18\/maps_with_r_1\/\">my last post<\/a> I described how to produce a multivariate choropleth map with R. Now I will show how to create a map from raster files. One of them is a factor which will group the values of the other one. Thus, once again, I will superpose several groups in the same map.<\/p>\n<p><strong>NOTE: Although the procedure described in this post is valid, there is a<a href=\"https:\/\/github.com\/oscarperpinan\/spacetime-vis\/tree\/master\/raster.R\">newer code version<\/a> in one of the chapters of the book \u201c<a href=\"http:\/\/oscarperpinan.github.io\/spacetime-vis\/\">Displaying time series, spatial and space-time data with R<\/a>\u201c<\/strong><\/p>\n<p>First let\u2019s load the packages.<\/p>\n<div>\n<div id=\"highlighter_908853\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(raster)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(rasterVis)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(colorspace)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Now, I define the geographical extent to be analyzed (approximately India and China).<\/p>\n<div>\n<div id=\"highlighter_633259\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">ext &lt;- <\/code><code class=\"r functions\">extent<\/code><code class=\"r plain\">(65, 135, 5, 55)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>The first raster file is the <a class=\"zem_slink\" title=\"Population density\" href=\"http:\/\/en.wikipedia.org\/wiki\/Population_density\" rel=\"wikipedia\">population density<\/a> in our planet, available at this<a href=\"http:\/\/neo.sci.gsfc.nasa.gov\/Search.html?group=64\">NEO-NASA webpage<\/a> (choose the <a class=\"zem_slink\" title=\"GeoTIFF\" href=\"http:\/\/en.wikipedia.org\/wiki\/GeoTIFF\" rel=\"wikipedia\">Geo-TIFF<\/a> floating option, ~25Mb). After reading the data with <code>raster<\/code> I subset the geographical extent and replace the 99999 with <code>NA<\/code>.<\/p>\n<div>\n<div id=\"highlighter_837780\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">pop &lt;- <\/code><code class=\"r functions\">raster<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'875430rgb-167772161.0.FLOAT.TIFF'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">pop &lt;- <\/code><code class=\"r functions\">crop<\/code><code class=\"r plain\">(pop, ext)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">pop[pop==99999] &lt;- <\/code><code class=\"r keyword\">NA<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">pTotal &lt;- <\/code><code class=\"r functions\">levelplot<\/code><code class=\"r plain\">(pop, zscaleLog=10, par.settings=BTCTheme)<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r plain\">pTotal<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p><a href=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/pop.jpeg\"><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-1078\" title=\"pop\" src=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/pop.jpeg?w=529&amp;h=529\" alt=\"\" width=\"529\" height=\"529\" \/><\/a>The second raster file is the land cover classification (available at this <a href=\"http:\/\/neo.sci.gsfc.nasa.gov\/Search.html?group=20\">NEO-NASA webpage<\/a>)<\/p>\n<div>\n<div id=\"highlighter_141261\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">landClass &lt;- <\/code><code class=\"r functions\">raster<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'241243rgb-167772161.0.TIFF'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">landClass &lt;- <\/code><code class=\"r functions\">crop<\/code><code class=\"r plain\">(landClass, ext)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>The codes of the classification are described <a href=\"http:\/\/eoimages.gsfc.nasa.gov\/images\/news\/NasaNews\/ReleaseImages\/LCC\/Images\/lcc_key.jpg\">here<\/a>. In summary, the sea is labeled with 0, forests with 1 to 5, shrublands, grasslands and wetlands with 6 to 11, agriculture and urban lands with 12 to 14, and snow and barren with 15 and 16. This four groups (sea is replaced <code>NA<\/code>) will be the levels of the factor. (I am not sure if these sets of different land covers is sensible: comments from experts are welcome!)<\/p>\n<p>EDIT: Following a question from a user of <a title=\"rasterVis\" href=\"http:\/\/rastervis.r-forge.r-project.org\/\">rasterVis<\/a> I include some lines of code to display this qualitative variable in the map.<br \/>\nEDIT2: <code>raster<\/code> and <code>rasterVis<\/code> are able to work with categorical data using ratify<code>.<br \/>\n<\/code><\/p>\n<div>\n<div id=\"highlighter_979003\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<div class=\"line number13 index12 alt2\">13<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">landClass[landClass %<\/code><code class=\"r keyword\">in<\/code><code class=\"r plain\">% <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(0, 254)] &lt;- <\/code><code class=\"r keyword\">NA<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">landClass &lt;- <\/code><code class=\"r functions\">cut<\/code><code class=\"r plain\">(landClass, <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(0, 5, 11, 14, 16))<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r comments\">## Add a Raster Atribute Table and define the raster as categorical data<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">landClass &lt;- <\/code><code class=\"r functions\">ratify<\/code><code class=\"r plain\">(landClass)<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r comments\">## Configure the RAT: first create a RAT data.frame using the<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r comments\">## levels method; second, set the values for each class (to be<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r comments\">## used by levelplot); third, assign this RAT to the raster<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r comments\">## using again levels<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r plain\">rat &lt;- <\/code><code class=\"r functions\">levels<\/code><code class=\"r plain\">(landClass)[[1]]<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r plain\">rat$classes &lt;- <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'Forest'<\/code><code class=\"r plain\">, <\/code><code class=\"r string\">'Land'<\/code><code class=\"r plain\">, <\/code><code class=\"r string\">'Urban'<\/code><code class=\"r plain\">, <\/code><code class=\"r string\">'Snow'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><code class=\"r functions\">levels<\/code><code class=\"r plain\">(landClass) &lt;- rat<\/code><\/div>\n<div class=\"line number12 index11 alt1\"><\/div>\n<div class=\"line number13 index12 alt2\"><code class=\"r functions\">levelplot<\/code><code class=\"r plain\">(landClass, col.regions=<\/code><code class=\"r functions\">terrain_hcl<\/code><code class=\"r plain\">(4))<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p><a href=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/landclass.jpeg\"><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-1109\" title=\"landClass\" src=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/landclass.jpeg?w=529&amp;h=396\" alt=\"\" width=\"529\" height=\"396\" \/><\/a><\/p>\n<p>This histogram shows the distribution of the population density in each land class.<\/p>\n<div>\n<div id=\"highlighter_204177\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">s &lt;- <\/code><code class=\"r functions\">stack<\/code><code class=\"r plain\">(pop, landClass)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r functions\">layerNames<\/code><code class=\"r plain\">(s) &lt;- <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'pop'<\/code><code class=\"r plain\">, <\/code><code class=\"r string\">'landClass'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r functions\">histogram<\/code><code class=\"r plain\">(~<\/code><code class=\"r functions\">log10<\/code><code class=\"r plain\">(pop)|landClass, data=s,<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">scales=<\/code><code class=\"r functions\">list<\/code><code class=\"r plain\">(relation=<\/code><code class=\"r string\">'free'<\/code><code class=\"r plain\">))<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p><a href=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/histogram.jpg\"><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-medium wp-image-1079\" title=\"histogram\" src=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/histogram.jpg?w=300&amp;h=300\" alt=\"\" width=\"300\" height=\"300\" \/><\/a>Everything is ready for the map. I will create a list of <code>trellis<\/code> objects with four elements (one for each level of the factor). Each of these objects is the representation of the population density in a particular land class. I use the same scale for all of them to allow for comparisons (the <code>at<\/code> argument of levelplot receives the correspondent <code>at<\/code> values from the <em>global<\/em> map)<\/p>\n<div>\n<div id=\"highlighter_320975\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">at &lt;- pTotal$legend$bottom$args$key$at<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">pList &lt;- <\/code><code class=\"r functions\">lapply<\/code><code class=\"r plain\">(1:nClasses, <\/code><code class=\"r keyword\">function<\/code><code class=\"r plain\">(i){<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">landSub &lt;- landClass<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">landSub[!(landClass==i)] &lt;- <\/code><code class=\"r keyword\">NA<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">popSub &lt;- <\/code><code class=\"r functions\">mask<\/code><code class=\"r plain\">(pop, landSub)<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">step &lt;- 360\/nClasses<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">pal &lt;- <\/code><code class=\"r functions\">rev<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">sequential_hcl<\/code><code class=\"r plain\">(16, h = (30 + step*(i-1))%%360))<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">pClass &lt;- <\/code><code class=\"r functions\">levelplot<\/code><code class=\"r plain\">(popSub, zscaleLog=10, at=at,<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">col.regions=pal, margin=<\/code><code class=\"r keyword\">FALSE<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><code class=\"r plain\">})<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>And that\u2019s all. The rest of the code is exactly the same as in <a href=\"https:\/\/procomun.wordpress.com\/2012\/02\/18\/maps_with_r_1\/\">the previous post<\/a>. If you execute it you will get this image (click on it for higher resolution).<\/p>\n<p><a href=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/pop_landclass.jpg\"><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-1075\" title=\"pop_landClass\" src=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/pop_landclass.jpg?w=529&amp;h=396\" alt=\"\" width=\"529\" height=\"396\" \/><\/a><\/p>\n<p>In my previous posts (<a title=\"Maps with R\u00a0(I)\" href=\"https:\/\/procomun.wordpress.com\/2012\/02\/18\/maps_with_r_1\/\" target=\"_blank\" rel=\"noopener\">1<\/a> and <a title=\"Maps with R\u00a0(II)\" href=\"https:\/\/procomun.wordpress.com\/2012\/02\/20\/maps_with_r_2\/\" target=\"_blank\" rel=\"noopener\">2<\/a>) I wrote about maps with complex legends but without any kind of interactivity. In this post I show how to produce an <a href=\"http:\/\/en.wikipedia.org\/wiki\/Scalable_Vector_Graphics\">SVG<\/a>file with interactive functionalities with the <a href=\"http:\/\/cran.r-project.org\/web\/packages\/gridSVG\/\">gridSVG<\/a> package.<\/p>\n<p>As an example, I use a dataset about population from the Spanish <a href=\"http:\/\/ine.es\/\">Instituto Nacional de Estad\u00edstica<\/a>. This organism publishes information using the <a href=\"http:\/\/www.scb.se\/Pages\/StandardNoLeftMeny____314045.aspx\">PC_Axis<\/a>format which can be imported into R with the <a href=\"http:\/\/cran.r-project.org\/web\/packages\/pxR\/\">pxR<\/a> package. This dataset is available at the <a href=\"http:\/\/www.ine.es\/jaxi\/menu.do?type=pcaxis&amp;path=%2Ft20%2Fe260%2Fa2009%2F&amp;file=pcaxis&amp;N=&amp;L=0\">INE webpage<\/a> or directly <a href=\"http:\/\/dl.dropbox.com\/u\/40293713\/annotateMap\/pcaxis-676270323.px\">here<\/a>.<\/p>\n<p>Let\u2019s start loading packages.<\/p>\n<div>\n<div id=\"highlighter_507072\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(gridSVG)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(pxR)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(sp)<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(lattice)<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(latticeExtra)<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(maptools)<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(classInt)<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r functions\">library<\/code><code class=\"r plain\">(colorspace)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Then I read the <code>px<\/code> file and make some changes to get the <code>datWide<\/code> <code>data.frame<\/code>(which is available <a href=\"http:\/\/dl.dropbox.com\/u\/40293713\/annotateMap\/datWide.Rda\">here<\/a> if you are not interested in the PC-Axis details<code><\/code>).<\/p>\n<div>\n<div id=\"highlighter_481142\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">datPX &lt;- <\/code><code class=\"r functions\">read.px<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'pcaxis-676270323.px'<\/code><code class=\"r plain\">, encoding=<\/code><code class=\"r string\">'latin1'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">datWide &lt;- <\/code><code class=\"r functions\">as.data.frame<\/code><code class=\"r plain\">(datPX, direction = <\/code><code class=\"r string\">'wide'<\/code><code class=\"r plain\">, use.codes=<\/code><code class=\"r keyword\">FALSE<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r plain\">provID &lt;- <\/code><code class=\"r functions\">strsplit<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">as.character<\/code><code class=\"r plain\">(datWide$provincias), <\/code><code class=\"r string\">'\u00a0 '<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r plain\">provID &lt;- <\/code><code class=\"r functions\">as.data.frame<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">do.call<\/code><code class=\"r plain\">(rbind, provID))<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r functions\">names<\/code><code class=\"r plain\">(provID) &lt;- <\/code><code class=\"r functions\">c<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'code'<\/code><code class=\"r plain\">, <\/code><code class=\"r string\">'prov'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r plain\">datWide &lt;- <\/code><code class=\"r functions\">cbind<\/code><code class=\"r plain\">(datWide, provID)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Now it\u2019s time to read a suitable <code>shapefile<\/code> (read <a href=\"https:\/\/procomun.wordpress.com\/2012\/02\/18\/maps_with_r_1\/\">the first post of this series<\/a> for information about it).<\/p>\n<div>\n<div id=\"highlighter_96171\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">mapSHP &lt;-\u00a0 <\/code><code class=\"r functions\">readShapePoly<\/code><code class=\"r plain\">(fn = <\/code><code class=\"r string\">'mapas_completo_municipal\/spain_provinces_ind_2'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r functions\">Encoding<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">levels<\/code><code class=\"r plain\">(mapSHP$NOMBRE99)) &lt;- <\/code><code class=\"r string\">\"latin1\"<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r comments\">## The encoding must be UTF8 to be correctly displayed in the SVG file<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r functions\">levels<\/code><code class=\"r plain\">(mapSHP$NOMBRE99) &lt;- <\/code><code class=\"r functions\">enc2utf8<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">levels<\/code><code class=\"r plain\">(mapSHP$NOMBRE99))<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>Both the <code>shapefile<\/code> and the <code>data.frame<\/code> have to be combined using the matches between the <code>PROV<\/code> variable of the <code>shapefile<\/code> and <code>code<\/code> from the <code>data.frame<\/code>. The numeric values of the row names (<code>mapaIDs<\/code>) will be useful in the last step.<\/p>\n<div>\n<div id=\"highlighter_913195\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">idx &lt;- <\/code><code class=\"r functions\">match<\/code><code class=\"r plain\">(mapSHP$PROV, datWide$code)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">Total &lt;- datWide[idx, <\/code><code class=\"r string\">\"Total\"<\/code><code class=\"r plain\">]<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">mapSHP@data &lt;- <\/code><code class=\"r functions\">cbind<\/code><code class=\"r plain\">(mapSHP@data, Total)<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">mapaDat &lt;- <\/code><code class=\"r functions\">as.data.frame<\/code><code class=\"r plain\">(mapSHP)<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r plain\">mapaIDs &lt;- <\/code><code class=\"r functions\">as.numeric<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">rownames<\/code><code class=\"r plain\">(mapaDat))<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>A final step is needed before calling <code>spplot<\/code>. I will use the functions of <code>gridSVG<\/code>to include information in the SVG file according to the characteristics of each polygon. Since <code>gridSVG<\/code> works after the plot has been created, I need a key to identify each polygon and match it with the correspondent element of the original dataset. Unfortunately, the <code>panel.polygonsplot<\/code> (which is the function used by <code>spplot<\/code> when drawing polygons) <a href=\"http:\/\/www.stat.auckland.ac.nz\/~paul\/R\/Names\/MurrellNames.pdf\">does not assign a name<\/a> to each polygon. Let\u2019s create a new function (<code>panel.polygonNames<\/code>) adding a small change in <code>panel.polygonsplot<\/code> (you should read the full code of<code>panel.polygonsplot<\/code> to understand what is happening here).<\/p>\n<div>\n<div id=\"highlighter_891710\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">panel.str &lt;- <\/code><code class=\"r functions\">deparse<\/code><code class=\"r plain\">(panel.polygonsplot, width=500)<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">panel.str &lt;- <\/code><code class=\"r functions\">sub<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">\"grid.polygon\\\\((.*)\\\\)\"<\/code><code class=\"r plain\">,<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r string\">\"grid.polygon(\\\\1, name=paste('ID', slot(pls\\\\[\\\\[i\\\\]\\\\], 'ID'\\\\), sep=':'))\"<\/code><code class=\"r plain\">,<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">panel.str)<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r plain\">panel.polygonNames &lt;- <\/code><code class=\"r functions\">eval<\/code><code class=\"r plain\">(<\/code><code class=\"r functions\">parse<\/code><code class=\"r plain\">(text=panel.str),<\/code><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">envir=<\/code><code class=\"r functions\">environment<\/code><code class=\"r plain\">(panel.polygonsplot))<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>EDITED: Thanks to Andre\u2019s comment (see below), I have found that<code>panel.polygonsplot<\/code> has been changed to add hole-handling. This hack will only work if this new behaviour is disabled with <code>set_Polypath(FALSE)<\/code> before the next code chunk.<br \/>\nNow everything is ready for drawing. I use the <a href=\"http:\/\/books.google.es\/books?id=4gg8yx_lcj0C&amp;lpg=PA78&amp;ots=yzcH8v813H&amp;dq=class%20Intervals%20fisher&amp;pg=PA77#v=onepage&amp;q=class%20Intervals%20fisher&amp;f=false\">jenks<\/a> style of the<code>classIntervals<\/code> function from the <a href=\"http:\/\/cran.r-project.org\/web\/packages\/classInt\/index.html\">classInt<\/a> package to set the breaks of the color key.<\/p>\n<div>\n<div id=\"highlighter_753206\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r plain\">n=7<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">int &lt;- <\/code><code class=\"r functions\">classIntervals<\/code><code class=\"r plain\">(Total, n, style=<\/code><code class=\"r string\">'jenks'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r plain\">pal &lt;- <\/code><code class=\"r functions\">brewer.pal<\/code><code class=\"r plain\">(n, <\/code><code class=\"r string\">'Blues'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r plain\">p &lt;- <\/code><code class=\"r functions\">spplot<\/code><code class=\"r plain\">(mapSHP[<\/code><code class=\"r string\">\"Total\"<\/code><code class=\"r plain\">], panel=panel.polygonNames,<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">col.regions=pal, at=<\/code><code class=\"r functions\">signif<\/code><code class=\"r plain\">(int$brks, digits=2))<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><code class=\"r plain\">p<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>EDITED: You can recover the default hole-handling setting with<code>set_Polypath(TRUE)<\/code> after the <code>p<\/code> object has been printed.<\/p>\n<p>Once the plot has been created (do not close the graphic window!) the<code>grid.garnish<\/code> attaches SVG attributes (in this example <code>onmouseover<\/code> and<code>onmouseout<\/code>) to each polygon, which is identified with its name thanks to the<code>panel.polygonNames function<\/code>.<\/p>\n<p>These attributes are related to <code>javascript<\/code> functions (<code>showTooltip<\/code> and<code>hideTooltip<\/code>) included in this <a href=\"http:\/\/dl.dropbox.com\/u\/40293713\/annotateMap\/tooltip.js\">javascript file<\/a> (this file is only a minor modification of the original file available at the <a href=\"http:\/\/www.stat.auckland.ac.nz\/~paul\/gridSVG\/\">webpage of the creator of <code>grid<\/code>and <code>gridSVG<\/code><\/a>). The <code>grid.script<\/code> function attaches the <code>javascript<\/code> file to the <code>grob<\/code>and <code>gridToSVG<\/code> produces the SVG file with a simple HTML page. EDITED: The javascript file (tooltip.js) must be saved in the same folder as the SVG and HTML files.<\/p>\n<div>\n<div id=\"highlighter_519678\" class=\"syntaxhighlighter  r\">\n<table border=\"0\" cellspacing=\"0\" cellpadding=\"0\">\n<tbody>\n<tr>\n<td class=\"gutter\">\n<div class=\"line number1 index0 alt2\">1<\/div>\n<div class=\"line number2 index1 alt1\">2<\/div>\n<div class=\"line number3 index2 alt2\">3<\/div>\n<div class=\"line number4 index3 alt1\">4<\/div>\n<div class=\"line number5 index4 alt2\">5<\/div>\n<div class=\"line number6 index5 alt1\">6<\/div>\n<div class=\"line number7 index6 alt2\">7<\/div>\n<div class=\"line number8 index7 alt1\">8<\/div>\n<div class=\"line number9 index8 alt2\">9<\/div>\n<div class=\"line number10 index9 alt1\">10<\/div>\n<div class=\"line number11 index10 alt2\">11<\/div>\n<div class=\"line number12 index11 alt1\">12<\/div>\n<div class=\"line number13 index12 alt2\">13<\/div>\n<div class=\"line number14 index13 alt1\">14<\/div>\n<div class=\"line number15 index14 alt2\">15<\/div>\n<div class=\"line number16 index15 alt1\">16<\/div>\n<div class=\"line number17 index16 alt2\">17<\/div>\n<div class=\"line number18 index17 alt1\">18<\/div>\n<div class=\"line number19 index18 alt2\">19<\/div>\n<div class=\"line number20 index19 alt1\">20<\/div>\n<div class=\"line number21 index20 alt2\">21<\/div>\n<div class=\"line number22 index21 alt1\">22<\/div>\n<div class=\"line number23 index22 alt2\">23<\/div>\n<div class=\"line number24 index23 alt1\">24<\/div>\n<div class=\"line number25 index24 alt2\">25<\/div>\n<\/td>\n<td class=\"code\">\n<div class=\"container\">\n<div class=\"line number1 index0 alt2\"><code class=\"r comments\">## grobs in the graphical output<\/code><\/div>\n<div class=\"line number2 index1 alt1\"><code class=\"r plain\">grobs &lt;- <\/code><code class=\"r functions\">grid.ls<\/code><code class=\"r plain\">()<\/code><\/div>\n<div class=\"line number3 index2 alt2\"><code class=\"r comments\">## only interested in those with \"ID:\" in the name<\/code><\/div>\n<div class=\"line number4 index3 alt1\"><code class=\"r plain\">nms &lt;- grobs$name[grobs$type == <\/code><code class=\"r string\">\"grobListing\"<\/code><code class=\"r plain\">]<\/code><\/div>\n<div class=\"line number5 index4 alt2\"><code class=\"r plain\">idxNames &lt;- <\/code><code class=\"r functions\">grep<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'ID:'<\/code><code class=\"r plain\">, nms)<\/code><\/div>\n<div class=\"line number6 index5 alt1\"><code class=\"r plain\">IDs &lt;- nms[idxNames]<\/code><\/div>\n<div class=\"line number7 index6 alt2\"><\/div>\n<div class=\"line number8 index7 alt1\"><code class=\"r functions\">for <\/code><code class=\"r plain\">(id <\/code><code class=\"r keyword\">in<\/code> <code class=\"r functions\">unique<\/code><code class=\"r plain\">(IDs)){<\/code><\/div>\n<div class=\"line number9 index8 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r comments\">## extract information from the data<\/code><\/div>\n<div class=\"line number10 index9 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r comments\">## according to the ID value<\/code><\/div>\n<div class=\"line number11 index10 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">i &lt;- <\/code><code class=\"r functions\">strsplit<\/code><code class=\"r plain\">(id, <\/code><code class=\"r string\">'ID:'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number12 index11 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">i &lt;- <\/code><code class=\"r functions\">sapply<\/code><code class=\"r plain\">(i, <\/code><code class=\"r keyword\">function<\/code><code class=\"r plain\">(x)<\/code><code class=\"r functions\">as.numeric<\/code><code class=\"r plain\">(x[2]))<\/code><\/div>\n<div class=\"line number13 index12 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">dat &lt;- mapaDat[<\/code><code class=\"r functions\">which<\/code><code class=\"r plain\">(mapaIDs==i),]<\/code><\/div>\n<div class=\"line number14 index13 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r comments\">## Information to be attached to each polygon<\/code><\/div>\n<div class=\"line number15 index14 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">info &lt;- <\/code><code class=\"r functions\">paste<\/code><code class=\"r plain\">(dat$NOMBRE99, dat$Total, sep=<\/code><code class=\"r string\">':'<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number16 index15 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r plain\">g &lt;- <\/code><code class=\"r functions\">grid.get<\/code><code class=\"r plain\">(id)<\/code><\/div>\n<div class=\"line number17 index16 alt2\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r comments\">## attach SVG attributes<\/code><\/div>\n<div class=\"line number18 index17 alt1\"><code class=\"r spaces\">\u00a0\u00a0<\/code><code class=\"r functions\">grid.garnish<\/code><code class=\"r plain\">(id,<\/code><\/div>\n<div class=\"line number19 index18 alt2\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">onmouseover=<\/code><code class=\"r functions\">paste<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">\"showTooltip(evt, '\"<\/code><code class=\"r plain\">, info, <\/code><code class=\"r string\">\"')\"<\/code><code class=\"r plain\">),<\/code><\/div>\n<div class=\"line number20 index19 alt1\"><code class=\"r spaces\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<\/code><code class=\"r plain\">onmouseout=<\/code><code class=\"r string\">\"hideTooltip()\"<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number21 index20 alt2\"><code class=\"r plain\">}<\/code><\/div>\n<div class=\"line number22 index21 alt1\"><\/div>\n<div class=\"line number23 index22 alt2\"><code class=\"r functions\">grid.script<\/code><code class=\"r plain\">(filename=<\/code><code class=\"r string\">\"tooltip.js\"<\/code><code class=\"r plain\">)<\/code><\/div>\n<div class=\"line number24 index23 alt1\"><\/div>\n<div class=\"line number25 index24 alt2\"><code class=\"r functions\">gridToSVG<\/code><code class=\"r plain\">(<\/code><code class=\"r string\">'map_with_annotations.svg'<\/code><code class=\"r plain\">)<\/code><\/div>\n<\/div>\n<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<\/div>\n<\/div>\n<p>(Click on the image to show the SVG graphic. Move the mouse over it to display the information)<\/p>\n<p><a href=\"http:\/\/dl.dropbox.com\/u\/40293713\/annotateMap\/map_with_annotations.svg.html\"><img loading=\"lazy\" decoding=\"async\" src=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/wpid-map.jpg?w=1920&amp;h=1440\" alt=\"https:\/\/procomun.files.wordpress.com\/2012\/02\/map.jpg\" width=\"1920\" height=\"1440\" \/><\/a><\/p>\n<h6 class=\"zemanta-related-title\"><\/h6>\n","protected":false},"excerpt":{"rendered":"<p>This is the first post of a short series to show some code I have learnt to produce maps with R. NOTE: Although the procedure&hellip; <\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[20],"tags":[],"class_list":["post-845","post","type-post","status-publish","format-standard","hentry","category-r"],"_links":{"self":[{"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/posts\/845","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/comments?post=845"}],"version-history":[{"count":0,"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/posts\/845\/revisions"}],"wp:attachment":[{"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/media?parent=845"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/categories?post=845"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/zhuoyao.net\/index.php\/wp-json\/wp\/v2\/tags?post=845"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}