0
votes

I want to plot some point estimates with a couple of interval estimates around them, and then to superimpose the true point values using a different color and size, with a legend for the color.

I've tried lots of things. If I just use a new call to geom_point, I can't figure out how to add a legend. Therefore, my current approach resorts to stacking the data on top of itself, which is clumsy. Even then, the graph comes out wrong with big blue points for the True values, with the desired orange points on top of them.

I'd appreciate any help I can get.

nms <- c("2.5%","25%","50%","75%","97.5%","dose","truep")
a <- c(9.00614679684893e-    44,0.000123271800672435,0.0339603711049475,0.187721170170911,0.67452033450121,5,0.040752445325937)
b <- c(1.59502878028266e-25,0.00328588588499889,0.0738203422543555,0.25210200886225,0.714843425007051,10,0.0885844107052267)
cc <- c(1.41975723605948e-14,0.0184599181547097,0.118284929584256,0.311068595276067,0.74339745948793,15,0.141941915501108)
d <- c(0.0311851190805834,0.154722028150561,0.299318020818234,0.50887634580605,0.838779816278485,25,0.359181624981881)
e <- c(0.0529617924263383,0.289588386297245,0.566777817134668,0.883959271416755,0.999999999999317,40,0.680133380561602)
f <- c(0.0598904847882839,0.327655201251564,0.640100529843672,0.950060245074853,1,50,0.768120635812406)
g <- c(0.0641613025760661,0.355626055560067,0.686504841650593,0.978023943968809,1,60,0.823805809980712)

p <- as.data.frame(t(data.frame(a, b, cc, d, e, f, g)))
names(p) <- nms

# Faff duplicating data
p$truep <- 1.2 * p$truep
p2 <- p
p2[, 1:5] <- p$truep # truep is known, so there are no intervals

p3 <- rbind(p2, p)
p3$wh <- rep((c(2, 3)), each=nrow(p))
p3$col <- rep(c("orange", "blue"), each=nrow(p))

ggplot(p3, aes(dose, `50%`)) +
  geom_point(aes(size=wh, color=col)) +
  scale_size(range=c(5, 7), guide="none") +
  scale_color_manual(name="", labels=c("Prior", "True"), values=c("blue", "orange")) +
  geom_pointrange(aes(ymin=`2.5%`, ymax=`97.5%`, x=dose), color="blue") +
  geom_pointrange(aes(ymin=`25%`, ymax=`75%`, x=dose), color="blue", size=2) +
  geom_point(aes(dose, truep), color="orange") +
  theme(axis.text.x=element_text(size=12), axis.title.x=element_text(size=14),
    axis.text.y=element_text(size=12), axis.title.y=element_text(size=14),
    legend.text=element_text(size=12))

R 3.3.1, ggplot2_2.1.1

Thanks, Harry

2

2 Answers

0
votes

I found a solution by splitting the dataset in two parts:

library(dplyr)

priors <- p%>%
  mutate(datatype = 'Prior')

truevals <-  p%>%
  select(dose, truep)%>%
  mutate(datatype = 'True')


ggplot(truevals, aes(x = dose, y = truep, colour = datatype))+
  geom_pointrange(data = priors, aes(ymin=`25%`, ymax=`75%`, y = `50%`), size=1.5) +
  geom_pointrange(data = priors, aes(ymin=`2.5%`, ymax=`97.5%`, y = `50%`))+
  geom_point()+
  scale_color_manual(name="", values=c("Prior" = "blue", "True" = "orange")) +
  theme(axis.text.x=element_text(size=12), axis.title.x=element_text(size=14),
        axis.text.y=element_text(size=12), axis.title.y=element_text(size=14),
        legend.text=element_text(size=12))

First we plot the two pointranges based on the dataset with priors. Then the actual values. By adding a row with the datatype to both datasets we can add the legend. The result is this graph: enter image description here

0
votes

For the method ggplot2::geom_point() there is a show.legend attribute which is NA by default so setting this to TRUE should help.

You can add a legend using the labels attribute as follows:

ggplot2::scale_fill_manual(values = c("red", "black",
                           labels = c("Number of people",
                                      "Number of birds"))

You are already doing this with labels=c("Prior", "True")

You can also change the look of the legend with:

ggplot2::theme(legend.position = "bottom",
               legend.text = ggplot2::element_text(size = 22),
               legend.box = "horizontal",
               legend.key = ggplot2::element_blank())