Visualization with ggplot2
## Learning Objectives
- Understand ggplot2 grammar of graphics
- Create basic plots
- Customize aesthetics
- Facet and layer plots
- Save plots
## Introduction to ggplot2
### What is ggplot2?
ggplot2 is a system for creating graphics based on the grammar of graphics:
- **Layered** - Plots built from components
- **Declarative** - You specify what, not how
- **Extensible** - Easy to customize
### Installation
```r
install.packages("ggplot2")
library(ggplot2)
```
## Basic Concepts
### Components of a Plot
1. **Data** - The dataframe
2. **Aesthetics** - Mapping variables to visual properties
3. **Geoms** - Geometric objects (points, lines, bars)
4. **Stats** - Statistical transformations
5. **Scales** - How aesthetics map to values
6. **Facets** - Split into subplots
7. **Theme** - Visual styling
### Basic Template
```r
ggplot(data = ) +
(mapping = aes())
```
## Getting Started
### Simple Scatter Plot
```r
# Create data
df <- data.frame(
x = c(1, 2, 3, 4, 5),
y = c(2, 4, 3, 5, 4)
)
# Basic scatter plot
ggplot(data = df, aes(x = x, y = y)) +
geom_point()
```
### Same with Pipe
```r
df %>%
ggplot(aes(x = x, y = y)) +
geom_point()
```
## Aesthetic Mappings
### What are Aesthetics?
Aesthetics connect data variables to visual properties:
- x, y - position
- color - point/line color
- size - point size
- shape - point shape
- alpha - transparency
### Mapping Variables
```r
df <- data.frame(
x = 1:10,
y = 1:10,
group = rep(c("A", "B"), 5)
)
# Color by group
ggplot(df, aes(x = x, y = y, color = group)) +
geom_point()
# Size by value
ggplot(df, aes(x = x, y = y, size = x)) +
geom_point()
# Shape by group
ggplot(df, aes(x = x, y = y, shape = group)) +
geom_point()
```
### Setting vs Mapping
```r
# Mapping: variable mapped to aesthetic
ggplot(df, aes(x = x, y = y, color = group)) +
geom_point()
# Setting: fixed value
ggplot(df, aes(x = x, y = y)) +
geom_point(color = "blue")
```
## Common Geoms
### geom_point()
```r
# Scatter plot
ggplot(df, aes(x = x, y = y)) +
geom_point()
# With all aesthetics
ggplot(df, aes(x = x, y = y, size = x, color = group)) +
geom_point(alpha = 0.7) # transparency
```
### geom_line()
```r
# Line plot
ggplot(df, aes(x = x, y = y)) +
geom_line()
# Line + points
ggplot(df, aes(x = x, y = y)) +
geom_line() +
geom_point()
```
### geom_smooth()
```r
# Add smoothed line
ggplot(df, aes(x = x, y = y)) +
geom_point() +
geom_smooth()
# Without confidence interval
ggplot(df, aes(x = x, y = y)) +
geom_point() +
geom_smooth(se = FALSE)
# Linear model
ggplot(df, aes(x = x, y = y)) +
geom_point() +
geom_smooth(method = "lm")
```
### geom_bar()
```r
# Count of categorical variable
df <- data.frame(
category = c("A", "B", "C", "A", "B", "A")
)
ggplot(df, aes(x = category)) +
geom_bar()
# From summarized data
df <- data.frame(
category = c("A", "B", "C"),
count = c(30, 45, 25)
)
ggplot(df, aes(x = category, y = count)) +
geom_bar(stat = "identity")
```
### geom_histogram()
```r
# Histogram of continuous variable
df <- data.frame(x = rnorm(1000))
ggplot(df, aes(x = x)) +
geom_histogram()
# Adjust bins
ggplot(df, aes(x = x)) +
geom_histogram(bins = 30)
# Different fill
ggplot(df, aes(x = x)) +
geom_histogram(fill = "steelblue", color = "white")
```
### geom_boxplot()
```r
# Boxplot
df <- data.frame(
group = rep(c("A", "B"), each = 50),
value = c(rnorm(50, 5, 1), rnorm(50, 7, 1))
)
ggplot(df, aes(x = group, y = value)) +
geom_boxplot()
# Horizontal
ggplot(df, aes(x = group, y = value)) +
geom_boxplot() +
coord_flip()
```
### geom_violin()
```r
# Violin plot (distribution shape)
ggplot(df, aes(x = group, y = value)) +
geom_violin()
```
### geom_density()
```r
# Density plot
ggplot(df, aes(x = value)) +
geom_density()
# Filled
ggplot(df, aes(x = value, fill = group)) +
geom_density(alpha = 0.5) # semi-transparent
```
### geom_text()
```r
# Add labels
ggplot(df, aes(x = x, y = y, label = group)) +
geom_text()
```
### geom_label()
```r
# Labels with background
ggplot(df, aes(x = x, y = y, label = group)) +
geom_label()
```
## Scales
### Color Scales
```r
# Manual colors
ggplot(df, aes(x = x, y = y, color = group)) +
geom_point() +
scale_color_manual(values = c("red", "blue"))
# Gradient
ggplot(df, aes(x = x, y = y, color = value)) +
geom_point() +
scale_color_gradient(low = "blue", high = "red")
# Gradient2 for diverging
ggplot(df, aes(x = x, y = y, color = value)) +
geom_point() +
scale_color_gradient2(low = "blue", mid = "white", high = "red")
```
### Size Scales
```r
# Manual size
ggplot(df, aes(x = x, y = y, size = value)) +
geom_point() +
scale_size(range = c(1, 10))
```
### Axis Scales
```r
# Log scale
ggplot(df, aes(x = x, y = y)) +
geom_point() +
scale_y_log10()
# Manual breaks
ggplot(df, aes(x = x, y = y)) +
geom_point() +
scale_y_continuous(breaks = seq(0, 100, 10))
```
## Labels and Titles
### labs()
```r
ggplot(df, aes(x = x, y = y)) +
geom_point() +
labs(
title = "My Title",
subtitle = "Subtitle here",
x = "X Axis Label",
y = "Y Axis Label",
color = "Legend Title",
caption = "Data source: ..."
)
```
### ggtitle()
```r
ggplot(df, aes(x = x, y = y)) +
geom_point() +
ggtitle("Title") +
xlab("X") +
ylab("Y")
```
## Themes
### Built-in Themes
```r
ggplot(df, aes(x = x, y = y)) +
geom_point() +
theme_minimal()
ggplot(df, aes(x = x, y = y)) +
geom_point() +
theme_bw()
ggplot(df, aes(x = x, y = y)) +
geom_point() +
theme_classic()
ggplot(df, aes(x = x, y = y)) +
geom_point() +
theme_dark()
```
### Theme Customization
```r
ggplot(df, aes(x = x, y = y)) +
geom_point() +
theme(
panel.background = element_rect(fill = "white"),
panel.grid.major = element_line(color = "gray90"),
panel.grid.minor = element_line(color = "gray95"),
text = element_text(family = "sans", size = 12),
plot.title = element_text(hjust = 0.5, face = "bold")
)
```
## Facets
### facet_wrap()
```r
# Wrap by one variable
df <- data.frame(
x = 1:20,
y = 1:20,
group = rep(c("A", "B", "C", "D"), 5)
)
ggplot(df, aes(x = x, y = y)) +
geom_point() +
facet_wrap(~group)
# Multiple rows
ggplot(df, aes(x = x, y = y)) +
geom_point() +
facet_wrap(~group, nrow = 2)
```
### facet_grid()
```r
# Grid by two variables
df <- data.frame(
x = 1:10,
y = 1:10,
group1 = rep(c("A", "B"), each = 10),
group2 = rep(c("X", "Y"), 10)
)
ggplot(df, aes(x = x, y = y)) +
geom_point() +
facet_grid(group1 ~ group2)
```
## Statistical Transformations
### Built-in Stats
```r
# Statistical summaries
ggplot(df, aes(x = x, y = y)) +
stat_summary()
# Boxplot with notches
ggplot(df, aes(x = group, y = value)) +
geom_boxplot(notch = TRUE)
```
## Position Adjustments
### Dodge, Stack, Fill
```r
# Bar chart
df <- data.frame(
group = c("A", "A", "B", "B"),
type = c("X", "Y", "X", "Y"),
value = c(10, 20, 15, 25)
)
# Side by side
ggplot(df, aes(x = group, y = value, fill = type)) +
geom_bar(position = "dodge", stat = "identity")
# Stacked
ggplot(df, aes(x = group, y = value, fill = type)) +
geom_bar(position = "stack", stat = "identity")
# Filled (proportions)
ggplot(df, aes(x = group, y = value, fill = type)) +
geom_bar(position = "fill", stat = "identity")
```
## Coordinates
### coord_flip()
```r
# Horizontal bars
ggplot(df, aes(x = category, y = value)) +
geom_bar(stat = "identity") +
coord_flip()
```
### coord_cartesian()
```r
# Zoom without affecting data
ggplot(df, aes(x = x, y = y)) +
geom_point() +
coord_cartesian(xlim = c(0, 50), ylim = c(0, 50))
```
## Saving Plots
### ggsave()
```r
# Save last plot
ggsave("my_plot.png")
ggsave("my_plot.pdf")
# Specific plot
p <- ggplot(df, aes(x = x, y = y)) + geom_point()
ggsave("my_plot.png", p)
# Specify size and resolution
ggsave("my_plot.png", width = 10, height = 8, dpi = 300)
```
### Export Functions
```r
# PNG
png("plot.png", width = 800, height = 600)
print(ggplot(df, aes(x = x, y = y)) + geom_point())
dev.off()
# PDF
pdf("plot.pdf", width = 10, height = 8)
print(ggplot(df, aes(x = x, y = y)) + geom_point())
dev.off()
```
## Extensions
### Common Extensions
```r
# patchwork - combine plots
install.packages("patchwork")
library(patchwork)
p1 <- ggplot(df, aes(x = x, y = y)) + geom_point()
p2 <- ggplot(df, aes(x = x)) + geom_histogram()
p1 + p2
# gganimate - animations
install.packages("gganimate")
library(gganimate)
```
## Summary
- ggplot2 uses layered grammar of graphics
- Map data to aesthetics with `aes()`
- Use `geom_*` functions for different plot types
- Customize with `scale_*`, `theme()`, `labs()`
- `facet_wrap()` and `facet_grid()` for subplots
- `ggsave()` to save plots
- Combine plots with patchwork or gridExtra
Comments
Comments powered by Giscus
To enable comments, add your Giscus embed code here.
Learn more about Giscus →