r-tmap / tmap

R package for thematic maps
https://r-tmap.github.io/tmap
GNU General Public License v3.0
852 stars 120 forks source link

Position all attribute within map except logo #793

Open ar-onos opened 9 months ago

ar-onos commented 9 months ago

I need to put my logo at the top right of a plot just outside the map window within the title panel box. Is there a way to position the logo alone without attr.position.outside = T, please? I want all other attributes within the plot window except the logo

library(sf)
library(tmap)

tm_shape(NLD_muni) + tm_borders("population") +  tm_layout(bg.color= "#e3f3ff", frame.lwd=0.8, inner.margins = 
c(0.18,0.07,0.05,0.27),panel.label.bg.color ="yellow", panel.labels = "my title", panel.label.size = 0.95, panel.label.fontface = 
"bold",panel.label.color = "white", main.title =NA, frame=T,legend.frame.lwd = 0.5,legend.frame=T,legend.text.color = "gray35", 
legend.text.size=0.55, legend.title.fontface="bold",legend.position=c("right",0.13),legend.title.color = "gray30", 
legend.title.size=0.65,legend.bg.color ="gray95") +  tmap_options(max.raster =c(plot = 1e12 ,view = 1e12),check.and.fix = TRUE)+  tm_logo(Logo, height=1.05, position = c("right",1),  margin = 0 ) 

Here is an example of what I mean: image

tim-salabim commented 9 months ago

I think quarto + grid is a better approach for layouts like this!

ar-onos commented 9 months ago

I think quarto + grid is a better approach for layouts like this!

Thanks @tim-salabim. The panel already comes in with tmap. is there a way to use viewport from grid to insert an image with inset_vp ? This could be an option to position the this since the logo is in png format before exporting the map.

mtennekes commented 9 months ago

I still need to implement tm_logo into v4, but for the time being, either the approach suggested by @tim-salabim or alternatively, a workaround based on this approach here: https://stackoverflow.com/a/69699524

Ignore the ggplot2 part in this code. What is important is the l object, which is a grid::rasterGrob.

The workaround is:

png("mymap.png", width = 800, height = 800)
tm_shape(NLD_muni) + tm_polygons("population")
grid::grid.draw(l)
dev.off()

When creating the rasterGrob, you specify the x, y, width and height. These determine the position of the logo on the device.

ar-onos commented 9 months ago

I still need to implement tm_logo into v4, but for the time being, either the approach suggested by @tim-salabim or alternatively, a workaround based on this approach here: https://stackoverflow.com/a/69699524

Ignore the ggplot2 part in this code. What is important is the l object, which is a grid::rasterGrob.

The workaround is:

png("mymap.png", width = 800, height = 800)
tm_shape(NLD_muni) + tm_polygons("population")
grid::grid.draw(l)
dev.off()

When creating the rasterGrob, you specify the x, y, width and height. These determine the position of the logo on the device.

Thanks, @mtennekes and @tim-salabim . In ggplot2, I can just do:

  TM + annotation_custom(l, xmin = 1, xmax = 1.5, ymin = 210, ymax = 245)

where TM is a ggplot2 object. For tmap V4, is it possible to add something like "tm_annotation" that will allow you to use the viewport to add a png or jpg object to a map while saving with tmap_save ? For example:

AP <- tm_png ("mylogo.png") +tm_annotation( )

# Get bounding box and aspect ratio of i (Country)
xy <- st_bbox(NLD_muni)
asp <- (xy$ymax - xy$ymin)/(xy$xmax - xy$xmin)
## Aspect
# Create viewport for inset map
w <- 0.15
h <- w/3
vp <- viewport(x = 0.95, y = 1.05, width = w, height=w/3, just=c("right", "top"))

##Save Main map and inset to file
tmap_save(NLD, filename= "NLDWhite_20231012.png", dpi = 750, insets_tm= AP, insets_vp= vp)

Another option I imagine is adding this to the tm_layout options:

tm_layout(attr.logo.position.outside=T, attr.logo.position=c("top","right"))

I do a lot of mapping in loops by attributes and having this option to add logos outside where possible will be great.

tim-salabim commented 9 months ago

Imho, it really pays off to learn grid. That way you can have full control of your plotting and mix every and all grid based graphics (tmap, ggplot, lattice, native grid) into the layout of your choice. This may not help directly with your current endeavour, but it will help in the future . And now I'm shutting up and leave it to the experts here...

ar-onos commented 9 months ago

Imho, it really pays off to learn grid. That way you can have full control of your plotting and mix every and all grid based graphics (tmap, ggplot, lattice, native grid) into the layout of your choice. This may not help directly with your current endeavour, but it will help in the future . And now I'm shutting up and leave it to the experts here...

Thanks @tim-salabim for your recommendations.