The hardware and bandwidth for this mirror is donated by dogado GmbH, the Webhosting and Full Service-Cloud Provider. Check out our Wordpress Tutorial.
If you wish to report a bug, or if you are interested in having us mirror your free-software or open-source project, please feel free to contact us at mirror[@]dogado.de.

Overview

The dumbbell package creates dumbbell plots in ggplot2. A dumbbell plot compares two numeric values for the same item and connects them with a line segment. This is useful when you want to show before/after values, treatment/control values, male/female values, or any paired comparison.

The main function is dumbbell(). It expects a data frame with at least four columns:

  1. an ID column for the y-axis labels,
  2. a grouping or facet key,
  3. the first numeric value,
  4. the second numeric value.

The function returns a ggplot object, so you can add standard ggplot2 layers such as facet_wrap(), labs(), theme(), or coord_cartesian().

Installation

Install the package from CRAN with:

install.packages("dumbbell")

Or install a development version from a local source directory:

devtools::install("path/to/dumbbell")

Load packages

suppressPackageStartupMessages({
  library(dumbbell)
  library(dplyr)
  library(ggplot2)
})

Example data

The example below creates paired measurements for two groups. Each subject has a value for group A and group B. The data are then reshaped into the format expected by dumbbell().

set.seed(123)

raw_data <- data.frame(
  Group = rep(c("A", "B"), each = 10),
  Subject = rep(paste0("sub_", 1:10), times = 2),
  result = sample(1:100000, 20, replace = TRUE),
  analysis = rep(rep(c("a", "b"), each = 5), times = 2)
)

group_a <- raw_data %>% filter(Group == "A")
group_b <- raw_data %>% filter(Group == "B")

plot_data <- merge(
  group_a,
  group_b,
  by = c("Subject", "analysis")
)

plot_data <- plot_data %>%
  mutate(diff = result.x - result.y) %>%
  arrange(diff)

plot_data$Subject <- factor(plot_data$Subject, levels = plot_data$Subject)

head(plot_data)

Basic dumbbell plot

Use id for the labels on the y-axis, key for the grouping variable, and column1/column2 for the paired numeric values.

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B"
)

Add a delta column

Set delt = 1 to add the difference between the two values at the right side of the plot.

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B",
  delt = 1,
  expandx = 0.1
)

Add value labels

Set pt_val = 1 to print the numeric values next to the points. Use col_lab1 and col_lab2 to control the label colors.

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B",
  pt_val = 1,
  expandx = 0.05,
  col_lab1 = "blue",
  col_lab2 = "red"
)

Add arrows

Set arrow = 1 to draw arrows along the connecting segments. Use arrow_size, segsize, pointsize, pt_alpha, col_seg1, and col_seg2 to customize the display.

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B",
  arrow = 1,
  arrow_size = 0.2,
  segsize = 0.7,
  pointsize = 1.5,
  pt_alpha = 0.6,
  col_seg1 = "#A9A9A9",
  col_seg2 = "#A9A9A9"
)

Facet by group

Because dumbbell() returns a ggplot object, you can add facet_wrap() directly.

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B"
) +
  facet_wrap(~ analysis, ncol = 1, scales = "free_y")

Add paired p-values

The pval argument adds a paired test result to the facet label:

The current implementation uses base R functions from the stats package, so the package does not need to depend on rstatix for these tests.

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B",
  pval = 1
) +
  facet_wrap(~ analysis, ncol = 1, scales = "free_y")

Complete customized example

This example combines facets, arrows, highlighted segment colors, point transparency, and delta labels.

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B",
  delt = 1,
  col_seg2 = "red",
  col_seg1 = "blue",
  arrow = 1,
  pt_alpha = 0.6,
  pointsize = 2,
  expandx = 0.2,
  segsize = 0.5,
  textsize = 2,
  pval = 1
) +
  facet_wrap(~ analysis, ncol = 1, scales = "free_y")

Working with axis limits

Because dumbbell() already adds an x-axis scale, xlim() will replace that scale and may remove data outside the requested range. To zoom without dropping observations, use coord_cartesian():

dumbbell(
  xdf = plot_data,
  id = "Subject",
  key = "analysis",
  column1 = "result.x",
  column2 = "result.y",
  lab1 = "Group A",
  lab2 = "Group B"
) +
  coord_cartesian(xlim = c(0, 100000))

Main arguments

Argument Description
xdf Input data frame.
id Column used for the y-axis labels.
key Grouping variable, commonly used with facet_wrap().
column1, column2 Paired numeric columns to compare.
lab1, lab2 Labels for the two compared values.
delt Set to 1 to display the difference between the two values.
pt_val Set to 1 to display point value labels.
pval Set to 1 for paired Wilcoxon test or 2 for paired t-test.
arrow Set to 1 to add arrows to the connecting segments.
pointsize, textsize, segsize Control point, label, and segment sizes.
p_col1, p_col2 Colors for the two point groups.
col_seg1, col_seg2 Segment colors by direction.
expandx, expandy Expansion around the x- and y-axes.

Notes for package maintainers

These binaries (installable software) and packages are in development.
They may not be fully stable and should be used with caution. We make no claims about them.
Health stats visible at Monitor.