使用一个常见图例绘制类tmap的多个对象

时间:2017-02-16 18:00:33

标签: r-grid tmap

我正在尝试使用tm_shape()和tm_layout()在一个页面中使用grid-package中的grid.layout()从tmap-package中绘制多个地图。我想只绘制所有地图的一个常见图例,类似于此处显示的示例:

ggplot separate legend and plot

不幸的是,tmap没有提供ggplot对象。有人知道如何用tmaps做同样的事情吗?这是一个可重复的例子:

data(World, rivers, metro)

# creating two separate maps
africa <- World[World@data$continent=='Africa',]
asia <- World[World@data$continent=='Asia',]

my.breaks <- seq(0,80,20)

africa.map <- tm_shape(africa) + 
  tm_fill("HPI",style = 'fixed',breaks = my.breaks) + 
  tm_layout(bg.color = "white", legend.text.size = 1.3, legend.width = 0.6,
            legend.outside=TRUE, legend.outside.position = 'top', 
            legend.outside.size = .1, legend.position = c(0.8, 0.2))

asia.map <- tm_shape(asia) + 
  tm_fill("HPI",style = 'fixed',breaks = my.breaks) + 
  tm_layout(bg.color = "white", legend.text.size = 1.3, legend.width = 0.6,
            legend.outside=TRUE, legend.outside.position = 'top', 
            legend.outside.size = .1, legend.position = c(0.8, 0.2))

page.layout <- grid.layout(nrow = 8, ncol = 5,
                           widths = unit(c(1), "null"),
                           heights = unit(c(1), "null"),
                           default.units = "null",
                           respect = FALSE,
                           just = "centre")

grid.newpage()
pushViewport(viewport(layout = page.layout))
grid.text(paste('Happy Planet Index'), 
          vp = viewport(layout.pos.row = 1, layout.pos.col = 1:5),gp=gpar(fontsize=20))

grid.text('Africa', vp = viewport(layout.pos.row = 2, layout.pos.col = 1:2),gp=gpar(fontsize=20))
print(africa.map, vp=viewport(layout.pos.row = 3:6, layout.pos.col = 1:2))

grid.text('Asia', vp = viewport(layout.pos.row = 2, layout.pos.col = 3:5),gp=gpar(fontsize=20))
print(asia.map, vp=viewport(layout.pos.row = 3:6, layout.pos.col = 3:5))

最佳, 埃里希

1 个答案:

答案 0 :(得分:2)

我不知道这是不是你的意思:

data(World)

tm_shape(World) +
    tm_polygons(c("economy", "HPI")) +
    tm_layout(legend.outside = TRUE)

常见图例在地图外绘制。由于两个地图都有不同的图例,因此只会拍摄第一张地图的图例。

还有一些方法可以使用grid.layout。在这种情况下,您需要在网格视口中打印tmap贴图(请参阅print.tmap),并在另一个中打印图例。

更新:

只是为了完成:通常,应该有一种方法来使用facets:

data(World)
AfAs <- World[World@data$continent %in% c('Africa', 'Asia'),]
tm_shape(AfAs) + 
    tm_fill("HPI",style = 'fixed',breaks = my.breaks) + 
    tm_facets(by = "continent", drop.units = TRUE, free.coords = TRUE)

如果您需要绘制两个tmap调用,最方便的是将图例作为单独的地图处理legend.only=TRUE

africa.map <- tm_shape(africa) + 
    tm_fill("HPI",style = 'fixed',breaks = my.breaks) +
    tm_layout(legend.show = FALSE)

asia.map <- tm_shape(asia) + 
    tm_fill("HPI",style = 'fixed',breaks = my.breaks) +
    tm_layout(legend.show = FALSE)

legend.map <- tm_shape(africa) + 
    tm_fill("HPI",style = 'fixed',breaks = my.breaks) +
    tm_layout(legend.only = TRUE)

grid.newpage()
page.layout <- grid.layout(nrow = 2, ncol = 2, widths=c(.4,.6), heights=c(.6,.4))
pushViewport(viewport(layout = page.layout))

print(africa.map, vp=viewport(layout.pos.row = 1:2, layout.pos.col = 1))
print(asia.map, vp=viewport(layout.pos.row = 1, layout.pos.col = 2))
print(legend.map, vp=viewport(layout.pos.row = 2, layout.pos.col = 2))

更新2

可以使用以下代码放大图例:

legend.map <- tm_shape(africa) + 
    tm_fill("HPI",style = 'fixed',breaks = my.breaks) +
    tm_layout(legend.only = TRUE, design.mode=TRUE, scale=2, asp=0)
设计地图时,

design.mode=TRUE很方便。我不得不将asp设置为0,因为它占用了非洲的宽高比:这是一个错误,因为当legend.only = TRUE时,宽高比应该遵循设备/视口。这在devel版本中得到修复。