Seeking help with identifying geom_vline() in legend

848 views
Skip to first unread message

canoe.moore

unread,
Aug 8, 2010, 9:09:57 PM8/8/10
to ggplot2
Hello,

I'm trying to plot a legend that identifies varying shapes and a
vertical line, but I can't get the legend to identify the geom_vline()
layer.

Here are some earlier posts that seem relevant but didn't enable me to
do what I'm trying:
http://groups.google.com/group/ggplot2/browse_thread/thread/1811cce4fd7d05c5
http://groups.google.com/group/ggplot2/browse_thread/thread/7f1525795e5e5c9d
http://groups.google.com/group/ggplot2/browse_thread/thread/e275ac1e28a4d615

Thanks in advance for any help you can provide.

Regards,
Chris


#Reproducible example

#Simulate outcomes from a regression discontinuity design.
set.seed(100)
x <- rnorm(200, 0, 10)
z <- ifelse(x<0, 1, 0)
tx <- which(z==1)
set.seed(101)
y <- rnorm(200, 50, 10) + 10*z + 0.5*x - 0.025*x^2

#Fit a regression discontinuity model.
model <- lm(y ~ z + x + I(x^2))
coefs <- coefficients(model)

#Plot fitted lines, vertical line/cutoff, and legend.
plot(y ~ x, col=NULL, ylim=c(min(y)-10, max(y)+10))
abline(v=0, lty=2, lwd=2, col="darkgrey")
points(x[tx], y[tx], col="darkgrey", pch=4)
points(x[-tx], y[-tx], col="darkgrey")
curve(coefs[1] + coefs[2] + coefs[3]*x + coefs[4]*x^2, min(x)-10, 0,
add=T)
curve(coefs[1] + coefs[3]*x + coefs[4]*x^2, 0, max(x)+10, add=T)
legend("bottomright", bg="white", cex=.75, pt.cex=.75, c("Treatment ",
"Control ", "Cutoff "), lty=c(NA, NA, 2), lwd=c(NA, NA, 2),
col=c("darkgrey", "darkgrey", "darkgrey"), pch=c(4, 1, NA))

#Plot fitted lines and vertical line/cutoff with ggplot.
data.plot <- data.frame(x, y, z)
library(ggplot2)
f1 <- function(x) ifelse(x <= 0.1, coefs[1] + coefs[2] + coefs[3] * x
+ coefs[4] * x^2, NA)
f2 <- function(x) ifelse(x >= 0, coefs[1] + coefs[3] * x + coefs[4] *
x^2, NA)
g1 <- ggplot(data.plot, aes(y=y, x=x)) +
geom_point(aes(shape=factor(z)), color="darkgrey")
g2 <- g1 + stat_function(fun = f1) + stat_function(fun = f2)
g2 + geom_vline(xintercept=0, lwd=1, linetype=3, color="darkgrey") +
scale_shape_manual(name="Legend", labels=c("Control", "Treatment"),
value=c(1, 4))

#Attempt (unsuccessfully) to add vertical line to legend.
g2 + geom_vline(xintercept=0, lwd=1, linetype=3, color="darkgrey") +
scale_shape_manual(name="Legend", labels=c("Control", "Treatment"),
value=c(1, 4)) + scale_linetype_manual(name="Legend", value=3)
#vertical line/cutoff not in legend
g2 + geom_vline(xintercept=0, lwd=1, linetype=3, color="darkgrey") +
scale_shape_manual(name="Legend", labels=c("Control", "Treatment",
"Cutoff"), value=c(1, 4, NA)) + scale_linetype_manual(name="Legend",
labels=c("Control", "Treatment", "Cutoff"), value=c(NA, NA, 3)) #Error
in `$<-.data.frame`(`*tmp*`, ".labels", value = c("Control",
"Treatment", : replacement has 3 rows, data has 2
g2 + geom_vline(xintercept=0, lwd=1, linetype=3, color="darkgrey",
labels="Cutoff") + scale_shape_manual(name="Legend",
labels=c("Control", "Treatment", "Cutoff"), value=c(1, 4, NA)) +
scale_linetype_manual(name="Legend", labels=c("Control", "Treatment",
"Cutoff"), value=c(NA, NA, 3)) #Error in `$<-.data.frame`(`*tmp*`,
".labels", value = c("Control", "Treatment", : replacement has 3 rows,
data has 2
g2 + geom_vline(xintercept=0, lwd=1, linetype=3, color="darkgrey",
labels=c("Control", "Treatment", "Cutoff")) +
scale_shape_manual(name="Legend", labels=c("Control", "Treatment",
"Cutoff"), value=c(1, 4, NA)) + scale_linetype_manual(name="Legend",
labels=c("Control", "Treatment", "Cutoff"), value=c(NA, NA, 3)) #Error
in `$<-.data.frame`(`*tmp*`, ".labels", value = c("Control",
"Treatment", : replacement has 3 rows, data has 2
g2 + geom_vline(xintercept=0, lwd=1, linetype=3, color="darkgrey",
labels=c("Control", "Treatment", "Cutoff")) +
scale_shape_manual(name="Legend", labels=c("Control", "Treatment",
"Cutoff"), value=c(1, 4, NA)) + scale_linetype_manual(name="Legend",
labels=c("Control", "Treatment", "Cutoff"), value=c(NA, NA, 3)) #Error
in `$<-.data.frame`(`*tmp*`, ".labels", value = c("Control",
"Treatment", : replacement has 3 rows, data has 2

> sessionInfo()
R version 2.9.2 (2009-08-24)
i386-pc-mingw32
locale:
LC_COLLATE=English_United States.1252;LC_CTYPE=English_United States.
1252;LC_MONETARY=English_United States.
1252;LC_NUMERIC=C;LC_TIME=English_United States.1252
attached base packages:
[1] grid stats graphics grDevices utils datasets
methods base
other attached packages:
[1] ggplot2_0.8.3 reshape_0.8.3 plyr_0.1.9 proto_0.3-8

Andrie de Vries

unread,
Aug 9, 2010, 5:49:26 AM8/9/10
to ggplot2
Chris

ggplot will only construct a scale if the underlying data is in a
data.frame. As far as I can tell, your code examples used fixed
values of linetype, rather than mapping data to the linetype.

I have modified your example as follows:
1) construct a data frame with a single row containing data to
construct the vline
2) map this data to the geom_vline() paramaters using aes()

Please also note that you are using a rather old version of R, ggplot
and plyr. This meant that your reproducible example didn't actually
work on my configuration. Likewise, this example may not work on your
machine, and you may have to do small amount of backporting to make it
work.

One caveat. I couldn't get the legends to collapse into one, even
when naming them the same (this should have worked, but I am not sure
why it doesn't). As a workaroud I created two legends, one called
Symbols and one called Lines.

The current versions:
- [R] : 2.11.1
- ggplot: 0.8.8
- plyr: 1.0.3

Anyway, here is the code. I hope this helps.

Andrie

#Reproducible example

#Simulate outcomes from a regression discontinuity design.
set.seed(100)
x <- rnorm(200, 0, 10)
z <- ifelse(x<0, 1, 0)
tx <- which(z==1)
set.seed(101)
y <- rnorm(200, 50, 10) + 10*z + 0.5*x - 0.025*x^2

#Fit a regression discontinuity model.
model <- lm(y ~ z + x + I(x^2))
coefs <- coefficients(model)


#Plot fitted lines and vertical line/cutoff with ggplot.
data.plot <- data.frame(x, y, z)
library(ggplot2)
f1 <- function(x) ifelse(x <= 0.1, coefs[1] + coefs[2] + coefs[3] * x
+
coefs[4] * x^2, NA)
f2 <- function(x) ifelse(x >= 0, coefs[1] + coefs[3] * x + coefs[4] *
x^2, NA)

g1 <- ggplot(data.plot, aes(y=y, x=x)) +
geom_point(aes(shape=factor(z)), color="darkgrey")

g2 <- g1 + stat_function(fun = f1) + stat_function(fun = f2)

g2 + geom_vline(xintercept=0, lwd=1, linetype=3, color="darkgrey") +
scale_shape("Legend", breaks=c(0,1), labels=c("Control",
"Treatment"))

data.vline <- data.frame(xintercept=0, Cutoff=3)

#Add vertical line to legend.
g2 + geom_vline(data=data.vline, aes(xintercept=xintercept,
linetype=factor(Cutoff)), lwd=1, color="darkgrey") +
scale_shape_manual(name="Symbols ", labels=c("Control",
"Treatment"), breaks=c(0, 1), values=c(1,4)) +
scale_linetype_manual(name="Line ", labels="Cutoff", values=3,
breaks=3)
Reply all
Reply to author
Forward
0 new messages