2016-06-24 12 views
3

Ich kann drei Plots kombinieren, die keine Legenden haben, aber wenn ich Legenden zu zwei der Plots hinzufügen, kann ich sie nicht kombinieren. Wie kann ich einige Plots mit Legenden mit einem Plot ohne Legende kombinieren?Kombinieren Sie Plots mit einer Legende mit einer, die nicht

Hier ist ein Beispiel dafür, wie ich Parzellen ohne Legenden bin Kombination:

library(ggplot2) 
map_data <- data.frame(lon = c(-177.5, -172.5, -167.5, -162.5, -157.5, -152.5), 
         lat = c(87.5, 87.5, 87.5, 87.5, 87.5, 87.5), 
         ssta = c(-2.78999996, 0.09999999, 0.19999999, 0.06000000, 1.65999997, -0.41000000)) 

# one map 
p.1 <- ggplot() + 
    borders("world", 
      colour="black", 
      fill="white") + 
    geom_tile(data = map_data, 
      aes(lon, 
       lat)) + # no fill value so no legend 
    coord_fixed() + 
    scale_fill_viridis(na.value = "transparent") + 
    theme_minimal() 

# a second map, the same general shape 
p.2 <- p.1 

# a line plot 
library(lubridate) 
time_sequence <- seq(dmy("01-01-1800"), 
         dmy("01-01-1960"), 
         by = 'month') 
long_plot_data <- data.frame(variable = seq(dmy("01-01-1800"), 
              dmy("01-01-1960"), 
              by = 'month'), 
          value = runif(length(time_sequence)), 
          col = runif(length(time_sequence))) 

p.3 <- ggplot(long_plot_data, 
       aes(variable, 
        value)) + 
    geom_line() + 
    theme_minimal() 


# combine plots 
library(grid) 
grid.newpage() 
grid.draw(rbind(ggplotGrob(p.1), 
       ggplotGrob(p.2), 
       ggplotGrob(p.3), 
       size = "last")) 

enter image description here

Und jetzt, wenn ich einen Füllwerts auf die Karte Plots hinzufügen, erhalte ich eine Legende und ein Fehler wenn ich versuche, auf die gleiche Art und Weise zu kombinieren:

Hier ist, wie das aussieht:

enter image description here

# a second map, the same general shape 
p.2 <- p.1 

# a line plot 
library(lubridate) 
time_sequence <- seq(dmy("01-01-1800"), 
         dmy("01-01-1960"), 
         by = 'month') 
long_plot_data <- data.frame(variable = seq(dmy("01-01-1800"), 
              dmy("01-01-1960"), 
              by = 'month'), 
          value = runif(length(time_sequence)), 
          col = runif(length(time_sequence))) 

p.3 <- ggplot(long_plot_data, 
       aes(variable, 
        value)) + 
    geom_line() + 
    theme_minimal() 

Jetzt versuche ich die beiden Karten mit Legenden zu verbinden und die Liniendiagramm ohne eine Legende:

# combine plots 
library(grid) 
grid.newpage() 
grid.draw(rbind(ggplotGrob(p.1), 
       ggplotGrob(p.2), 
       ggplotGrob(p.3), 
       size = "last")) 

Der Ausgang Error: ncol(x) == ncol(y) is not TRUE

ist aber, wenn ich hinzufügen, eine Legende das Liniendiagramm, so dass alle drei Plots Legenden haben, kann ich sie kombinieren:

enter image description here

Wie kann ich zwei Diagramme mit Legenden mit einem ohne Legende kombinieren?

+0

Möglicherweise müssen Sie die Legende zu einem separaten grob bewegen und dann mit Gitter positioniere es auf der linken Seite mit zwei leeren Groschen darunter (super super hacky), ähnlich wie https://github.com/hadley/ggplot2/wiki/Share-a-legend-between-two-ggplot2-graphs – Andrew

+1

Habe a schau dir @baptistes Ei-Paket an, [hier verfügbar] (https: //github.c Om/Baptiste/Ei) auf gtihub. –

Antwort

6

Der Grund, warum Sie den Fehler bekommen werden, weil eine Ihrer 3 gtable Objekte 5 Spalten hat, während die anderen 6 hat (das p.3 Objekt hat 5, weil Sie die Legende ausschließen). Sie können die verschiedenen Layouts der gtable Objekte überprüfen, indem Sie:

library(gtable) 
gtable_show_layout(ggplotGrob(p.1)) 
gtable_show_layout(ggplotGrob(p.2)) 
gtable_show_layout(ggplotGrob(p.3)) 

Ich werde nicht die Bilder hier posten, weil sie aus der Antwort schmälern würde, aber ich denke, das ist der Mühe wert auf eigene Faust zu überprüfen.

Wie auch immer, was wir tun können, um dieses Problem zu beheben, wird einfach eine zusätzliche Spalte auf Ihr p.3 gtable hinzufügen und verwenden Sie dann die size="first" Option (weil wir die Legende sein, an der richtigen Stelle für die Stellplätze wollen, wo wir Legenden haben) .

Dies sollte funktionieren:

library(grid) 
library(gtable) 

grid.draw(rbind(ggplotGrob(p.1), 
       ggplotGrob(p.2), 
       gtable_add_cols(ggplotGrob(p.3),unit(1,"lines")), 
       size = "first")) 

enter image description here

Eine letzte Sache ist, die y-Achse Titel auf der letzten Handlung nur geringfügig mit den Etiketten überlappt, ist dies, weil wir die Dimensionierung von der ersten nahm Plot und die Beschriftungen sind im ersten Plot kleiner (daher benötigen die Y-Achsen-Labels weniger Platz). Um dies zu beheben könnten Sie leicht Ihre p.3 Code ändern zu:

p.3<- ggplot(long_plot_data, 
       aes(variable, 
        value)) + 
    geom_line() + 
    theme_minimal() %+replace% theme(axis.title.y=element_text(margin=margin(0,20,0,0),angle=90)) 

rerunning uns gibt:

grid.draw(rbind(ggplotGrob(p.1), 
       ggplotGrob(p.2), 
       gtable_add_cols(ggplotGrob(p.3),unit(1,"lines")), 
       size = "first")) 

enter image description here

+0

Fantastisch, danke. Ja, ich habe das über die unterschiedliche Anzahl der Spalten in den Tabellen gesehen, aber ich hatte keine Ahnung, was ich dagegen tun sollte. 'gtable_add_cols' ist neu für mich und perfekt für dieses Problem, nochmals vielen Dank. – Ben

2

Die Verwendung von plot_grid() aus Paket cowplot kann helfen - zumindest gelingt es, Plots mit und ohne Legenden zu kombinieren, aber es scheint schwierig, die Plots perfekt auszurichten. Ich poste trotzdem, da dies hilfreich sein kann und vielleicht jemand anderes weiß, wie man das Ausrichtungsproblem aussortiert

Hinweis, fügte coord_fixed() auch zum Liniendiagramm hinzu, um es gleiche Größe wie die Karten zu machen.

p.3 <- ggplot(long_plot_data, aes(variable, value)) + 
    geom_line() + 
    coord_fixed() + 
    theme_minimal() 

library(cowplot) 
plot_grid(p.1,p.2,p.3,ncol=1, align='h') 

enter image description here

Verwandte Themen