Можно создать вложенные графики?
Я знаю, что при использовании par( fig=c( ... ), new=T )
вы можете создавать графические вставки. Однако мне было интересно, можно ли использовать библиотеку ggplot2 для создания графиков "вставки".
ОБНОВЛЕНИЕ 1: Я попытался использовать par()
с ggplot2, но он не работает.
ОБНОВЛЕНИЕ 2: я нашел рабочее решение ggplot2 GoogleGroups с помощью grid::viewport()
.
Ответы
Ответ 1
Раздел 8.4 книги объясняет, как это сделать. Хитрость заключается в использовании grid
viewport
пакета grid
s.
#Any old plot
a_plot <- ggplot(cars, aes(speed, dist)) + geom_line()
#A viewport taking up a fraction of the plot area
vp <- viewport(width = 0.4, height = 0.4, x = 0.8, y = 0.2)
#Just draw the plot twice
png("test.png")
print(a_plot)
print(a_plot, vp = vp)
dev.off()
Ответ 2
Я предпочитаю решения, которые работают с ggsave. После многоголоса вокруг я закончил с этим (что является общей формулой для позиционирования и определения размера сюжета, который вы вставляете.
library(tidyverse)
plot1 = qplot(1.00*mpg, 1.00*wt, data=mtcars) # Make sure x and y values are floating values in plot 1
plot2 = qplot(hp, cyl, data=mtcars)
plot(plot1)
# Specify position of plot2 (in percentages of plot1)
# This is in the top left and 25% width and 25% height
xleft = 0.05
xright = 0.30
ybottom = 0.70
ytop = 0.95
# Calculate position in plot1 coordinates
# Extract x and y values from plot1
l1 = ggplot_build(plot1)
x1 = l1$layout$panel_ranges[[1]]$x.range[1]
x2 = l1$layout$panel_ranges[[1]]$x.range[2]
y1 = l1$layout$panel_ranges[[1]]$y.range[1]
y2 = l1$layout$panel_ranges[[1]]$y.range[2]
xdif = x2-x1
ydif = y2-y1
xmin = x1 + (xleft*xdif)
xmax = x1 + (xright*xdif)
ymin = y1 + (ybottom*ydif)
ymax = y1 + (ytop*ydif)
# Get plot2 and make grob
g2 = ggplotGrob(plot2)
plot3 = plot1 + annotation_custom(grob = g2, xmin=xmin, xmax=xmax, ymin=ymin, ymax=ymax)
plot(plot3)
ggsave(filename = "test.png", plot = plot3)
# Try and make a weird combination of plots
g1 <- ggplotGrob(plot1)
g2 <- ggplotGrob(plot2)
g3 <- ggplotGrob(plot3)
library(gridExtra)
library(grid)
t1 = arrangeGrob(g1,ncol=1, left = textGrob("A", y = 1, vjust=1, gp=gpar(fontsize=20)))
t2 = arrangeGrob(g2,ncol=1, left = textGrob("B", y = 1, vjust=1, gp=gpar(fontsize=20)))
t3 = arrangeGrob(g3,ncol=1, left = textGrob("C", y = 1, vjust=1, gp=gpar(fontsize=20)))
final = arrangeGrob(t1,t2,t3, layout_matrix = cbind(c(1,2), c(3,3)))
grid.arrange(final)
ggsave(filename = "test2.png", plot = final)
![Изображение, показывающее вставку и относительно сложную компоновку]()
Ответ 3
Гораздо проще решение с использованием ggplot2
и egg
. Самое главное, это решение работает с ggsave
.
library(tidyverse)
library(egg)
plotx <- ggplot(mpg, aes(displ, hwy)) + geom_point()
plotx +
annotation_custom(
ggplotGrob(plotx),
xmin = 5, xmax = 7, ymin = 30, ymax = 44
)
ggsave(filename = "inset-plot.png")
Ответ 4
В качестве альтернативы можно использовать пакет cowplot
R от Claus O. Wilke (cowplot
- мощное расширение ggplot2
). У автора есть пример прорисовки вставки внутри большего графика в этой вводной виньетке. Вот некоторый адаптированный код:
library(cowplot)
main.plot <-
ggplot(data = mpg, aes(x = cty, y = hwy, colour = factor(cyl))) +
geom_point(size = 2.5)
inset.plot <- main.plot + theme(legend.position = "none")
plot.with.inset <-
ggdraw() +
draw_plot(main.plot) +
draw_plot(inset.plot, x = 0.07, y = .7, width = .3, height = .3)
# Can save the plot with ggsave()
ggsave(filename = "plot.with.inset.png",
plot = plot.with.inset,
width = 17,
height = 12,
units = "cm",
dpi = 300)
![enter image description here]()
Ответ 5
Этот post в блоге Learning R рассказывает о том, как построить сюжет. В блоге есть много других замечательных сообщений на ggplot2.
Ответ 6
'ggplot2'> = 3.0.0 делает возможными новые подходы для добавления вставок, поскольку теперь tibble
объекты, содержащие списки в виде столбцов-членов, можно передавать как данные. Объекты в столбце списка могут быть даже целыми ggplots... Последняя версия моего пакета 'ggpmisc' предоставляет geom_plot()
, geom_table()
и geom_grob()
, а также версии, которые используют npc-единицы вместо собственных блоков данных для определения местоположения. вставки. Эти geoms могут добавлять несколько вставок за вызов и подчиняться огранке, чего нет у annotation_custom()
. Я копирую пример со страницы справки, которая добавляет вставку с увеличенной детализацией основного графика как вставку.
library(tibble)
library(ggpmisc)
p <-
ggplot(data = mtcars, mapping = aes(wt, mpg)) +
geom_point()
df <- tibble(x = 0.01, y = 0.01,
plot = list(p +
coord_cartesian(xlim = c(3, 4),
ylim = c(13, 16)) +
labs(x = NULL, y = NULL) +
theme_bw(10)))
p +
expand_limits(x = 0, y = 0) +
geom_plot_npc(data = df, aes(npcx = x, npcy = y, label = plot))
![ggplot with ggplot as inset]()
Или барплот как вкладыш, взятый из виньетки пакета.
library(tibble)
library(ggpmisc)
p <- ggplot(mpg, aes(factor(cyl), hwy, fill = factor(cyl))) +
stat_summary(geom = "col", fun.y = mean, width = 2/3) +
labs(x = "Number of cylinders", y = NULL, title = "Means") +
scale_fill_discrete(guide = FALSE)
data.tb <- tibble(x = 7, y = 44,
plot = list(p +
theme_bw(8)))
ggplot(mpg, aes(displ, hwy, colour = factor(cyl))) +
geom_plot(data = data.tb, aes(x, y, label = plot)) +
geom_point() +
labs(x = "Engine displacement (l)", y = "Fuel use efficiency (MPG)",
colour = "Engine cylinders\n(number)") +
theme_bw()
![enter image description here]()