I would like to plot a chart with dual Y, both are bar plot with ggplot2, and both bar with its own error bar and label, the following code fails. The bars overlaped, and the labels can not be displayed.
df<- structure(list(dose = structure(1:3, .Label = c("0.5", "1", "2"
), class = "factor"), mean1 = c(13.23, 22.7, 26.06), sd1 = c(0.1,
0.2, 0.3), label = c("a", "b", "c"), mean2 = c(7.98, 16.77, 26.14
), sd2 = c(0.01, 0.2, 0.3), label2 = c("a", "b", "c")), row.names = c(NA,
-3L), class = "data.frame")
ggplot(df,aes(x = dose, fill = dose))
geom_bar(aes(y = mean1), position = 'dodge', stat="identity", width=.4)
geom_bar(aes(y = mean2/5), position = 'dodge', stat="identity", width=.4)
scale_y_continuous(sec.axis = sec_axis(~. *5, name = "mean2"))
geom_errorbar(aes(ymin = mean1, ymax = mean1 sd1), width=.07,
position=position_dodge(0.4))
geom_errorbar(aes(ymin = mean2, ymax = mean2 sd2), width=.07,
position=position_dodge(0.4))
geom_text(aes(y =mean1 sd1, label = label1),vjust = -0.5, position=position_dodge(0.4))
geom_text(aes(y =mean2 sd2, label = label2,),vjust = -0.5, position=position_dodge(0.4))
CodePudding user response:
Is this what you are looking for? You just need to restructure your data so that it can be dodged by group.
bind_rows(
df |>
select(dose, label, mean = mean1, sd = sd1) |>
mutate(group = 1),
df |>
select(dose, label, mean = mean2, sd = sd2) |>
mutate(group = 2,
mean = mean/5)
) |>
ggplot(aes(x = dose, fill = dose, group = group))
geom_bar(aes(y = mean), position = 'dodge', stat="identity", width=.4)
geom_errorbar(aes(ymin = mean, ymax = mean sd), width=.07,
position=position_dodge(0.4))
geom_text(aes(y =mean sd, label = label),vjust = -0.5, position=position_dodge(0.4))
scale_y_continuous(sec.axis = sec_axis(~. *5, name = "mean2"))