交互式复杂的热图是如何实现的

Zuguang Gu (z.gu@dkfz.de)

2021-05-19

热图是主要用于可视化组织共同模式的行和列。观察到的模式之后,下一步是提取相应的团体的行和列的热图,需要互动的热图。的ComplexHeatmap包是众所周知的生成静态的热图(一个热图或热图的列表,可能与复杂的注释)。这里的包InteractiveComplexHeatmap让互动ComplexHeatmap。新功能允许用户通过点击/捕获sub-heatmaps盘旋的热图单个细胞或选择区域。

不像其他包支持交互式基于JavaScript的热图,如。,iheatmapr,的热图d3heatmap,包InteractiveComplexHeatmap有一种特殊的方式来捕获用户选定的位置,从矩阵中提取相应的值。在这个描述中,我将详细解释如何互动的基础上实现ComplexHeatmap

为了演示,我首先生成一个两个的热图和应用列表k在数字的热图——集群。

图书馆(ComplexHeatmap)图书馆(InteractiveComplexHeatmap)set.seed(123年)mat1 =矩阵(rnorm(One hundred.),10)rownames(mat1) =colnames(mat1) =paste0(“一个”,1:10)mat2 =矩阵(样本(信1:10),One hundred.,取代=真正的),10)rownames(mat2) =colnames(mat2) =paste0(“b”,1:10)ht_list =的热图(mat1name =“mat_a”,row_km =2,column_km =2)+的热图(mat2name =“mat_b”)

InteractiveComplexHeatmap实现了两种类型的交互:

  1. 在交互式图形设备上,
  2. 一个闪亮的应用。

交互式图形设备上的交互性是闪亮的交互性的应用程序的基础,所以在下面几节中,我将首先介绍如何implemneted交互性与交互式图形设备。

在交互式图形设备上

这里的“交互式图形设备”窗口,打开生成的情节在你的会话如果使用R在本地终端或R GUI,或图面板Rstudio IDE。

我将首先解释InteractiveComplexHeatmap捕获用户点击设备的位置和它如何与矩阵中的值相关联。

当用户点击设备,设备的物理位置相对的左下角(补偿设备在x和y方向)捕捉到网格:grid.locator ()。的物理位置的热图(更准确地说,热图片)也可以捕捉到网格:deviceLoc ()。知道点击点的确切位置和热图,可以告诉热图的点击点。此外,通过计算点击点的相对距离的热图,也可以知道哪个行和列点击点对应。

将用户的点击点的热图,我们首先需要计算所有的热图的位置。有一个helper函数htPositionsOnDevice ()做这个工作。

在执行之前htPositionsOnDevice (),热图应该画在设备和热图的布局应该是生成的,这样htPositionsOnDevice ()可以访问各种视窗的情节。因此,热图对象ht_list应该明确的更新画()函数。

下面的代码将设备的热图6英寸宽4英寸高。

ht_list =(ht_list)pos =htPositionsOnDevice(ht_list)

返回的对象pos是一个DataFrame对象包含所有的热图片的位置。一个DataFrame对象(DataFrame类中定义的S4Vectors)是bacially非常类似于一个数据帧,但它可以存储更复杂的数据类型,如simpleUnit向量(由网格::单元())。

pos
# # DataFrame用6 # # 8行和列的热图片row_slice column_slice # # <人物> <人物> <整数> <整数> # # 1 mat_a mat_a_heatmap_body_1_1 1 1 # # 2 mat_a mat_a_heatmap_body_1_2 1 2 # # 3 mat_a mat_a_heatmap_body_2_1 2 1 # # 4 mat_a mat_a_heatmap_body_2_2 2 2 # # 5 mat_b mat_b_heatmap_body_1_1 1 1 # # 6 mat_b mat_b_heatmap_body_2_1 2 1 # # x_min x_max y_min # # < simpleUnit > < simpleUnit > < simpleUnit > # 0.742676161627057 # 1 . n:行情). .# # 2 1.78748414410527英寸1.02923575725979英寸1.82685422284543英寸2.87166220532365英寸1.02923575725979英寸0.742676161627057 # # 3 . n:行情). .1.78748414410527英寸0.43284365824135英寸# # 4 1.82685422284543英寸2.87166220532365英寸0.43284365824135英寸# # 5 # # 2.95040236280396英寸5.07938840650056英寸1.02923575725979英寸2.95040236280396英寸5.07938840650056英寸0.43284365824135英寸6 # # y_max # # < simpleUnit > # # 1 # # 3 # # 2 3.25732383837294英寸3.25732383837294英寸0.989865678519637 . n:行情). .0.989865678519637 # # 4 . n:行情). .0.989865678519637 # # 5 # # 3.25732383837294英寸6 . n:行情). .

我们可以确认位置是否正确被下面的代码。在接下来的图,黑色矩形对应的热图片和虚线矩形对应于整个图像的边界。

dev.new(宽度=6,身高=4)grid.newpage()grid.rect(gp =gpar(lty =2))(我seq_len(nrow(pos))) {x_min =pos(我“x_min”]x_max =pos(我“x_max”]y_min =pos(我“y_min”]y_max =pos(我“y_max”]pushViewport(视窗(x =x_min,y =y_min,name =pos(我“切”),宽度=x_max- - - - - -x_min,身高=y_max- - - - - -y_min,就=c(“左”,“底”)))grid.rect()upViewport()}

是的,所有的热图片的位置是正确的了!

因为现在我们知道(通过点击的位置点网格:grid.locator ())和所有的热图片的位置,可以计算原始矩阵行和列的用户点击对应。

在接下来的图,蓝色的点坐标\ \ ((a, b))由用户点击。用户点击进入范围的热图片\ ((x_1、x_2) \)在x方向和范围\ ((y_1 y_2) \)在y方向上这热图片可以很容易地发现通过比较每一个热图片的位置的位置单击。有\ (n_r \)行(\ (n_r = 8 \)),\ (n_c \)列(\ (n_c = 5 \))在这个热图切片的虚线。注意所有的坐标值(即。,\ \ (),\ (b \),\ (x_1 \),\ (y_1 \),\ (x_2 \)\ (y_2 \))测量图形设备的物理位置。

在这个热图切片,行索引\ (i_r \)和列索引\ (i_c \)细胞的关键是在可以计算(假设左边底部对应的索引1对行和列):

\ [i_c = \ lceil \压裂{a - x_1} {x_2 - x_1} \ cdot n_c \ rceil \]\ [i_r = \ lceil \压裂{b - y_1} {y_2 - y_1} \ cdot n_r \ rceil \]

的象征\ (\ lceil x \ rceil \)意味着数值的上限\ \ (x)。在ComplexHeatmap1,行用指数总是放在顶部的热图,\ (i_r \)应调整为:

\ [i_r = n_r - \ lceil \压裂{b - y_1} {y_2 - y_1} \ cdot n_r \ rceil + 1 \]

行和列的子集的原始矩阵指数属于所选的热图片已经存储在ht_list(他们可以检索对象row_order ()column_order ()功能),因此,我们可以获得原始矩阵的行和列索引对应于用户的观点很容易\ (i_r \)\ (i_c \)

表示完整的矩阵的热图(没有切片)\ \(米),表示行和列的子集的热图作为指标阿\ (^ {\ mathrm{行}}\)阿\ (^ {\ mathrm{坳}}\)。请注意,阿\ (^ {\ mathrm{行}}\)阿\ (^ {\ mathrm{坳}}\)由于聚类可以被重新排序。然后行和列指数(\ (j_r \)\ (j_c \)),所选的点\ \(米)

\ [j_r = o ^ {\ mathrm{行}}_ {i_r} \]\ [j_c = o ^ {\ mathrm{坳}}_ {i_c} \]

和相应的价值\ \(米)\ (M_ {j_r, j_c} \)

InteractiveComplexHeatmap有两个功能selectPosition ()selectArea ()这允许用户选择单一的位置或从热图选择区域。在交互式图形设备,用户不需要运行htPositionsOnDevice ()明确。热图的位置会自动计算,缓存和重用如果热图是相同的和设备没有改变它的大小。如果用户改变了设备的大小,htPositionsOnDevice ()将自动重新执行。

接下来的图片显示了一个示例selectPosition ()

交互,功能要求用户点击热图上的一个位置。函数返回一个DataFrame它包含的热图名称、片名称和矩阵的行/列索引的热图。

与1 # # DataFrame行6列# #的热图片row_slice column_slice row_index # # <人物> <人物> <数字> <数字> <整数> # # 1 mat_a mat_a_heatmap_body_1_2 1 2 9 # # column_index # # 1 # # <整数> 1

输出方式,用户点击的位置是在一个名为“mat_a”的热图,片在第一行和第二列片。假设是矩阵送到热图“mat_a”,然后点击点对应的值垫(9,1)

如果没有在任何位置点击热图的片,函数返回

类似地,selectArea ()功能要求用户点击热图上两个位置定义一个区域。

注意自选择区域可能在多个重叠的热图和切割,函数返回一个DataFrame与多行包含的热图的名字,片名字和热图的行/列指数。输出如下一个例子。

# # DataFrame 4行6列# #的热图片row_slice column_slice row_index # # <人物> <人物> <数字> <数字> < IntegerList > # # 1 mat_a mat_a_heatmap_body_1_2 1 2 7, 5, 2,…# # 2 mat_a mat_a_heatmap_body_2_2 2 2 6 3 # # 3 mat_b mat_b_heatmap_body_1_1 1 1 7, 5, 2,…# # 4 mat_b mat_b_heatmap_body_2_1 2 1 6、3 # # column_index # # 1 # # < IntegerList > 2, 4, 1,…# # 2 2 4 1,……3 # # 1、2、3、……4 # # 1、2、3、……

row_indexcolumn_index存储在IntegerList格式。行指数如。mat_a_heatmap_body_1_2(第一行),用户可以使用以下命令(假设之一DataFrame对象被称为df):

df (1,“row_index”][[1]]unlist(df [1,“row_index”])df美元row_index [[1]]

矩形的点标志着区域可以通过设置关闭马克参数

在离屏图形设备上

也可以使用selectPosition ()selectArea ()在其他屏幕图形设备等pdf ()png ()。现在你不能选择位置交互,而是你可以指定pos论点selectPosition ()pos1/pos2selectArea ()模拟点击。的值pos,pos1pos2都应该是一个单位对象的长度两个对应的x和y坐标位置。

pdf(…)ht_list =(ht_list)pos =selectPosition(ht_listpos =单位(c(3,3),“厘米”))dev.off()

# #点:x = 3.0厘米,y = 3.0厘米(以图形设备)# # # #的热图已经改变了。计算新热图的位置。# #搜索的热图mat_a # # -行片1,列片1 (mat_a_heatmap_body_1_1)…重叠
pos
与1 # # DataFrame行6列# #的热图片row_slice column_slice row_index # # <人物> <人物> <数字> <数字> <整数> # # 1 mat_a mat_a_heatmap_body_1_1 1 1 8 # # column_index # # 1 # # <整数> 7
pdf(…)ht_list =(ht_list)pos =selectArea(ht_listpos1 =单位(c(3,3),“厘米”),pos2 =单位(c(5,5),“厘米”))dev.off()

# #点1:x = 3.0厘米,y = 3.0厘米(以图形设备)# #点2:x = 5.0厘米,y = 5.0厘米(以图形设备)# # # #的热图位置已经计算,使用缓存。# #搜索的热图mat_a # # -行片1,列片1 (mat_a_heatmap_body_1_1)…重叠在热图mat_a的# # # #搜索——行片1,列片2 [mat_a_heatmap_body_1_2]…重叠在热图mat_a的# # # #搜索——行片2列片1 (mat_a_heatmap_body_2_1)…没有重叠在热图mat_a的# # # #搜索——行片2列片2 [mat_a_heatmap_body_2_2]…没有重叠在热图mat_b的# # # #搜索——行片1,列片1 (mat_b_heatmap_body_1_1)…没有重叠在热图mat_b的# # # #搜索——行片2列片1 (mat_b_heatmap_body_2_1)…没有重叠
pos
# # DataFrame 2行6列# #的热图片row_slice column_slice row_index # # <人物> <人物> <数字> <数字> < IntegerList > # # 1 mat_a mat_a_heatmap_body_1_1 1 1 7, 5, 2,…# # 2 mat_a mat_a_heatmap_body_1_2 1 2 7, 5, 2,…# # column_index # # < IntegerList > # 7 # 1、3、5 # 6 # 2

用户不需要离屏图形设备直接使用这个功能,但是,它是非常有用的,当情节发展中一个闪亮的应用实际上是生成在萤幕下的图形设备。我将在下一节中解释。

闪闪发光的应用

三个功能htPositionsOnDevice (),selectPosition ()selectArea (),它是可能实现的应用程序交互处理的热图。现在的问题是服务器端如何获取用户点击网页的位置。幸运的是,有一个解决方案。输出的热图通常是把内闪亮的::plotOutput ()plotOutput ()提供了两种操作点击。然后在服务器端,可以获取用户点击的位置的信息。可以设置的位置selectPosition ()selectArea ()通过pospos1/pos2正确的参数对应于原始矩阵中的值。