18

I have searched around for a solution to this, but it appears that most deal with individually generated plots being combined into PDF format, rather than separating out plots generated using faceting onto separate pages of a PDF.

Example Data

In the above data using the following code, selecting all items in the generated list:

Ex<-read.csv("StackOverflowEx (3).csv")
library(ggplot2)
library(reshape2)
vars <- select.list(names(Ex),multiple=TRUE,graphics=TRUE)
Cases<-subset(Ex,select=vars)

gg<-melt(Cases,id=c("Item","Total","Admin"))
print(ggplot(gg, aes(x=Total,y=Admin))+
  geom_point(colour="dark green",size=1.5)+
  geom_point(aes(y=value,color=variable))+
  geom_smooth(aes(y=value,fill=variable),
              method=loess,size=1,linetype=1,se=T)+
  facet_wrap(~variable,ncol=2,nrow=1000)+
  ylim(0,1)+
  labs(x="Expected",y="Admin",title=vars))

...should generate a facet wrap of all 8 (A-H) Cases. However, generating this tends to cramp the plots and make them less readable, and in practice, I intend to use this on 500+ cases (which just returns bars labeled with the column name with no readable charts).

Is it possible to specify the number of charts in the faceting to appear on an individual page when converting to PDF, rather than having all plots compress into a single page? For example, using the above data, generating two 2x2 plots on separate pages that contain all 8 cases individually (i.e. Cases A-D on pg 1, Cases E-H on pg 2).

I could do this by highlighting 4 cases + "Item", "Total" & "Admin" and repeating for the next 4 cases and combining the resultant PDFs. However with upwards of 500 cases in practice this would mean more than 100 iterations with lots of potential for human error. Some help with automating the process would be great.

ZTIrwin42
  • 195
  • 1
  • 6
  • if you search for `marrangeGrob` you might find a few ideas, e.g. [here](http://stackoverflow.com/q/16809488/471093) – baptiste Apr 10 '14 at 20:35
  • 1
    Hadley suggested manual intervention [in 2011](http://osdir.com/ml/ggplot2/2011-06/msg00248.html). I'd try figuring out what # facets/pg works and then sandwich the loop or "apply' over that `n` between `pdf(…)` & `dev.off()` calls. – hrbrmstr Apr 11 '14 at 01:28
  • 1
    I would loop over the 500 variables in groups of 4 or 5 and then generate a chart for each, dumping all to pdf. I recently did something similar where I used a loop to generate 4 plots per page and grid.arrange to plot 4 in each pdf page – user1617979 May 23 '14 at 19:58
  • 1
    All very helpful. Unfortunately, my comprehension exceeds my coding ability, so my efforts thus far have not been very fruitful. – ZTIrwin42 Jun 04 '14 at 15:29
  • Data link at top of post is currently protected. Would be helpful to future users if reproducing example didn't depend on sending a request for permission to access that info on a Google Drive. – noLongerRandom Jan 07 '17 at 15:18

1 Answers1

8

As there is no answer yet. Here is one:

library(ggplot2)
library(reshape2)

Ex <- read.csv("C:/Users/Thomas/Desktop/StackOverflowEx (3).csv")
gg <- melt(Ex,  id = c("Item", "Total", "Admin"))

# put in number of plots here
noPlots <- 4
# save all variables in a seperate vector to select in for-loop
allVars <- unique(gg$variable)
noVars <- length(allVars)

# indices for plotting variables
plotSequence <- c(seq(0, noVars-1, by = noPlots), noVars)

# pdf("plotpath.pdf") # uncomment to save the resulting plots in a pdf file
# loop over the variables to plot
for(ii in 2:length(plotSequence)){
  # select start and end of variables to plot
  start <- plotSequence[ii-1] + 1
  end <- plotSequence[ii]

  # subset the variables and save new temporary data.frame
  tmp <- subset(gg, variable %in% allVars[start:end])
  cat(unique(tmp$variable), "\n")

  # generate plot
  p <- ggplot(tmp,  aes(x = Total, y = Admin))+
    geom_point(colour = "dark green", size = 1.5)+
    geom_point(aes(y = value, color = variable))+
    geom_smooth(aes(y = value, fill = variable), 
                method = loess, size = 1, linetype = 1, se = T)+
    facet_wrap(~variable, ncol = 2, nrow = 1000)+
    ylim(0, 1)+
    labs(x = "Expected",  y = "Admin")
  print(p)
}
# dev.off()
schlusie
  • 1,907
  • 2
  • 20
  • 26
  • Wow. Thank you. I had put this project on the back burner, but your code did exactly what I was looking for. Again, very appreciated. – ZTIrwin42 Apr 29 '15 at 14:54