0

I am trying to produce a variable number of rectangles (layers) in a ggplot of a zoo object. I would like to do this in a loop since I do not know ahead of time how many rectangles I will need. Here is a toy example.

library("zoo")
library("ggplot2")
set.seed(1)
y <- runif(50, min = 1, max = 2)
start <- as.numeric(as.Date("2018-01-01"))
x <- as.Date(start:(start + 49))
x.zoo <- zoo(y, order.by = x)
## Fill areas
bars <- data.frame(start = c(x[5], x[20], x[35]),
                end = c(x[10], x[25], x[40]))

I can plot these manually with this code:

## Plot manually
print(autoplot.zoo(x.zoo, facets = NULL) +
        geom_rect(aes(xmin = bars[1,1],
                  xmax = bars[1,2], ymin = -Inf, ymax = Inf),
                  fill = "pink", alpha = 0.01) +
        geom_rect(aes(xmin = bars[2,1],
                  xmax = bars[2,2], ymin = -Inf, ymax = Inf),
                  fill = "pink", alpha = 0.01) +
        geom_rect(aes(xmin = bars[3,1],
                  xmax = bars[3,2], ymin = -Inf, ymax = Inf),
                  fill = "pink", alpha = 0.01))

This gives me this desired image: Desired Image

I tried using the loop below but it only plots the last bar. How do I do this??

## This didn't work but illustrates what I am trying to do
p =  autoplot.zoo(x.zoo, facets = NULL)
for(i in 1:3) {
  p = p + geom_rect(aes(xmin = bars[i,1],
                    xmax = bars[i,2], ymin = -Inf, ymax = Inf),
                    fill = "pink", alpha = 0.01)

}
print(p)
4
  • What is the error? Commented Mar 20, 2018 at 14:09
  • Sorry - I misspoke. This incarnation of the loop only plots the last bar and not the first two. It does NOT throw an error Commented Mar 20, 2018 at 14:27
  • This isn't related to your problem, but as.Date() give me an error unless I supply an origin = parameter specifying how many days to start counting from. Commented Mar 20, 2018 at 14:30
  • @divibisan, OP used the zoo package. @Ernie, please include the important packages. Commented Mar 20, 2018 at 14:32

2 Answers 2

4

You don't need a loop. geom_rect is vectorised

autoplot.zoo(x.zoo, facets = NULL) +
  geom_rect(aes(xmin = start, xmax = end, ymin = -Inf, ymax = Inf), data = bars, fill = "pink", alpha = 0.4, inherit.aes = FALSE) 
Sign up to request clarification or add additional context in comments.

Comments

1

One way to avoid the for loop is to convert x.zoo into a data.frame and map the data to geom_line. This way, you can map the bars data to geom_rect separately.

dat <- data.frame(index = index(x.zoo), data.frame(x.zoo))

ggplot() + 
  geom_rect(data = bars, aes(xmin = start, xmax = end, ymin =-Inf, ymax = Inf), fill = 'pink', alpha = .5) +
  geom_line(data=dat, aes(x = index, y = x.zoo))

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.