rggplot2ggpattern

ggplot: stat_contour_filled combined with ggpattern for region filling based on certain conditions


For example, I want to use ggpattern's stripes to fill in areas for values greater than 50. But the breaks parameter (probably my problem) doesn't achieve the result I want.

library(tidyverse)

d <- expand.grid(x = 1:10 ,y=1:10)
d$value <- 1:100

# The target area is concentrated in the upper right corner
ggplot(data = d,aes(x = x,y = y,fill = value))+
  geom_tile()

ggplot(d)+
  stat_contour_filled(aes(x = x, y = y, z = value),
                      breaks = c(-Inf, 50, Inf),
                      geom = ggpattern::GeomPolygonPattern, 
                      pattern_angle = 60,
                      fill = 'transparent', color = NA,
                      pattern = 'stripe',
                      pattern_fill = 'black',
                      pattern_density = 0.001,
                      pattern_spacing = 0.03,
                      pattern_size = 0.3) +
  scale_pattern_manual(values = c(NA,'stripe'))

or

ggplot(d)+
  stat_contour_filled(aes(x = x, y = y, z = value>50),
                      geom = ggpattern::GeomPolygonPattern, 
                      pattern_angle = 60,
                      fill = 'transparent', color = NA,
                      pattern = 'stripe',
                      pattern_fill = 'black',
                      pattern_density = 0.001,
                      pattern_spacing = 0.03,
                      pattern_size = 0.3)

result: enter image description here


Solution

  • You want to map the pattern aesthetic to a variable so you need to move it inside the aes() function:

    ggplot(d) +
        stat_contour_filled(
            aes(
                x = x,
                y = y,
                z = value,
                pattern = value > 50 # this is new
            ),
            breaks = c(-Inf, 50, Inf),
            geom = ggpattern::GeomPolygonPattern,
            pattern_angle = 60,
            # removed pattern = 'stripe' from here
            fill = "transparent", color = NA,
            pattern_fill = "black",
            pattern_density = 0.001,
            pattern_spacing = 0.03,
            pattern_size = 0.3
        ) +
        scale_pattern_manual(values = c(NA, "stripe")) +
        theme(legend.position = "none")
    

    plot with pattern

    A note on ggpattern options

    This runs fine for me but for the OP returned the error:

    Error in check_numeric_scalar(width, "width") : 
      width must be a numeric scalar
    

    This appears to be related to ggpattern options introduced in R 4.1 as I could reproduce it by setting options(ggpattern_use_R4.1_gradients = FALSE, ggpattern_use_R4.1_masks = FALSE).

    The following options resolved the error:

    options(
        ggpattern_use_R4.1_gradients = TRUE,
        ggpattern_use_R4.1_masks = TRUE,
        ggpattern_geometry_funcs = NULL,
        ggpattern_res = NULL,
        ggpattern_use_R4.1_clipping = NULL,
        ggpattern_use_R4.1_patterns = NULL
    )