Soru Ggplot2 tarafından oluşturulan arsa altında metin görüntüleme


Oluşturulan çizimin altındaki verilerle ilgili bazı bilgileri görüntülemeye çalışıyorum ggplot2. N değişkenini çizimin X ekseni koordinatını kullanarak çizmek istiyorum ancak Y koordinatının ekranın altından% 10 olması gerekiyor. Aslında, istenen Y koordinatları zaten veri çerçevesinde y_pos değişkenidir.

Kullanarak 3 yaklaşım düşünebilirim ggplot2:

1) gerçek arsa altında boş bir arsa oluşturun, aynı ölçeği kullanın ve sonra boş arsa üzerinde verileri çizmek için geom_text kullanın. Bu yaklaşım işler bir tür ama son derece karmaşıktır.

2) Kullanım geom_text Verileri çizmek için, ancak bir şekilde y koordinatını ekranın yüzdesi olarak kullanın (% 10). Bu sayıların arsanın altında görüntülenmesini zorlar. Doğru sözdizimini anlayamıyorum.

3) Metni görüntülemek için grid.text kullanın. Ekranın altından% 10 oranında kolayca ayarlayabilirim fakat X koordinatının arsa ile eşleşmesini nasıl ayarlayacağımı anlayamıyorum. İlk X pozisyonunu yakalamak için grconvert kullanmayı denedim ama işe yaramadı.

Aşağıda, kukla verilerle temel çizim yer almaktadır:

graphics.off()      # close graphics windows   

library(car)
library(ggplot2)  #load ggplot
library(gridExtra) #load Grid
library(RGraphics) # support of the "R graphics" book, on CRAN

#create dummy data
test= data.frame(
  Group = c("A", "B", "A","B", "A", "B"), 
  x = c(1 ,1,2,2,3,3 ),
  y = c(33,25,27,36,43,25),
  n=c(71,55,65,58,65,58),
  y_pos=c(9,6,9,6,9,6)
  )

#create ggplot
p1 <- qplot(x, y, data=test, colour=Group) +
  ylab("Mean change from baseline") + 
  geom_line()+
  scale_x_continuous("Weeks", breaks=seq(-1,3, by = 1) ) +
  opts( 
        legend.position=c(.1,0.9))

#display plot
p1

Aşağıdaki değiştirilmiş gplot, konuların sayısını gösterir, ancak arsa ININDE görüntülenir. Y ölçeğini genişletmek için zorlarlar. Bu sayıları arsada göstermek istiyorum.

    p1 <- qplot(x, y, data=test, colour=Group) +
  ylab("Mean change from baseline") + 
  geom_line()+
  scale_x_continuous("Weeks", breaks=seq(-1,3, by = 1) ) +
  opts( plot.margin = unit(c(0,2,2,1), "lines"),
        legend.position=c(.1,0.9))+
  geom_text(data = test,aes(x=x,y=y_pos,label=n))

p1

Sayıları görüntülemenin farklı bir yaklaşımı, gerçek arsa altında kukla bir çizim oluşturmayı içerir. İşte kod:

graphics.off()      # close graphics windows   

library(car)
library(ggplot2)  #load ggplot
library(gridExtra) #load Grid
library(RGraphics) # support of the "R graphics" book, on CRAN

#create dummy data
test= data.frame(
  group = c("A", "B", "A","B", "A", "B"), 
  x = c(1 ,1,2,2,3,3 ),
  y = c(33,25,27,36,43,25),
  n=c(71,55,65,58,65,58),
  y_pos=c(15,6,15,6,15,6)
  )


p1 <- qplot(x, y, data=test, colour=group) +
  ylab("Mean change from baseline") + 
  opts(plot.margin = unit(c(1,2,-1,1), "lines")) +
  geom_line()+
  scale_x_continuous("Weeks", breaks=seq(-1,3, by = 1) ) +
  opts(legend.position="bottom",
       legend.title=theme_blank(),
       title.text="Line plot using GGPLOT") 
p1

p2 <- qplot(x, y, data=test, geom="blank")+
  ylab(" ")+
  opts(     plot.margin = unit(c(0,2,-2,1), "lines"),
            axis.line = theme_blank(), 
            axis.ticks = theme_segment(colour = "white"),           
            axis.text.x=theme_text(angle=-90,colour="white"),
            axis.text.y=theme_text(angle=-90,colour="white"),
            panel.background = theme_rect(fill = "transparent",colour = NA), 
            panel.grid.minor = theme_blank(),      
            panel.grid.major = theme_blank()
            )+
  geom_text(data = test,aes(x=x,y=y_pos,label=n)) 
p2

grid.arrange(p1, p2, heights = c(8.5, 1.5),             nrow=2 )

Ancak, bu çok karmaşık ve farklı veriler için değiştirmek zor olurdu. İdeal olarak, Y koordinatlarını ekranın yüzdesi olarak geçirebilmek istiyorum.


32
2018-04-04 15:21


Menşei


annotation_custom () ve kod buradan size yardımcı olabilir. Aşağıya bakınız. - Sandy Muspratt
Cevabımı aşağıya bakın. Kabul edilen cevaptan kesinlikle daha basittir. - Taylor C. White
Ggplot2'nin yeni sürümleri şu anda aşağıdaki yanıtlara göre oluşturulmuştur: stackoverflow.com/a/36036479/170352 - Brandon Bertelsen


Cevaplar:


Düzenlenen  opts kullanımdan kaldırıldı, yerine theme; element_blank Değiştirildi theme_blank; ve ggtitle() yerine kullanılır opts(title = ...

Sandy- çok teşekkür ederim !! Bu tam olarak istediğimi yapar. Kırpayı geom.text veya geom.annotate içinde kontrol edebilmeyi diliyorum.

Başka biri ilgilenirse aşağıdaki programı bir araya getirdim.

 rm(list = ls())     # clear objects  
 graphics.off()      # close graphics windows   

library(ggplot2)
library(gridExtra)

#create dummy data
test= data.frame(
  group = c("Group 1", "Group 1", "Group 1","Group 2", "Group 2", "Group 2"), 
  x = c(1 ,2,3,1,2,3 ),
  y = c(33,25,27,36,23,25),
  n=c(71,55,65,58,65,58),
  ypos=c(18,18,18,17,17,17)

  )


p1 <- qplot(x=x, y=y, data=test, colour=group) +
  ylab("Mean change from baseline") + 
  theme(plot.margin = unit(c(1,3,8,1), "lines")) +
  geom_line()+
  scale_x_continuous("Visits", breaks=seq(-1,3) ) +
  theme(legend.position="bottom",
       legend.title=element_blank())+
   ggtitle("Line plot") 


# Create the textGrobs 
for (ii in 1:nrow(test))
{
  #display numbers at each visit
  p1=p1+ annotation_custom(grob = textGrob(test$n[ii]),  
                           xmin = test$x[ii], 
                           xmax = test$x[ii], 
                           ymin = test$ypos[ii], 
                           ymax = test$ypos[ii])

    #display group text
    if (ii %in% c(1,4)) #there is probably a better way 
      {
    p1=p1+ annotation_custom(grob = textGrob(test$group[ii]),  
                             xmin = 0.85, 
                             xmax = 0.85, 
                             ymin = test$ypos[ii], 
                             ymax = test$ypos[ii])
    }

  }




  # Code to override clipping
  gt <- ggplot_gtable(ggplot_build(p1))
  gt$layout$clip[gt$layout$name=="panel"] <- "off"
  grid.draw(gt)

enter image description here


20
2018-05-03 02:59



Çok hoş!! Kendi cevabını kabul etmeyi unutma. - Sandy Muspratt
Tam burada görünmüyor, kod hala sizin için çalışıyor mu? - PatrickT


Mevcut sürüm (> 2.1) bir + labs(caption = "text")Bu, çizimin altında bir ek açıklama görüntüler. Bu, (font özellikleri, ... sol / sağ hizalı) Görmek https://github.com/hadley/ggplot2/pull/1582 Örneğin.


16
2018-03-16 13:01





Güncellenmiş  opts() ile değiştirildi theme()

Aşağıdaki kodda, arsanın altında daha geniş bir marj ile bir taban arsası çizilir. TextGrob oluşturulur, ardından annotation_custom () kullanılarak arsaya eklenir. Metin, arsa panelinin dışında olduğu için görünür değil - çıktı panele kırpılır. Ama baptiste kodunu kullanarak buradankırpma kırpma aşırı olabilir. Konum veri birimleri cinsinden ve her iki metin etiketi ortalanır.

library(ggplot2)
library(grid)

# Base plot
df = data.frame(x=seq(1:10), y = seq(1:10))
p = ggplot(data = df, aes(x = x, y = y)) + geom_point() + ylim(0,10) +
    theme(plot.margin = unit(c(1,1,3,1), "cm"))
p

# Create the textGrobs
Text1 = textGrob(paste("Largest x-value is", round(max(df$x), 2), sep = " "))
Text2 = textGrob(paste("Mean = ", mean(df$x), sep = ""))

p1 = p + annotation_custom(grob = Text1,  xmin = 4, xmax = 4, ymin = -3, ymax = -3) +
        annotation_custom(grob = Text2,  xmin = 8, xmax = 8, ymin = -3, ymax = -3)
p1

# Code to override clipping
gt <- ggplotGrob(p1)
gt$layout$clip[gt$layout$name=="panel"] <- "off"
grid.draw(gt)

enter image description here

Ya da grid etiketi oluşturmak ve konumlandırmak için fonksiyonlar.

p
grid.text((paste("Largest x-value is", max(df$x), sep = " ")),
   x = unit(.2, "npc"), y = unit(.1, "npc"), just = c("left", "bottom"), 
   gp = gpar(fontface = "bold", fontsize = 18, col = "blue"))

enter image description here

Düzenle Veya, gtable işlevlerini kullanarak metin grob ekleyin.

library(ggplot2)
library(grid)
library(gtable)

# Base plot
df = data.frame(x=seq(1:10), y = seq(1:10))
p = ggplot(data = df, aes(x = x, y = y)) + geom_point() + ylim(0,10) 

# Construct the text grob
lab = textGrob((paste("Largest x-value is", max(df$x), sep = " ")),
   x = unit(.1, "npc"), just = c("left"), 
   gp = gpar(fontface = "bold", fontsize = 18, col = "blue"))


gp = ggplotGrob(p)

# Add a row below the 2nd from the bottom
gp = gtable_add_rows(gp, unit(2, "grobheight", lab), -2)

# Add 'lab' grob to that row, under the plot panel
gp = gtable_add_grob(gp, lab, t = -2, l = gp$layout[gp$layout$name == "panel",]$l)

grid.newpage()
grid.draw(gp)

enter image description here


15
2018-04-27 07:46



Çok teşekkür ederim!!! Grid işlevlerinin, aygıta herhangi bir yere metin yerleştirmesine izin verdiğini anlıyorum. Ben sadece, bu arsa AŞAĞIDA metin yerleştirmek mümkün olsa merak ediyorum, ama bir şekilde X koordinatları arsa kullanın. R temelindeki metin işleviyle yapabileceklerinize benzer bir şey. - Max C
Teşekkürler! Hata alıyorum: "ggplot_gtable"> gt $ layout $ clip [gt $ layout $ name == "panel"] <- "kapalı" işlev bulamadı - Max C
İçinde bir işlev ggplot2. Hangi ggplot2 sürümünü kullanıyorsunuz? Yeni sürüme geçmeniz gerekebilir. En son sürüm 0.9.0 - Sandy Muspratt
Sandy: R stüdyo bir şekilde GGPLOT'un eski versiyonunu kurmaya devam ediyor. Bunun için üzgünüm. - Max C
Bendede aynı sorun var. CRAN'dan değilse güncellenmiş sürümü nasıl alabilirim? - Atticus29


Aslında en iyi cevap ve en kolay çözüm cowplot paketini kullanmaktır.

Cowplot paketinin (CRAN'da) 0.5.0 sürümü, add_sub fonksiyonunu kullanarak ggplot2 altyazısını idare eder.

Bunu şöyle kullanın:

  diamondsCubed <-ggplot(aes(carat, price), data = diamonds) + 
  geom_point() + 
  scale_x_continuous(trans = cuberoot_trans(), limits = c(0.2, 3),
                     breaks = c(0.2, 0.5, 1, 2, 3)) + 
  scale_y_continuous(trans = log10_trans(), limits = c(350, 15000),
                     breaks = c(350, 1000, 5000, 10000, 15000)) +
  ggtitle('Price log10 by Cube-Root of Carat') +
  theme_xkcd()


  ggdraw(add_sub(diamondsCubed, "This is an annotation.\nAnnotations can span multiple lines."))

5
2018-01-04 02:10