Here's some data with x
and y
values, along with two grouping variables level1
and level2
. I'd like to plot the grouping variables with colour
and linetype
aesthetics, like this:
library(ggplot2)
library(dplyr)
set.seed(100)
dat <- data.frame(
x = rep(2010:2014, each = 6),
level1 = rep(letters[1:3], times = 10),
level2 = rep(rep(c("y", "z"), each = 3), times = 5),
y = rnorm(30)
)
dat %>%
ggplot(aes(x = x, y = y, colour = level1, linetype = level2))
geom_line()
This plot is actually correct. The problem is when I change the x-axis to a factor (or character):
dat %>%
mutate(x = factor(x)) %>%
ggplot(aes(x = x, y = y, colour = level1, linetype = level2))
geom_line()
geom_path: Each group consists of only one observation. Do you need to adjust the group aesthetic?
That seems fair enough, I never actually specified the group
aesthetic, it just seemed to work out of the box when x
was numeric. My first thought was to specify group = level1
, but that leads to
Error: geom_path: If you are using dotted or dashed lines, colour, size and linetype must be constant over the line
Which also seems reasonable, because there are actually six lines, and they're defined by the combination of level1
and level2
, not just level1
. But I'm not sure it's possible to specify a multi-level line grouping, e.g.,
dat %>%
mutate(x = factor(x)) %>%
ggplot(aes(x = x, y = y, colour = level1, linetype = level2))
geom_line(aes(group = c(level1, level2)))
Error: Aesthetics must be either length 1 or the same as the data (30): group
The desired output is a reproduction of the first plot, but with the x-variable as a factor rather than numeric. Any insight into why the plot seems to work when x
is numeric would be interesting as well. Thanks.
CodePudding user response:
You had generally the right idea trying to use two grouping variables. To do this you need to use the interaction between level1
and level2
in the group argument.
library(ggplot2)
library(dplyr)
dat %>%
mutate(x = factor(x)) %>%
ggplot(aes(x = x, y = y, colour = level1, linetype = level2, group = interaction(level1, level2)))
geom_line()