2
votes

Might be missing something simple here, but my goal is to plot two heatmaps from two separate matrices. The matrices are of different dimensions, but I want each of the individual plotted tiles to be the same physical measurements between the two graphs. The graph size should then be dependent on the matrix dimensions, since the tile size will be constant between the graphs.

Here is an example of two different size matrices and a stripped down version of the graphs I want to make.

mat_lg <- matrix(rexp(20, rate=.1), ncol = 5)

melt(mat_lg) %>%
  ggplot(aes(x = Var1, y = Var2, fill = value)) +
  geom_tile() +
  theme_bw() +
  coord_equal()

mat_sm <- matrix(rexp(12, rate = .1), ncol = 3)

melt(mat_sm) %>%
  ggplot(aes(x = Var1, y = Var2, fill = value)) +
  geom_tile() +
  theme_bw() +
  coord_equal()

The graph made from mat_lg has smaller tiles... enter image description here

compared to the tiles in the graph made from mat_sm... enter image description here

I've played around with the width/height settings in geom_tile, but was unable to achieve my goal. Have also played with grid.arrange as well as facet_wrap settings but to no avail.

My guess is that I need to change the final plot size based on my initial matrix dimension in order to get the tiles with the same physical measurements. Would gladly appreciate any help on this matter!

2

2 Answers

3
votes

If the two matrices have at least one dimension that is equal, then this is accomplished directly by egg::ggarrange(), which lines up the plot panels:

## Save plots into variables
gg1 <- melt(mat_lg) %>% ggplot(...)
gg2 <- melt(mat_sm) %>% ggplot(...)

## Let ggarrange line up the panels
egg::ggarrange( gg1, gg2 )

enter image description here

If dimensions of the two matrices differ entirely, use egg::set_panel_size to adjust the panel sizes explicitly:

p1 <- egg::set_panel_size( gg1, height=unit(ncol(mat_lg), "cm"),
                          width=unit(nrow(mat_lg), "cm") )
p2 <- egg::set_panel_size( gg2, height=unit(ncol(mat_sm), "cm"),
                          width=unit(nrow(mat_sm), "cm") )
cowplot::plot_grid( p1, p2, nrow=1 )

enter image description here

1
votes

If I understand right, you want that both your heatmap as the same heigh and width. Based on your example, you should calculate the ratio between your matrices and passed it as argument in coord_equal. On your example, it should look like:

library(ggplot2)
library(dplyr)
mat_lg <- matrix(rexp(20, rate=.1), ncol = 5)

melt(mat_lg) %>%
  ggplot(aes(x = Var1, y = Var2, fill = value)) +
  geom_tile() +
  theme_bw() +
  coord_equal()

mat_sm <- matrix(rexp(12, rate = .1), ncol = 3)
scale_factor = ncol(mat_lg) / ncol(mat_sm)

melt(mat_sm) %>%
  ggplot(aes(x = Var1, y = Var2, fill = value)) +
  geom_tile() +
  theme_bw() +
  coord_equal(ratio = scale_factor)

And you get both heatmaps at the same size:

mat_sm:

enter image description here

mat_lg:

enter image description here

Is it what you are looking for ?