【问题标题】:Difficulty positioning heatmap.2 components难定位heatmap.2组件
【发布时间】:2019-04-24 05:57:18
【问题描述】:

我一直在努力定位 heatmap.2 输出的组件。

I found this old answer@IanSudbery 解释了元素定位的工作原理,这似乎很清楚,我认为它给了我所需的理解,但我仍然没有掌握一些东西。

我知道这些元素基本上都放在了一个格子窗中,但它们的行为方式与我理解的不同。

这是我的代码和当前输出(最底部是对图形元素进行排序的有趣部分):

for(i in 1:length(ConditionsAbbr)) {

# creates its own colour palette 
    my_palette <- colorRampPalette(c("snow", "yellow", "darkorange", "red"))(n = 399)

  # (optional) defines the colour breaks manually for a "skewed" colour transition
    col_breaks = c(seq(0,0.09,length=100),    #white 'snow'
                 seq(0.1,0.19,length=100), # for yellow
                 seq(0.2,0.29,length=100), # for orange 'darkorange'
                 seq(0.3,1,length=100))    # for red

  # creates a 5 x 5 inch image
  png(paste(SourceDir, "Heatmap_", ConditionsAbbr[i], "XYZ.png"),    # create PNG for the heat map        
      width = 5*600,        # 5 x 600 pixels
      height = 5*600,
      res = 300,            # 300 pixels per inch
      pointsize = 8)        # smaller font size

  heatmap.2(ConditionsMtx[[ConditionsAbbr[i]]],
            cellnote = ConditionsMtx[[ConditionsAbbr[i]]],  # same data set for cell labels
            main =  paste(ConditionsAbbr[i], "XYZ"), # heat map title
            notecol="black",      # change font color of cell labels to black
            density.info="none",  # turns off density plot inside color legend
            trace="none",         # turns off trace lines inside the heat map
            margins =c(12,9),     # widens margins around plot
            col=my_palette,       # use on color palette defined earlier
            breaks=col_breaks,    # enable color transition at specified limits
            dendrogram="none",     # No dendogram
            srtCol = 0 ,        #correct angle of label numbers
            asp = 1 ,         #this overrides layout methinks and for some reason makes it square
            adjCol = c(NA, -35) ,
            adjRow = c(53, NA) ,
            keysize =  1.2 ,
            Colv = FALSE ,      #turn off column clustering
            Rowv =  FALSE ,    # turn off row clustering
            key.xlab = paste("Correlation") ,
            lmat = rbind( c(0, 3), c(2,1), c(0,4) ), 
            lhei = c(0.9, 4, 0.5) )

  dev.off()               # close the PNG device


}

这给出:

如您所见,key在矩阵的右边,矩阵、上面的标题和下面的key之间有大量的空白,而且标题和矩阵不是在PNG中居中吗?

我对自己说“好吧,我将创建一个易于理解和编辑的 3x3”,例如

        |        |
        |        |  (3)
        |        |      
--------------------------
        |  (1)   |
   (2)  | Matrix |  
        |        | 
--------------------------   
        |  (4)   |
        |  Key   |
        |        | 

然后我可以去掉空白,让它更像这样。

        |        |(3)      
    ------------------
        |  (1)   |
     (2)| Matrix |  
        |        | 
    ------------------   
        |(4) Key |

我这样做是:

lmat = rbind( c(0, 0, 3), c(2, 1, 0), c(0, 4, 0) ), 
            lhei = c(0.9, 4, 0.5) ,
            lwid = c(1, 4, 1))

这就是它的样子:

尽管我的矩阵位于中心,但我的钥匙仍然对齐矩阵的右侧,并且我的标题是沿着丝绸之路东行?更不用说所有多余的空白了?

如何让它们对齐并一起移动,以使图形组件紧密贴合在一起?

编辑:减少我的边距有助于减少空白,但仍然过多。

【问题讨论】:

    标签: r position alignment element heatmap


    【解决方案1】:

    这是我为获得结果所做的最终更改,但是,如果您对 heatmap.2 不太投入,我建议您使用 Maurits Evers 的建议。不要忽视我对图像尺寸所做的更改。

    # creates my own colour palette
        my_palette <- colorRampPalette(c("snow", "yellow", "darkorange", "red"))(n = 399)
    
      # (optional) defines the colour breaks manually for a "skewed" colour transition
        col_breaks = c(seq(0,0.09,length=100),    #white 'snow'
                     seq(0.1,0.19,length=100), # for yellow
                     seq(0.2,0.29,length=100), # for orange 'darkorange'
                     seq(0.3,1,length=100))    # for red
    
      # creates an image
      png(paste(SourceDir, "Heatmap_XYZ.png" )
    
      # create PNG for the heat map        
          width = 5*580,        # 5 x 580 pixels
          height = 5*420,       # 5 x 420 pixels
          res = 300,            # 300 pixels per inch
          pointsize =11)        # smaller font size
    
      heatmap.2(ConditionsMtx[[ConditionsAbbr[i]]],
                cellnote = ConditionsMtx[[ConditionsAbbr[i]]],  # same data set for cell labels
                main =  "XYZ", # heat map title
                notecol="black",      # change font color of cell labels to black
                density.info="none",  # turns off density plot inside color legend
                trace="none",         # turns off trace lines inside the heat map
                margins=c(0,0),     # widens margins around plot
                col=my_palette,       # use on color palette defined earlier
                breaks=col_breaks,    # enable color transition at specified limits
                dendrogram="none",     # only draw a row dendrogram
                srtCol = 0 ,        #correct angle of label numbers
                asp = 1 ,         #this overrides layout methinks and for some reason makes it square
                adjCol = c(NA, -38.3) , #shift column labels
                adjRow = c(77.5, NA) , #shift row labels
                keysize =  2 ,  #alter key size
                Colv = FALSE ,      #turn off column clustering
                Rowv =  FALSE ,    # turn off row clustering
                key.xlab = paste("Correlation") , #add label to key 
                cexRow = (1.8) , # alter row label font size
                cexCol = (1.8) , # alter column label font size
                notecex = (1.5) , # Alter cell font size
                lmat = rbind( c(0, 3, 0), c(2, 1, 0), c(0, 4, 0) ) , 
                lhei = c(0.43, 2.6, 0.6) , # Alter dimensions of display array cell heighs
                lwid = c(0.6, 4, 0.6) , # Alter dimensions of display array cell widths
                key.par=list(mar=c(4.5,0, 1.8,0) ) ) #tweak specific key paramters
    
      dev.off()
    

    这是输出,我将继续改进,直到所有间距和字体大小都符合我的审美偏好。我会确切地告诉你我做了什么,但我不是 100% 肯定,坦率地说,这一切感觉就像是用旧的口香糖和水桶绳固定在一起,但不要像他们所说的那样在代码中踢礼物马。

    【讨论】:

      【解决方案2】:

      我不知道您是否愿意接受非基于heatmap.2 的解决方案。在我看来,ggplot 提供了更大的灵活性,并且通过一些调整,您可以轻松地重现与您正在展示的热图相似的热图,同时最大限度地绘制“房地产”并避免过多的空白。

      如果您只是在寻找 heatmap.2 解决方案,我很乐意删除此帖子。

      除此之外,ggplot2 解决方案可能如下所示:

      首先,让我们生成一些示例数据

      set.seed(2018)
      df <- as_tibble(matrix(runif(7*10), ncol = 10), .name_repair = ~seq(1:10))
      

      在绘图之前,我们需要将df 从宽改成长

      library(tidyverse)
      df <- df %>%
          rowid_to_column("row") %>% 
          gather(col, Correlation, -row) %>%
          mutate(col = as.integer(col))
      

      然后绘制

       ggplot(df, aes(row, col, fill = Correlation)) +
          geom_tile() +
          scale_fill_gradientn(colours = my_palette) +     # Use your custom colour palette
          theme_void() +                                   # Minimal theme
          labs(title = "Main title") +
          geom_text(aes(label = sprintf("%2.1f", Correlation)), size = 2) +
          theme(
              plot.title = element_text(hjust = 1),        # Right-aligned text
              legend.position="bottom") +                  # Legend at the bottom
          guides(fill = guide_colourbar(
              title.position = "bottom",                   # Legend title below bar
              barwidth = 25,                               # Extend bar length
              title.hjust = 0.5))
      


      通过facet_wrap 在网格布局中具有多个热图的示例

      首先,让我们生成更复杂的数据。

      set.seed(2018)
      df <- replicate(
          4,
          as_tibble(matrix(runif(7*10), ncol = 10), .name_repair = ~seq(1:10)), simplify = F) %>%
          setNames(., paste("data", 1:4, sep = "")) %>%
          map(~ .x %>% rowid_to_column("row") %>%
              gather(col, Correlation, -row) %>%
              mutate(col = as.integer(col))) %>%
          bind_rows(.id = "data")
      

      然后绘图与我们之前所做的相同,加上一个额外的facet_wrap(~data, ncol = 2) 语句

      ggplot(df, aes(row, col, fill = Correlation)) +
          geom_tile() +
          scale_fill_gradientn(colours = my_palette) +     # Use your custom colour palette
          theme_void() +                                   # Minimal theme
          labs(title = "Main title") +
          geom_text(aes(label = sprintf("%2.1f", Correlation)), size = 2) +
          facet_wrap(~ data, ncol = 2) + 
          theme(
              plot.title = element_text(hjust = 1),        # Right-aligned text
              legend.position="bottom") +                  # Legend at the bottom
          guides(fill = guide_colourbar(
              title.position = "bottom",                   # Legend title below bar
              barwidth = 25,                               # Extend bar length
              title.hjust = 0.5))
      


      最后一次更新

      我认为看看我们可以在与您 link to from the paper 类似的复杂热图上走多远会很有趣/有趣。

      示例数据包含在末尾,因为这会占用一些空间。

      我们首先构建三个不同的 ggplot2 绘图对象,它们显示主热图 (gg3)、一个带有缺失值的附加较小热图 (gg2),以及一个表示每行组标签的条形 (gg1 )。

      gg3 <- ggplot(df.cor, aes(col, row, fill = Correlation)) +
          geom_tile() +
          scale_fill_distiller(palette = "RdYlBu") +
          theme_void() +
          labs(title = "Main title") +
          geom_text(aes(label = sprintf("%2.1f", Correlation)), size = 2) +
          scale_y_discrete(position = "right") +
          theme(
              plot.title = element_text(hjust = 1),
              legend.position="bottom",
              axis.text.y = element_text(color = "black", size = 10)) +
          guides(fill = guide_colourbar(
              title.position = "bottom",
              barwidth = 10,
              title.hjust = 0.5))
      
      gg2 <- ggplot(df.flag, aes(col, row, fill = Correlation)) +
          geom_tile(colour = "grey") +
          scale_fill_distiller(palette = "RdYlBu", guide = F, na.value = "white") +
          theme_void() +
          scale_x_discrete(position = "top") +
          theme(
              axis.text.x = element_text(color = "black", size = 10, angle = 90, hjust = 1, vjust = 0.5))
      
      
      gg1 <- ggplot(df.bar, aes(1, row, fill = grp)) +
          geom_tile() +
          scale_fill_manual(values = c("grp1" = "orange", "grp2" = "green")) +
          theme_void() +
          theme(legend.position = "left")
      

      我们现在可以使用egg::ggarrange 来定位所有三个图,以使 y 轴范围对齐。

      library(egg)
      ggarrange(gg1, gg2, gg3, ncol = 3, widths = c(0.1, 1, 3))
      


      样本数据

      library(tidyverse)
      set.seed(2018)
      nrow <- 7
      ncol <- 20
      df.cor <- matrix(runif(nrow * ncol, min = -1, max = 1), nrow = nrow) %>%
          as_tibble(.name_repair = ~seq(1:ncol)) %>%
          rowid_to_column("row") %>%
          gather(col, Correlation, -row) %>%
          mutate(
              row = factor(
                  paste("row", row, sep = ""),
                  levels = paste("row", 1:nrow, sep = "")),
              col = factor(
                  paste("col", col, sep = ""),
                  levels = paste("col", 1:ncol, sep = "")))
      
      nrow <- 7
      ncol <- 10
      df.flag <- matrix(runif(nrow * ncol, min = -1, max = 1), nrow = nrow) %>%
          as_tibble(.name_repair = ~seq(1:ncol)) %>%
          rowid_to_column("row") %>%
          gather(col, Correlation, -row) %>%
          mutate(
              row = factor(
                  paste("row", row, sep = ""),
                  levels = paste("row", 1:nrow, sep = "")),
              col = factor(
                  paste("col", col, sep = ""),
                  levels = paste("col", 1:ncol, sep = ""))) %>%
          mutate(Correlation = ifelse(abs(Correlation) < 0.5, NA, Correlation))
      
      
      df.bar <- data.frame(
          row = 1:nrow,
          grp = paste("grp", c(rep(1, nrow - 3), rep(2, 3)), sep = "")) %>%
          mutate(
              row = factor(
                  paste("row", row, sep = ""),
                  levels = paste("row", 1:nrow, sep = "")))
      

      【讨论】:

      • 我认为这是一个非常有用的答案,但我无法找到一个指南,向我展示如何绘制多个彼此相邻的热图,并使用颜色编码的 X 和 Y 条显示各种条件。
      • 如果我理解正确,应该有不同的方法来实现这一点。您可以使用构面让ggplot2 自动绘制和布局多个热图。或者您可以使用gridExtra::grid.arrange 在矩阵布局中手动布局任意数量的ggplot2 绘图对象。您能否详细说明“用颜色编码的 X 和 Y 条显示各种条件”是什么意思? X和Y是什么?什么条件?
      • @SolebaySharp 我添加了一个示例图,展示了如何使用构面绘制多个热图。请看一看。
      • @SolebaySharp 您指的是论文中的哪个数字?
      • 我的意思是这里的 Y 轴条线:media.springernature.com/lw785/springer-static/image/… 但是我想我会接受你对未来情节的建议。 --> 是的,对不起,我第一次搞砸并复制了整篇论文而不是指向特定图像的链接。
      猜你喜欢
      • 2014-06-20
      • 1970-01-01
      • 1970-01-01
      • 2013-12-28
      • 1970-01-01
      • 2017-05-27
      • 1970-01-01
      • 2022-11-07
      • 2013-05-09
      相关资源
      最近更新 更多