--- title: "Getting started with ggmeta" output: rmarkdown::html_vignette vignette: > %\VignetteIndexEntry{Getting started with ggmeta} %\VignetteEngine{knitr::rmarkdown} %\VignetteEncoding{UTF-8} --- ```{r, include = FALSE} knitr::opts_chunk$set( collapse = TRUE, comment = "#>", fig.width = 7, fig.height = 4.2, dpi = 96 ) has_meta <- requireNamespace("meta", quietly = TRUE) ``` **ggmeta** turns a meta-analysis into a publication-quality forest plot built on [ggplot2](https://ggplot2.tidyverse.org). It works two ways: * on a `meta` object (from the [meta](https://cran.r-project.org/package=meta) package), or * on a plain tidy data frame — no `meta` package required. Because the result is an ordinary `ggplot`, you keep the full ggplot2 toolbox: themes, scales, annotations, and saving with `ggsave()`. ```{r setup} library(ggmeta) library(ggplot2) ``` ## A forest plot from a `meta` object Fit a meta-analysis as usual, then hand it to `ggforest()`: ```{r meta-basic, eval = has_meta} library(meta) m <- metabin( event.e = c(14, 30, 15, 22), n.e = c(100, 150, 100, 120), event.c = c(10, 25, 12, 18), n.c = c(100, 150, 100, 120), studlab = c("Study A", "Study B", "Study C", "Study D"), sm = "RR" ) ggforest(m) ``` `ggforest()` does the sensible thing automatically: it draws study confidence intervals with weight-proportional squares, the common- and random-effects summary diamonds, a prediction interval, a null-effect reference line, a log x-axis for ratio measures, and a heterogeneity caption. ## Standalone: a tidy data frame You don't need the `meta` package. Any data frame with `studlab`, `estimate`, `ci_lower`, and `ci_upper` works: ```{r df-basic} df <- data.frame( studlab = c("Trial 1", "Trial 2", "Trial 3", "Trial 4"), estimate = c(0.82, 0.91, 0.68, 1.05), ci_lower = c(0.61, 0.74, 0.48, 0.80), ci_upper = c(1.10, 1.12, 0.96, 1.38) ) ggforest(df, null_effect = 1) ``` ### On-the-fly meta-analysis Give `ggforest()` a `se` column (or let it recover the standard error from the confidence interval) and set `add_summary = TRUE` to pool the studies with an inverse-variance common-effect and a DerSimonian–Laird random-effects model — without the `meta` package: ```{r df-pool} studies <- data.frame( studlab = c("Trial 1", "Trial 2", "Trial 3", "Trial 4", "Trial 5"), estimate = c(0.10, 0.35, 0.22, 0.48, 0.05), se = c(0.12, 0.10, 0.14, 0.16, 0.11) ) studies$ci_lower <- studies$estimate - 1.96 * studies$se studies$ci_upper <- studies$estimate + 1.96 * studies$se ggforest(studies, add_summary = TRUE) ``` ## A `meta::forest()`-style column table Set `columns = TRUE` to add the familiar effect / 95% CI / weight columns with headers to the right of the plot (use `effect_header` to name the estimate column, and pass a subset like `columns = c("estimate", "ci")` if you prefer): ```{r columns, fig.width = 9} ggforest(studies, add_summary = TRUE, columns = TRUE, effect_header = "SMD") ``` ## Custom text columns For a column of your own — sample sizes, events, anything — use `geom_forest_text()`, which aligns to the study rows through the shared `y`. `format_effect()` builds an "estimate (CI)" label. Widen the panel with `expand_limits()` to make room: ```{r text-cols, fig.width = 8.5} studies$n <- c(120, 240, 150, 180, 110) ggforest(studies, add_summary = TRUE) + geom_forest_text(aes(y = studlab, label = n), data = studies, x = -0.35, hjust = 0.5) + expand_limits(x = -0.45) ``` ## Journal styles Layout presets adapt a plot to common journal conventions. They are ordinary ggplot2 components, so you add them with `+`: ```{r layouts} p <- ggforest(df, null_effect = 1) layout_jama(p) ``` `layout_bmj()` and `layout_revman5()` are also available, and because the plot is a `ggplot` you can keep customising with `theme()`, `labs()`, and friends. ## Other effect measures `ggforest()` back-transforms every summary measure correctly — exponentiation for ratios, inverse-logit for logit proportions, Fisher's *z* for correlations, and so on. Single-group proportions and rates get no (meaningless) reference line: ```{r metaprop, eval = has_meta} prop <- metaprop( event = c(15, 20, 12, 25), n = c(50, 60, 55, 70), studlab = paste("Cohort", 1:4), sm = "PLOGIT" ) ggforest(prop) ``` ## Saving `ggforest()` returns a `ggplot`, so save it like any other: ```{r save, eval = FALSE} p <- ggforest(df, null_effect = 1) ggsave("forest.png", p, width = 7, height = 4, dpi = 300) ``` ## Where to next See `vignette("from-meta-forest")` for a side-by-side comparison with `meta::forest()` and tips on reproducing its output.