Combine Plot and Table in R GGplot2
When presenting data on a plot, it is sometimes useful to also show a table with the actual numbers next to the plot. In some cases (e.g., mean profile plots and forest plots), the x-axes or y-axes of the individual plots/tables need to align with each other.
There are several methods in combine plots and tables in r. In this article we will focus only on simple methods, based on the functions grid.arrange() and ggarrange().
Combine Mean Profile Plot and Table
We will achieve this in three steps:
- Create a mean profile plot
- Create a table with the number of samples per time point
- Combine plot and table
The Dataset
The following dataset will be used to create a mean profile plot (mean value over time). This is a dataset with mean blood glucose and 95% confidence interval over time calculated from a dummy longitudinal dataset.
Details on the longitudinal dataset can be found here. An extra group was added, and the sample sizes were changed to 20 patients per group.
1. Create a Mean Profile Plot
#Mean profiles with 95% confidence interval
g1 <- ggplot(statsBG, aes(x=timedays, y=meanBG, color=groupid, shape=groupid)) +
geom_line() +
geom_errorbar(aes(ymin = ci95lower, ymax = ci95upper), width = 0.3) +
geom_point(size = 3) +
labs(color="Group", x="Day", y = "Mean Fasting Blood Glucose (mg/dl)") +
scale_x_continuous(breaks=seq(1,10,1), limits = c(0.5,10.5)) +
ylim(110, 180) +
#specify "Group" to avoid creating separate legends
scale_color_manual("Group", values = c("#619847", "#023bb8", "#7a608e")) +
scale_shape_manual("Group", values=c(15,16,17)) +
theme_bw() +
#Place legend at the bottom of the plot to help align x-axis of the plot and the table
theme(legend.position="bottom")
g1
We have placed the legend at the bottom of the plot to align the x-axis of the plot and the table below the plot: see legend.position=”bottom” in the theme() function. Placing the legend at the top, or inside the plot area would also be fine.
Other arguments of the legend.position parameter are: “top”, “left” and “right”.
The legend can also be placed inside the plot area using the arguments legend.position=c(x, y), where x and y are the coordinates that can take values from 0 to 1.
2. Create a Table with the Mean Values and Confidence Intervals
The following r code uses the geom_text() function to create a sort of table of the mean values and confidence intervals per day.
*To get the table to align with the above plot, it is important to use the same axis specifications as the plot.
t1 <- ggplot(data=statsBG) +
geom_text(aes(y=groupid, x=timedays, label=paste0(round(n_size, digits=0)), hjust=1, vjust=0.5)) +
ggtitle("Number of Patients") +
#Thesame x-axis specifications as the above plot to ensure alignment
scale_x_continuous(breaks=seq(1,10,1), limits = c(0.5,10.5)) +
#Reverse y-axis to show Group A to C instead of Group C to A
scale_y_discrete(limits=rev) +
theme_classic(base_size=13) +
#Remove axis line, ticks and axis label to get the look of a table
theme(
axis.line = element_blank(),
axis.ticks = element_blank(),
axis.title.y = element_blank(),
axis.title.x = element_blank(),
axis.text.x = element_text(color="white"),
plot.title = element_text(size=11, hjust =-0.06)
)
t1
The axis lines, tick marks and labels were removed to give it a table look.
The order of the y-axis was reversed so that Group A is shown at the top.
3. Combine Plot and Table
To combine the plot and table above, we need to install and load the gridExtra package.
Combining the Plot and Table Using grid.arrange(…, ncol=1)
#Install and load gridExtra
install.packages("gridExtra")
library(gridExtra)
#Combine plot and table
grid.arrange(g1, t1, ncol=1, heights = c(4, 1))
The parameter ncol=1 places the table below the plot, to have one column with 2 rows. If needed, nrow=x can also be used to specify the number of rows x.
The parameter heights=c(4, 1) was used to make the plot four times taller than the table. The parameters widths=c(x, y) can also be used if the plot and table were to be placed side by side.
Combining the Plot and Table Using a Layout Matrix
The layout matrix is used for more complex layouts. But a layout matrix can also be used in our simple case. If we want the height of the plot to be three times that of the table below it, we can use the following layout matrix.
#The layout matrix
mlayout <- rbind(c(1,1,1,1),
c(1,1,1,1),
c(1,1,1,1),
c(2,2,2,2))
#Combine plot and table
grid.arrange(g1, t1, layout_matrix = mlayout)
The parameter layout_matrix=… was used to specify the layout matrix.
Alternatively, we can use the ggarrange() function from the ggpubr package to achieve the same results as above. The ggpubr package also uses the grid.arrange() function:
install.packages("ggpubr")
library(ggpubr)
ggarrange(g1, t1, ncol = 1, heights = c(4, 1))