0
votes

I am trying to create a 3X4 plot using grid.arrange and 12 ggplot objects

There is data from 3 data-frames being used to make this larger plot, so 4 ggplot objects are created from each dataset

Here's my code:

dataframes <- list(Healthy, patdata, post_patdata) # making list of dataframes to use in for-loop
data_label<- c("Healthy","Pre-Therapy", "Post-Therapy" ) # another vector used for labeling plots
col<- c("blue","red","green")                        # 3rd vector used for picking plot color
PC1p <- vector("list",12)

for (j in 1:3){

    dataset= dataframes[[j]]

    # PC1
    PC1p[[1+(j-1)*4]]=ggplot(dataset,aes(dataset$PC1w1)) + 
      geom_histogram(alpha=0.3,bins=20, fill=I(col[j]),col=I("black")) + 
ggtitle(paste(data_label[j], " PC1 W1 
              Shoulder Ab/Adduction")) + xlab("Weight 1")+ xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

    PC1p[[2+(j-1)*4]]= ggplot(dataset,aes(dataset$PC1w2))+
  geom_histogram(alpha=0.3,bins=20, fill=I(col[j]), col=I("black"))+
  ggtitle(paste(data_label[j], " PC1 W2 
Shoulder flexion/extension")) +xlab("Weight 2")+ xlim(c(-1,1))+ theme(plot.title = element_text(size=8))

PC1p[[3+(j-1)*4]]= ggplot(dataset,aes(dataset$PC1w3))+
  geom_histogram(alpha=0.3,bins=20, fill=I(col[j]), col=I("black"))+
  ggtitle(paste(data_label[j], " PC1 W3 
Shoulder rotation")) + xlab("Weight 3")+xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

PC1p[[4+(j-1)*4]]= ggplot(dataset,aes(dataset$PC1w4))+
  geom_histogram(alpha=0.3,bins=20, fill=I(col[j]), col=I("black"))+
  ggtitle(paste(data_label[j], " PC1 W4 
                Elbow")) + xlab("Weight 4")+ xlim(c(-1,1))+  theme(plot.title = element_text(size=8))

    }

do.call("grid.arrange", c(PC1p, ncol=4,nrow=3))

The last line, with the do.call and grid.arrange function returns the following error

Error: Aesthetics must be either length 1 or the same as the data (34): x

The same code runs and returns a grid.arrange plot w/o any errors, if all the individuals plots are created from the same dataframe.

Interestingly, if I construct the all 12 ggplot objects separately without using any for-loop, and then use grid.arrange (shown below), the plot is created just fine

p1=ggplot(Healthy,aes(Healthy$PC1w1))+ 
  geom_histogram(alpha=0.3,bins=20, fill=I("blue"),col=I("black"))+ 
  ggtitle("Healthy PC1 W1 
Shoulder Ab/Adduction") + xlab("Weight 1")+   xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

p2= ggplot(Healthy,aes(Healthy$PC1w2))+
  geom_histogram(alpha=0.3,bins=20, fill=I("blue"), col=I("black"))+
  ggtitle("Healthy PC1 W2 
Shoulder flexion/extension") +xlab("Weight 2")+ xlim(c(-1,1))+ theme(plot.title = element_text(size=8))

p3= ggplot(Healthy,aes(Healthy$PC1w3))+
  geom_histogram(alpha=0.3,bins=20, fill=I("blue"), col=I("black"))+
  ggtitle("Healthy PC1 W3 
Shoulder rotation") + xlab("Weight 3")+xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

p4= ggplot(Healthy,aes(Healthy$PC1w4))+
  geom_histogram(alpha=0.3,bins=20, fill=I("blue"), col=I("black"))+
  ggtitle("Healthy PC1 W4 
Elbow") + xlab("Weight 4")+ xlim(c(-1,1))+  theme(plot.title = element_text(size=8))

pre1=ggplot(patdata,aes(patdata$PC1w1))+ 
  geom_histogram(alpha=0.3,bins=20, fill=I("red"),col=I("black"))+ 
  ggtitle("Pre-therapy PC1 W1 
Shoulder Ab/Adduction") + xlab("Weight 1")+   xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

pre2= ggplot(patdata,aes(patdata$PC1w2))+
  geom_histogram(alpha=0.3,bins=20, fill=I("red"), col=I("black"))+
  ggtitle("Pre-therapy PC1 W2 
Shoulder flexion/extension") +xlab("Weight 2")+ xlim(c(-1,1))+ theme(plot.title = element_text(size=8))

pre3= ggplot(patdata,aes(patdata$PC1w3))+
  geom_histogram(alpha=0.3,bins=20, fill=I("red"), col=I("black"))+
  ggtitle("Pre-therapy PC1 W2 
Shoulder rotation") + xlab("Weight 3")+xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

pre4= ggplot(patdata,aes(patdata$PC1w4))+
  geom_histogram(alpha=0.3,bins=20, fill=I("red"), col=I("black"))+
  ggtitle("Pre-therapy PC1 W4 
Elbow") + xlab("Weight 4")+ xlim(c(-1,1))+  theme(plot.title = element_text(size=8))

Post1=ggplot(post_patdata,aes(post_patdata$PC1w1))+ 
  geom_histogram(alpha=0.3,bins=20, fill=I("green"),col=I("black"))+ 
  ggtitle("Post-therapy PC1 W1 
Shoulder Ab/Adduction") + xlab("Weight 1")+   xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

Post2= ggplot(post_patdata,aes(post_patdata$PC1w2))+
  geom_histogram(alpha=0.3,bins=20, fill=I("green"), col=I("black"))+
  ggtitle("Post-therapy PC1 W2 
Shoulder flexion/extension") +xlab("Weight 2")+ xlim(c(-1,1))+ theme(plot.title = element_text(size=8))

Post3= ggplot(post_patdata,aes(post_patdata$PC1w3))+
  geom_histogram(alpha=0.3,bins=20, fill=I("green"), col=I("black"))+
  ggtitle("Post-therapy PC1 W2 
Shoulder rotation") + xlab("Weight 3")+xlim(c(-1,1)) + theme(plot.title = element_text(size=8))

Post4= ggplot(post_patdata,aes(post_patdata$PC1w4))+
  geom_histogram(alpha=0.3,bins=20, fill=I("green"), col=I("black"))+
  ggtitle("Post-therapy PC1 W4 
Elbow") + xlab("Weight 4")+ xlim(c(-1,1))+  theme(plot.title = element_text(size=8))

grid.arrange(p1,p2,p3,p4,pre1,pre2,pre3,pre4,Post1,Post2,Post3,Post4, ncol=4, nrow=3)

I am not sure where I am going wrong. Any guidance will be greatly appreciated

2

2 Answers

0
votes

A good tip to de-bug code would be to start with a simpler case, building up with the less essential details until you are achieving all of the parts of your function.

When I run your code as is in my console, it will not go through with the for loop because of your dataframes list. Is this supposed to be a subset of data stored as a list?

Anyways, my guess is that your function is not producing as many plots as you think. Have you tried testing the length of your list out-put?

0
votes

Removing the reference to the dataframe in the aes() inside the ggplot calls seems to fix the issue.

So instead of writing

ggplot(dataset,aes(dataset$PC1w1)

writing

ggplot(dataset,aes(PC1w1)

for each ggplot call does the trick. I am not quite sure why this fixes it, however, and got the answer from a different blog