Home > Net >  GGplot second y axis without the transformation of y axis
GGplot second y axis without the transformation of y axis

Time:09-21

Does any one know how do you apply this

set.seed(101)
x <- 1:10
y <- rnorm(10)
## second data set on a very different scale
z <- runif(10, min=1000, max=10000) 
par(mar = c(5, 4, 4, 4)   0.3)  # Leave space for z axis
plot(x, y) # first plot
par(new = TRUE)
plot(x, z, type = "l", axes = FALSE, bty = "n", xlab = "", ylab = "")
axis(side=4, at = pretty(range(z)))
mtext("z", side=4, line=3)

but using ggplot.

In ggplot you can only create sec.axis() or dup.axis() using a transformation of y axis. What about a whole new independent y axis which will be applied only for z variable and the simple y axis to be applied for the y variable.

CodePudding user response:

ggplot2::sec_axis provides only one mechanism for providing a second axis, and it took a lot of convincing to get that into the codebase. You are responsible for coming up with the transformation. This transform must be linear in some way, so if either axis needs to be non-linear (e.g., exponential, logarithmic, etc), then your expert math skills will be put to the test.

If you can use scales, then this process becomes trivial:

dat <- data.frame(x, y, z)
ggplot(dat, aes(x, y))  
  geom_point()  
  geom_line(
    aes(y = zmod),
    data = ~ transform(., zmod = scales::rescale(z, range(y), range(z)))
  )  
  scale_y_continuous(
    sec.axis = sec_axis(~ scales::rescale(., range(dat$z), range(dat$y)),
                        breaks = c(2000,4000,6000,8000))
  )

side by side of base and ggplot2 graphics

Unless I've missed something (I just checked ggplot2-3.3.5's NEWS.md file), this has not changed.

CodePudding user response:

Since there is no perfect correlation between z and y, you can not use a secondary axis but you can normalize them and plot two geoms:

library(tidyverse)

set.seed(101)
x <- 1:10
y <- rnorm(10)
## second data set on a very different scale
z <- runif(10, min=1000, max=10000) 
par(mar = c(5, 4, 4, 4)   0.3)  # Leave space for z axis
plot(x, y) # first plot
par(new = TRUE)
plot(x, z, type = "l", axes = FALSE, bty = "n", xlab = "", ylab = "")
axis(side=4, at = pretty(range(z)))
mtext("z", side=4, line=3)


data <- tibble(
  x = x,
  y = y,
  z = z
)

data %>%
  mutate(y = scale(y), z = scale(z)) %>%
  ggplot(aes(x = x))  
    geom_line(aes(y = z))  
    geom_point(aes(y = y))

Created on 2021-09-20 by the reprex package (v2.0.1)

  • Related