7

I wish to build a plot, essentially identical to that which i can produce using ggplots 'stat_bin2d' layer, however instead of the counts being mapped to a variable, I want the counts associated with the bin to be displayed as a label to each bin.

I got the following solution to the equivalent 1D problem from another thread

data <- data.frame(x = rnorm(1000), y = rnorm(1000))

ggplot(data, aes(x = x)) +
  stat_bin() +  
  stat_bin(geom="text", aes(label=..count..), vjust=-1.5)

The counts for each bin are clearly labeled. However moving from the 1D to 2D case, this works,

ggplot(data, aes(x = x, y = y)) +
  stat_bin2d()

But this returns an error.

ggplot(data, aes(x = x, y = y)) +
  stat_bin2d() +  
  stat_bin2d(geom="text", aes(label=..count..))

Error: geom_text requires the following missing aesthetics: x, y
Community
  • 1
  • 1
user4009949
  • 101
  • 1
  • 5
  • 3
    Take the time to create a [reproducible example](http://stackoverflow.com/questions/5963269/how-to-make-a-great-r-reproducible-example) with sample input so it's clear what your data looks like. Show your attempts thus far. Describe exactly where you are getting stuck. – MrFlick Dec 15 '14 at 01:56
  • 1
    Appologies, i accidentally posted when i didn't mean to. Have updated! – user4009949 Dec 15 '14 at 02:03
  • The last comment I could find on this came from [Hadley in 2010](https://groups.google.com/forum/#!topic/ggplot2/6lx_mYJVf3w) where he basically says you can't use `stat_bin2d`, you'll have to do the summarization yourself. – MrFlick Dec 15 '14 at 03:11
  • @MrFlick, I think this has changed in recent versions of `ggplot2` - see my answer. – Andrie May 31 '16 at 10:43

2 Answers2

6

In more recent versions of ggplot this is perfectly possible and works without errors.

Just be sure that you use the same arguments to both call of stat_bin2d(). For example, set binwidth = 1 on both lines:

library(ggplot2)
data <- data.frame(x = rnorm(1000), y = rnorm(1000))

ggplot(data, aes(x = x, y = y)) +
  geom_bin2d(binwidth = 1) + 
  stat_bin2d(geom = "text", aes(label = ..count..), binwidth = 1) +
  scale_fill_gradient(low = "white", high = "red") +
  xlim(-4, 4) +
  ylim(-4, 4) +
  coord_equal()

enter image description here

Andrie
  • 176,377
  • 47
  • 447
  • 496
4

I accidentally answered your question writing a question of my own. I figured out that stat_bin2d will work when you convert the variable you are binning from number to text, so:

library(ggplot2)
data <- data.frame(x = rnorm(1000), y = rnorm(1000))
x_t<-as.character(round(data$x,.1))
y_t<-as.character(round(data$y,.1))
x_x<-as.character(seq(-3,3),1)
y_y<-as.character(seq(-3,3),1)
data<-cbind(data,x_t,y_t)



ggplot(data, aes(x = x_t, y = y_t)) +
  geom_bin2d() + 
  stat_bin2d(geom="text", aes(label=..count..))+
  scale_x_discrete(limits =x_x) +
  scale_y_discrete(limits=y_y) 

So there you go. Unfortunately you have to set the binwidths outside of ggplot() so it isnt an ideal solution. I don't know why it works when you convert the variables to text, but there it is.

SeldomSeenSlim
  • 811
  • 9
  • 24
  • 1
    It's not necessary to perform this character conversion. Perhaps this was an appropriate workaround when this answer was originally posted, but it's not necessary in more recent versions of `ggplot`. See my answer. – Andrie May 31 '16 at 10:44
  • Great! I'm glad they got this working. Binning outside of ggplot() wasn't the end of the world, but its much more convenient to do it within ggplot(). – SeldomSeenSlim Jun 01 '16 at 20:04