tmap icon indicating copy to clipboard operation
tmap copied to clipboard

tm_pos_out fails with tm_scalebar

Open DOSull opened this issue 2 years ago • 6 comments

The following code

library(tmap)

data(World)

tm_shape(World) +
  tm_fill() +
  tm_scalebar(
    position = tm_pos_out(
      cell.h = "center", cell.v = "bottom",
      pos.h = "right", pos.v = "top"))

fails with this error Error in if (is.na(unit.size)) { : argument is of length zero

Works fine for tm_compass()

DOSull avatar Nov 07 '23 08:11 DOSull

It took me a while, but it's working now.

mtennekes avatar Jan 11 '24 14:01 mtennekes

It seems that change had some negative consequences (detected by the geocompr gha) -- using custom scalebar breaks returns an error:

library(tmap)
library(sf)
f = system.file("shapes/world.gpkg", package = "spData")
world = read_sf(f)
tanzania = read_sf(f, query = 'SELECT * FROM world WHERE name_long = "Tanzania"')

# works
tm_shape(tanzania) +
  tm_polygons(lwd = 2) +
  tm_scalebar(position = c("left", "bottom"))


# fails
tm_shape(tanzania) +
  tm_polygons(lwd = 2) +
  tm_scalebar(c(0, 200, 400), position = c("left", "bottom"))
#> Error in tmapGridLegPlot.tm_scalebar(X[[i]], ...): object 'sbW' not found

Nowosad avatar Jan 11 '24 18:01 Nowosad

Thx @Nowosad should be working now...

mtennekes avatar Jan 12 '24 07:01 mtennekes

I just checked -- the updated geocompr github action works! Thanks

Nowosad avatar Jan 12 '24 08:01 Nowosad

Scalebar was still buggy in outside position, so changed the behaviour somewhat. Now, the width argument is no longer the map width fraction, but the number of text lines (so an absolute value). This was needed because otherwise it was not possible to determine the grid viewport column width before knowing the map size.

Downside is that users always have set the width scalebar when the position is outside and either on the left- or right-hand-side of the map, even if breaks have been specified. Why? Because this space is needed to claim grid viewport column space. If implemented correctly, this is not needed when the scalebar is below the map, because the grid viewport column space is already large because of the map.

Could you test this @Nowosad ?

mtennekes avatar Feb 07 '24 15:02 mtennekes

It seems to be working fine. I also assume that having a scale bar outside on the left/right is not the most popular situation.

Just one very picky note: look at the second map -- the scale bar starts just a few millimeters left from the frame. Would it be possible to align the scale bar with the frame?

library(tmap)
library(sf)
#> Linking to GEOS 3.12.1, GDAL 3.7.3, PROJ 9.2.1; sf_use_s2() is TRUE
f = system.file("shapes/world.gpkg", package = "spData")
world = read_sf(f)
tanzania = read_sf(f, query = 'SELECT * FROM world WHERE name_long = "Tanzania"')

tm_shape(tanzania) +
        tm_polygons(lwd = 2) +
        tm_scalebar(c(0, 200, 400), position = tm_pos_out("left", "bottom"))


tm_shape(tanzania) +
        tm_polygons(lwd = 2) +
        tm_scalebar(c(0, 200, 400), position = tm_pos_out("center", "bottom"))


tm_shape(tanzania) +
        tm_polygons(lwd = 2) +
        tm_scalebar(c(0, 200, 400), width = 1, position = tm_pos_out("left", "center"))
#> Warning: Not all scale bar breaks could be plotted. Try increasing the scale
#> bar width or descreasing the font size


tm_shape(tanzania) +
        tm_polygons(lwd = 2) +
        tm_scalebar(c(0, 200, 400), width = 20, position = tm_pos_out("left", "center"))

Nowosad avatar Feb 12 '24 13:02 Nowosad

Please check @Nowosad

mtennekes avatar Mar 07 '24 15:03 mtennekes

👍🏻

Nowosad avatar Mar 07 '24 17:03 Nowosad