Tyler Rinker
Tyler Rinker

Reputation: 109864

Difference plot

I don't know the name of this type of plot (comments around this are welcomed). Essentially it is a barplot with glyphs that are filled to indicate a loss/gain. The glyph is arrow like encoding information about direction, magnitude, and allowing the bar geom under to be seen.

enter image description here

This looks interesting but can't think of how to do it in ggplot2 (grid frame work). How could we recreate this plot in ggplot2/grid framework (base solutions welcomed as well for completeness of question). Specifically the glyphs, not the text as this is pretty straight forward in ggplot2 already.

Here is some code to create data and traditional overlaid & coordinate flipped dodged bar plots and line graphs to show typical ways of visualizing this type of data.

set.seed(10)
x <- sample(30:60, 12)
y <- jitter(x, 60)

library(ggplot2)
dat <- data.frame(
    year = rep(2012:2013, each=12),
    month = rep(month.abb, 2),
    profit = c(x, y)
)


ggplot() + 
geom_bar(data=subset(dat, year==2012), aes(x=month, weight=profit)) +
geom_bar(data=subset(dat, year==2013), aes(x=month, weight=profit), width=.5, fill="red")

ggplot(dat, aes(x=month, fill=factor(year))) +
    geom_bar(position="dodge", aes(weight=profit)) +
    coord_flip

ggplot(dat, aes(x=month, y=profit, group = year, color=factor(year))) +
    geom_line(size=1) 

enter image description here

enter image description here

enter image description here

Upvotes: 8

Views: 2457

Answers (1)

kohske
kohske

Reputation: 66842

Here is an example, perhaps there are other ways though,

dat <- data.frame(
  year = rep(2012:2013, each=12),
  month = factor(rep(1:12, 2), labels=month.abb),
  profit = c(x, y)
)
dat2 <- reshape2::dcast(dat, month~ year, value.var = "profit")
names(dat2)[2:3] <- paste0("Y", names(dat2)[2:3])

ggplot(dat2) + 
  geom_bar(aes(x=month, y = Y2012), stat = "identity", fill = "grey80", width = 0.6) +
  geom_segment(aes(x=as.numeric(month)-0.4, xend = as.numeric(month)+0.4, y = Y2013, yend = Y2013)) + 
  geom_segment(aes(x = month, xend = month, y = Y2013, yend = Y2012, colour = Y2013 < Y2012), 
               arrow = arrow(60, type = "closed", length = unit(0.1, "inches")), size = 1.5) +
  theme_bw()

enter image description here

Upvotes: 12

Related Questions