16

Question: I'm trying to create a map of U.S. states/counties with the sf package and geom_sf() from ggplot2, but I can't get the size argument for polygon border line width in geom_sf() to properly create thin lines when size < 1 (e.g. ggplot(sf_obj) %>% geom_sf(size = 0.5).

Specifically, the border lines of a state/county appear to have the same width from the arbitrarily small (e.g. size = 0.05) all the way up to size = 0.702. Then there seems to be a strange cutoff at size = 0.702, above which the border lines abruptly appear wider. Then from size = 0.703 up to size = 1 the border lines appear to have the same width. For size > 1, the border lines appear gradually wider, as expected.

Research: It does appear that geom_sf() supports gradual changes in size < 1, as shown in the code for maps by Bob Rudis here and Matt Strimas-Mackey here. It seems like my issue may be the same one referenced here on ggplot2's Github page titled "geom_sf rounds small sizes up to 1", but the issue was closed and I'm not sure if/how I can implement the fix on my machine. There's another similar-looking issue filed here (and here), but Hadley suggested that the problem in this case may be the graphics device/viewer. I replicated my issue (and the two Github issues linked above) in RStudio and RGUI, but I'm not sure how else to test/change my graphics device/viewer.

Version info: I'm using ggplot2_3.0.0, sf_0.6.3, R version 3.5.1, RStudio version 1.1.456, and Windows 10 version 1803; the issue was also replicated using RGUI.

Code: Below is a reprex using the North Carolina map from the geom_sf() docs. Any help would be appreciated. Thanks!

suppressPackageStartupMessages(library(ggplot2))
suppressPackageStartupMessages(library(reprex))
suppressPackageStartupMessages(library(sf))

#################################################

# plot north carolina map
nc <- sf::st_read(system.file("shape/nc.shp", package = "sf"), quiet = TRUE)
ggplot(nc) + geom_sf(size = 0.05)

nc %>% ggplot() + geom_sf(size = 0.702)

nc %>% ggplot() + geom_sf(size = 0.703)

# get version info
packageVersion("ggplot2")
#> [1] '3.0.0'
packageVersion("sf")
#> [1] '0.6.3'
version
#>                _                           
#> platform       x86_64-w64-mingw32          
#> arch           x86_64                      
#> os             mingw32                     
#> system         x86_64, mingw32             
#> status                                     
#> major          3                           
#> minor          5.1                         
#> year           2018                        
#> month          07                          
#> day            02                          
#> svn rev        74947                       
#> language       R                           
#> version.string R version 3.5.1 (2018-07-02)
#> nickname       Feather Spray

UPDATE: As Chris and Ibusett pointed out, the border lines have the expected width after using ggsave. Thanks!

enter image description here

Spacedman
  • 92,590
  • 12
  • 140
  • 224
sdevine188
  • 338
  • 3
  • 8
  • 3
    Did you output using `ggsave`? I can't reproduce the error on my machine. – Chris Aug 16 '18 at 10:21
  • 3
    I see the same behaviour, but I guess that really depends on the graphics device. For example, if you try saving to pdf using `ggsave` you will have different results. Also, consider that there is a limit on how much "thin" a line can be rendered on your monitor, and that the width of a line on a monitor is inevitably "quantized" (i.e., it can be 1 pixel or 2 pixels, but not 1.5 pixels), so that I think there will always be some "cutoff points" where you see sudden changes. – lbusett Aug 16 '18 at 10:50
  • 2
    I'm voting to close this question because it is a problem of graphic devices rather than a coding problem and the comments have provided a solution as per update of the OP – tjebo Feb 05 '20 at 21:07

1 Answers1

2

This answer is just for the people who don't like to ggsave all their plots, to provide some tricks.

Yes it does depend on the graphics device. Some graphics devices are pretty bad when it comes to these kinds of things (looking at you, default Windows device). The reprex that follows was executed with chunk options set to render the plot with the 'ragg' package.

#+ setup, include=FALSE
knitr::opts_chunk$set(dev = "ragg_png")

#+ main
library(ggplot2)
library(patchwork)

nc <- sf::st_read(system.file("shape/nc.shp", package = "sf"), quiet = TRUE)
p1 <- ggplot(nc) + geom_sf(size = 0.05) + ggtitle("size = 0.05")
p2 <- ggplot(nc) + geom_sf(size = 0.50) + ggtitle("size = 0.50")
p3 <- ggplot(nc) + geom_sf(size = 1.00) + ggtitle("size = 1.00")
p4 <- ggplot(nc) + geom_sf(size = 2.00) + ggtitle("size = 2.00")

p1 + p2 + p3 + p4

Created on 2022-01-14 by the reprex package (v2.0.1)

In markdown files, you can set the default graphics device in a similar way. For setting the device globally for the entire document:

```{r, include = FALSE}
knitr::opts_chunk$set(
  dev = "ragg_png"
)
```

To those working on RStudio, you can change the default graphics device by going to 'Tools > Global options > General > Graphics (tab)'

enter image description here

teunbrand
  • 33,645
  • 4
  • 37
  • 63