使用ComplexHeatmap绘制3D热图
共 2772字,需浏览 6分钟
· 2021-03-30
ComplexHeatmap包有一个densityHeatmap()
函数用来对一组分布进行可视化。例如下面的例子:
library(ComplexHeatmap)
set.seed(123)
mat = matrix(rnorm(500), ncol = 10)
colnames(mat) = letters[1:10]
densityHeatmap(mat)
![](https://filescdn.proginn.com/522663206fd88ea7e6e602877c8a7995/433f1dc0930e42e881e9e8c3a99656a1.webp)
在R图形系统中,我们也可以使用histogram来可视化分布,因此从ComplexHeatmap版本2.7.9开始,我新加了一个函数frequencyHeatmap()
,就像是一个histogram版本的density heatmap。其用法和densityHeatmap()
非常类似:
frequencyHeatmap(mat)
![](https://filescdn.proginn.com/e4f0815082280137cab5960fbb880092/2839b246a740a11acf1ff21f4ff2d86d.webp)
在这里,区间中的频度使用热图进行可视化。
那么现在,频度热图被称作是密度热图的histogram版本,但这看起来一点都不像histogram。那么可能一个3D的热图在这里更加适合。这可以通过在frequencyHeatmap()
中设置参数use_3d = TRUE
来将2D热图转换为3D热图:
frequencyHeatmap(mat, use_3d = TRUE)
![](https://filescdn.proginn.com/b2698a40a0178fe0f99d0c06d0126246/d9a7ea0bb0d01259e4ac2e2347024489.webp)
这看起来好多了!下面一节我将会介绍如何在ComplexHeatmap包中集成3D热图功能的。
3D热图的实现
首先,我们要能画3D的柱子,这可以通过新函数bar3D()
实现。用法如下:
bar3D(x = 0.5, y = 0.5, w = 0.2,
h = 0.2, l = unit(1, "cm"), theta = 60)
![](https://filescdn.proginn.com/799c48e00af154af57a23b44e2dcd75b/13881d2234e22a937d840d8ab2841acf.webp)
其中各个参数的意义不言而喻,见下图:
![](https://filescdn.proginn.com/14f35cbaab0cbff268b20182a9f37ef4/6d3ec0c6a09192b665aa8b1ef813275c.webp)
在bar3D()
中,fill
参数控制柱子的颜色。为了增强3D效果,柱子的三个面的颜色有略微轻微不同的明亮度。
bar3D(x = seq(0.2, 0.8, length = 4), y = 0.5,
w = unit(5, "mm"), h = unit(5, "mm"),
l = unit(1, "cm"), fill = c("red", "green", "blue", "purple"))
![](https://filescdn.proginn.com/c22efd1cebb4456357df8a878f925d37/bb33f5997d38caa8d4f73fc7768a6c34.webp)
参数theta
控制投影的角度,见下例:
bar3D(x = seq(0.2, 0.8, length = 4), y = 0.5,
w = unit(5, "mm"), h = unit(5, "mm"),
l = unit(1, "cm"), theta = c(20, 40, 60, 80))
![](https://filescdn.proginn.com/89e198f26721f3099924d8c320b0a7f5/ce7fac2da111eabb694a0323e5c663e9.webp)
好了,现在既然我们已经能够画3D的柱子了,为了实现3D的热图,我们可以通过cell_fun
或者layer_fun
提供的自定义函数来将每一个3D柱子放置在热图的格子上,其中柱子的高度和热图中相应的值对应。这里我写了一个新函数Heatmap3D()
可以直接拿来使用。其用法和Heatmap()
几乎完全相同。见下面的例子:
set.seed(7)
mat = matrix(runif(100), 10)
rownames(mat) = LETTERS[1:10]
colnames(mat) = letters[1:10]
Heatmap3D(mat, name = "mat", column_title = "This is a 3D heatmap")
![](https://filescdn.proginn.com/24d7cc0fc0b153c81353d458858deb05/c95fb74c9e553f0d703c267fa44b6e3c.webp)
当位于热图边缘的柱子太高时,可能会和热图中其他元件重叠,那么这时候需要进行手动的微调。在上面的例子中,标题和legend和3D柱子有重叠,这可以通过手动设置ht_opt$HEATMAP_LEGEND_PADDING
和ht_opt$TITLE_PADDING
来进行调整:
ht_opt$HEATMAP_LEGEND_PADDING = unit(5, "mm")
ht_opt$TITLE_PADDING = unit(c(9, 2), "mm") # bottom and top padding
Heatmap3D(mat, name = "mat", column_title = "This is a 3D heatmap")
![](https://filescdn.proginn.com/bca7cc452398f2ddb070871f47d10439/eac902df81a5cda004981d260369bf13.webp)
看,现在看起来好多了。
下面一个例子是对一个麻疹疫苗数据集的可视化,第一张图是2D热图,第二张图是3D热图。源代码可以通过点击“阅读全文”获得。
![](https://filescdn.proginn.com/bccf61db82b22c8ffd198b6e177852cd/9e9ceb4eb689f2974f7600a4111d665f.webp)
![](https://filescdn.proginn.com/6b717a00a2a61110a1fa9a2b80c05181/70a5023a39a9bd3b3d452152653fe120.webp)
最后,InteractiveComplexHeatmap包可以将任何通过ComplexHeatmap生成的热图转变为一个Shiny app,那么Heatmap3D()
生成的热图也同样可以。只需要在热图生成后运行htShiny()
即可:
往期精品(点击图片直达文字对应教程)
后台回复“生信宝典福利第一波”或点击阅读原文获取教程合集