2
votes

I am creating a chart in R using ggplot inside a function of my program. Depending on when the function is called, certain data may need to be plotted and sometimes not. I am attempting to use if statements within ggplot to handle these different scenarios.

It can be summarized as follows using the mtcars dataset and adding a timestamp which is 3/29/2016 9:00 - 3/29/2016 11:35 incremented by 5 min.

First, the working example without an if statement:

chart <-  ggplot(mtcars, aes(x=Date_Time))+
  geom_rect(aes(ymin=drat, ymax=wt, xmin=Date_Time-80, xmax=Date_Time+80, fill=factor(sign(drat-wt))))+
  scale_fill_manual(guide="none", values=c("red", "green"))

plot (chart)

Working plot

Adding the if statement below creates the error, "Error in geom_rect(aes(ymin = drat, ymax = wt, xmin = Date_Time - 80, : non-numeric argument to binary operator". Also, this error occurs before calling the print command.

    chart <-  ggplot(mtcars, aes(x=Date_Time))+
     if(TRUE){
      geom_rect(aes(ymin=drat, ymax=wt, xmin=Date_Time-80, xmax=Date_Time+80, fill=factor(sign(drat-wt))))+
      scale_fill_manual(guide="none", values=c("red", "green"))
     }

If I remove the "scale_fill_manual" command and leave in the if statement, it works.

chart <-  ggplot(mtcars, aes(x=Date_Time))+
  if(TRUE){
    geom_rect(aes(ymin=drat, ymax=wt, xmin=Date_Time-80, xmax=Date_Time+80, fill=factor(sign(drat-wt))))
  }

plot (chart)

Working example 2

Can anyone shed light on why the if statement is causing such trouble and how I can get ggplot to work with the if statement in place? Also, why does removing the scale_fill_manual command help? Obviously, in my case, I would like to leave in scale_fill_manual.

To generate the mtcars dataset as I have used it, please copy and paste this code:

mtcars <- structure(list(mpg = c(21, 21, 22.8, 21.4, 18.7, 18.1, 14.3, 
24.4, 22.8, 19.2, 17.8, 16.4, 17.3, 15.2, 10.4, 10.4, 14.7, 32.4, 
30.4, 33.9, 21.5, 15.5, 15.2, 13.3, 19.2, 27.3, 26, 30.4, 15.8, 
19.7, 15, 21.4), cyl = c(6, 6, 4, 6, 8, 6, 8, 4, 4, 6, 6, 8, 
8, 8, 8, 8, 8, 4, 4, 4, 4, 8, 8, 8, 8, 4, 4, 4, 8, 6, 8, 4), 
    disp = c(160, 160, 108, 258, 360, 225, 360, 146.7, 140.8, 
    167.6, 167.6, 275.8, 275.8, 275.8, 472, 460, 440, 78.7, 75.7, 
    71.1, 120.1, 318, 304, 350, 400, 79, 120.3, 95.1, 351, 145, 
    301, 121), hp = c(110, 110, 93, 110, 175, 105, 245, 62, 95, 
    123, 123, 180, 180, 180, 205, 215, 230, 66, 52, 65, 97, 150, 
    150, 245, 175, 66, 91, 113, 264, 175, 335, 109), drat = c(3.9, 
    3.9, 3.85, 3.08, 3.15, 2.76, 3.21, 3.69, 3.92, 3.92, 3.92, 
    3.07, 3.07, 3.07, 2.93, 3, 3.23, 4.08, 4.93, 4.22, 3.7, 2.76, 
    3.15, 3.73, 3.08, 4.08, 4.43, 3.77, 4.22, 3.62, 3.54, 4.11
    ), wt = c(2.62, 2.875, 2.32, 3.215, 3.44, 3.46, 3.57, 3.19, 
    3.15, 3.44, 3.44, 4.07, 3.73, 3.78, 5.25, 5.424, 5.345, 2.2, 
    1.615, 1.835, 2.465, 3.52, 3.435, 3.84, 3.845, 1.935, 2.14, 
    1.513, 3.17, 2.77, 3.57, 2.78), qsec = c(16.46, 17.02, 18.61, 
    19.44, 17.02, 20.22, 15.84, 20, 22.9, 18.3, 18.9, 17.4, 17.6, 
    18, 17.98, 17.82, 17.42, 19.47, 18.52, 19.9, 20.01, 16.87, 
    17.3, 15.41, 17.05, 18.9, 16.7, 16.9, 14.5, 15.5, 14.6, 18.6
    ), vs = c(0, 0, 1, 1, 0, 1, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 
    0, 1, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 1), am = c(1, 
    1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 
    0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1), gear = c(4, 4, 4, 3, 
    3, 3, 3, 4, 4, 4, 4, 3, 3, 3, 3, 3, 3, 4, 4, 4, 3, 3, 3, 
    3, 3, 4, 5, 5, 5, 5, 5, 4), carb = c(4, 4, 1, 1, 2, 1, 4, 
    2, 2, 4, 4, 3, 3, 3, 4, 4, 4, 1, 2, 1, 1, 2, 2, 4, 2, 1, 
    2, 2, 4, 6, 8, 2), Date_Time = structure(c(1459256400, 1459256700, 
    1459257000, 1459257300, 1459257600, 1459257900, 1459258200, 
    1459258500, 1459258800, 1459259100, 1459259400, 1459259700, 
    1459260000, 1459260300, 1459260600, 1459260900, 1459261200, 
    1459261500, 1459261800, 1459262100, 1459262400, 1459262700, 
    1459263000, 1459263300, 1459263600, 1459263900, 1459264200, 
    1459264500, 1459264800, 1459265100, 1459265400, 1459265700
    ), class = c("POSIXct", "POSIXt"), tzone = "")), .Names = c("mpg", 
"cyl", "disp", "hp", "drat", "wt", "qsec", "vs", "am", "gear", 
"carb", "Date_Time"), row.names = c("Mazda RX4", "Mazda RX4 Wag", 
"Datsun 710", "Hornet 4 Drive", "Hornet Sportabout", "Valiant", 
"Duster 360", "Merc 240D", "Merc 230", "Merc 280", "Merc 280C", 
"Merc 450SE", "Merc 450SL", "Merc 450SLC", "Cadillac Fleetwood", 
"Lincoln Continental", "Chrysler Imperial", "Fiat 128", "Honda Civic", 
"Toyota Corolla", "Toyota Corona", "Dodge Challenger", "AMC Javelin", 
"Camaro Z28", "Pontiac Firebird", "Fiat X1-9", "Porsche 914-2", 
"Lotus Europa", "Ford Pantera L", "Ferrari Dino", "Maserati Bora", 
"Volvo 142E"), class = "data.frame")

Thank you.

1
Ok, I see your second example, but I suspect it works sort of by accident. I've never seen anyone do this before.joran
I would guess because + is actually ggplot2:::`+.gg` and geom_rect is not of class "gg". I've tried this before, gave up. it would be nice if it workedrawr

1 Answers

4
votes

Probably you won't like this answer, but I just plain wouldn't do this. What's wrong with:

chart <-  ggplot(mtcars, aes(x=Date_Time))
if(TRUE){
  chart <- chart + geom_rect(aes(ymin=drat, ymax=wt, xmin=Date_Time-80, 
                                 xmax=Date_Time+80, fill=factor(sign(drat-wt))))+
  scale_fill_manual(guide="none", values=c("red", "green"))
}