Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Add legend to "geom_bar" using the ggplot2 package

Tags:

r

ggplot2

I am a newbie to R, so please pardon my ignorance. I made a pseudo-stacked barplot in which I drew 4 sets of bars on top of each other using geom_bar. There are 4 health status categories (alive, dead, infected, & sod-dead) for three species of oak trees (QUAG, QUKE, QUCH).

My code is as follows:


x <- as.data.frame(list(variable=c("QUAG", "QUKE", "QUCH"), alive = c(627,208,109),  infected = c(102,27,0), dead = c(133,112,12), sod.dead=c(49,8,0)))

x.plot = ggplot(x, aes(variable, alive)) + geom_bar(fill="gray85") + 
  geom_bar(aes(variable,dead), fill="gray65") +
  geom_bar(aes(variable, infected), fill="gray38") +
  geom_bar(aes(variable, sod.dead), fill="black")+
  opts(panel.background = theme_rect(fill='gray100'))
x.plot

Now I want to make a legend that shows which shade of gray relates to tree status, i.e., "gray65" is "dead trees", etc. I've been trying for the past hour and can't get it to work.

like image 997
Sarah Haas Avatar asked Nov 12 '12 23:11

Sarah Haas


People also ask

How do I add a legend in ggplot2?

Adding a legend If you want to add a legend to a ggplot2 chart you will need to pass a categorical (or numerical) variable to color , fill , shape or alpha inside aes . Depending on which argument you use to pass the data and your specific case the output will be different.

How do I change the legend in ggplot2?

You can use the following syntax to change the legend labels in ggplot2: p + scale_fill_discrete(labels=c('label1', 'label2', 'label3', ...))

Why is Ggplot not showing legend?

You need to put the color parameter inside the aesthetics. This will result in the mapping of colors for the legend. After that you can manually scale the color to get any color you desire.

What does Geom_col () Do How is it different to Geom_bar ()?

There are two types of bar charts: geom_bar() and geom_col() . geom_bar() makes the height of the bar proportional to the number of cases in each group (or if the weight aesthetic is supplied, the sum of the weights). If you want the heights of the bars to represent values in the data, use geom_col() instead.


1 Answers

I see that @Brandon Bertelsen has posted a great answer. I would like to add some code that addresses additional details mentioned in the original post:

  1. After you reshape your data and map health status to fill, ggplot will create the legend automatically.
  2. I suggest using scale_fill_manual() to get the exact grays mentioned in the original post.
  3. theme_bw() is a handy function to quickly get a black and white look to your plot.
  4. The plotting order of factor levels/colors can be controlled by specifying the desired order with the levels argument of factor().
  5. A dodged barplot (instead of stacked) may have some advantages for this data set.

library(reshape2)
library(ggplot2)

x <- as.data.frame(list(variable=c("QUAG", "QUKE", "QUCH"), 
                        alive=c(627, 208, 109),  infected=c(102, 27, 0), 
                        dead=c(133, 112, 12), sod.dead=c(49, 8, 0)))

# Put data into 'long form' with melt from the reshape2 package.
dat = melt(x, id.var="variable", variable.name="status")

head(dat)
#    variable   status value
# 1      QUAG    alive   627
# 2      QUKE    alive   208
# 3      QUCH    alive   109
# 4      QUAG infected   102
# 5      QUKE infected    27
# 6      QUCH infected     0

# By manually specifying the levels in the factor, you can control
# the stacking order of the associated fill colors.
dat$status = factor(as.character(dat$status), 
                    levels=c("sod.dead", "dead", "infected", "alive"))

# Create a named character vector that relates factor levels to colors.
grays = c(alive="gray85", dead="gray65", infected="gray38", sod.dead="black")

plot_1 = ggplot(dat, aes(x=variable, y=value, fill=status)) +
         theme_bw() +
         geom_bar(position="stack") +
         scale_fill_manual(values=grays)

ggsave(plot=plot_1, filename="plot_1.png", height=5, width=5)

enter image description here

# You may also want to try a dodged barplot.
plot_2 = ggplot(dat, aes(x=variable, y=value, fill=status)) +
         theme_bw() +
         geom_bar(position="dodge") +
         scale_fill_manual(values=grays)

ggsave(plot=plot_2, filename="plot_2.png", height=4, width=5)

enter image description here

like image 99
bdemarest Avatar answered Oct 08 '22 21:10

bdemarest