ggplot2 scale_x_date() in R: Format Date Axis
The scale_x_date() function in ggplot2 customizes the X axis when x is a Date. It controls break intervals (every month, every quarter) and label formats (year, month name, etc.).
+ scale_x_date(date_breaks = "1 month", date_labels = "%b %Y")
+ scale_x_date(date_breaks = "quarter")
+ scale_x_date(date_labels = "%Y")
+ scale_x_date(limits = as.Date(c("2020-01-01","2024-12-31")))
+ scale_x_datetime() # POSIXct versionNeed explanation? Read on for examples and pitfalls.
What scale_x_date() does in one sentence
scale_x_date() controls a Date X axis with shortcut arguments date_breaks (interval) and date_labels (strftime format). Used for time-series plots.
Syntax
**scale_x_date(date_breaks = NULL, date_labels = NULL, date_minor_breaks = NULL, ...). Standard scale__continuous args also apply.*
date_breaks = "1 month" is the cleanest way to control interval; manual breaks = works but is verbose for date data.Five common patterns
1. Yearly labels
2. Month-year
3. Day-month
4. Limit to a range
5. Quarterly breaks
date_labels uses strftime format codes. Common: %Y (4-digit year), %y (2-digit), %b (abbreviated month), %B (full month), %m (number), %d (day).scale_x_date() vs scale_x_datetime() vs scale_x_continuous
| Function | x class |
|---|---|
scale_x_date() |
Date |
scale_x_datetime() |
POSIXct |
scale_x_time() |
hms |
scale_x_continuous() |
numeric |
When to use which: pick by the class of your x variable. class(df$date) tells you which.
A practical workflow
For time-series, set sensible breaks and labels per data span.
Major ticks yearly, minor every month.
Common pitfalls
Pitfall 1: x is character, not Date. scale_x_date expects Date class. Convert first: mutate(date = as.Date(date_str)).
Pitfall 2: timezone surprises. For POSIXct, use scale_x_datetime. Date-only (no time) uses scale_x_date.
scale_x_date will fail silently if x is numeric or character. Always check class(df$x) returns "Date".Try it yourself
Try it: Plot economics$unemploy by date with yearly labels. Save to ex_plot.
Click to reveal solution
Explanation: Major ticks every 5 years; year-only labels.
Related ggplot2 / scales functions
After mastering scale_x_date, look at:
scale_x_datetime(): POSIXctscale_x_continuous(): numericscale_x_discrete(): factor / characterscales::date_breaks()/date_format(): lower-level helpers
FAQ
What does scale_x_date do in ggplot2?
scale_x_date() formats the X axis when x is a Date. Controls breaks and labels with date-specific shortcuts.
What is the difference between scale_x_date and scale_x_datetime?
scale_x_date for Date class (no time). scale_x_datetime for POSIXct (with time). Pick by class of your x.
How do I show only the year on x?
scale_x_date(date_labels = "%Y"). Use strftime codes for any format.
How do I make ticks every quarter?
scale_x_date(date_breaks = "3 months") or date_breaks = "quarter".
What if my dates are character?
Convert first: mutate(date = as.Date(date_str)). scale_x_date requires Date class.