I am doing time series analysis in R using the forecast package. The forecast::autoplot() creates a ggplot object.
I have two questions about plotting decomposed series:
- How do I place text in the trend panel (next to the vertical red line). Using ggplot or other packages?
- How can I rename the "data" panel to be capitalized as "Data"?
Here is my code:
library(forecast)
# Load in AirPassengers time series
data("AirPassengers")
# Decomopose time series
decomposed_ts <- decompose(AirPassengers)
# Plot decomposed time series
forecast::autoplot(decomposed_ts) geom_vline(xintercept = 1954, colour = "red")
For Q1, I tried to use annotate() but it places the same text labels on each facet, whereas I only want one label on only the trend panel (see screenshot). I also tried to use the ggtext package, but could not get it to work. I couldn't figure out what the faceted variable is because forecast::autoplot() automatically created the faceting.
For Q2. I saved the plot as a variable i.e. myPlot <- forecast::autoplot(decomposed_ts) geom_vline(xintercept = 1954, colour = "red"). I then tried myPlot$ looking for where the "data" facet is named.
CodePudding user response:
I'm sure someone smarter than me could dig into the architecture of a ggplot2 plot, but you could make your own autoplot function to keep it a little simpler(ish). Here I added a facet label argument to solve your problem:
library(tidyverse)
library(forecast)
my_new_autoplot <- function(decomp,
facet_labels = c("data", "trend", "seasonal", "remainder")){
list(
tibble(Time = time(decomp$x),
val = decomp$x,
type = facet_labels[1]),
tibble(Time = time(decomp$trend),
val = decomp$trend,
type = facet_labels[2]),
tibble(Time = time(decomp$seasonal),
val = decomp$seasonal,
type = facet_labels[3]),
tibble(Time = time(decomp$random),
val = decomp$random,
type = facet_labels[4]) |>
mutate(t1 = pmax(0, val),
t2 = pmin(val, 0),
val = 0)
) |>
bind_rows() |>
mutate(type = factor(type, levels = facet_labels)) |>
ggplot(aes(Time, val))
geom_path()
geom_errorbar(aes(ymin = t2, ymax = t1))
facet_wrap(~type, ncol = 1, scales = "free_y", strip.position = "left")
labs(y = "")
}
my_new_autoplot(decomposed_ts)
geom_vline(xintercept = 1954, colour = "red")
my_new_autoplot(decomposed_ts,
facet_labels = c("my_data!", "trend..", "~seasonal~", "rEmainDeR"))
geom_vline(xintercept = 1954, colour = "red")
And if we wanted to add text, we can do that too:
my_plot <- my_new_autoplot(decomposed_ts,
facet_labels = c("my_data!", "trend..", "~seasonal~", "rEmainDeR"))
geom_vline(xintercept = 1954, colour = "red")
add_text <- function(plot, facet, text, x, y, ...){
text_data <- tibble(Time = x, val = y, type = facet, label = text) |>
mutate(type = factor(type, levels = levels(plot$data$type)))
plot
geom_text(data = text_data, aes(label = label), ...)
}
add_text(plot = my_plot,
facet = "rEmainDeR",
text = "This is red",
x = 1955,
y = 40,
color = "red")
CodePudding user response:
You can add geom_text to the original auto_plot:
annotation <- data.frame(
x = c(1950),
y = c(250),
parts = c("trend"),
label = c("label 1")
)
forecast::autoplot(decomposed_ts)
geom_vline(xintercept = 1954, colour = "red")
geom_text(data = annotation, aes(x = x, y = y, label = label))