lcmsPlot is a Bioconductor package and to install it we
have to use BiocManager.
The dataset used in this vignette originates from a prepared sample spiked with known standards, specifically L-Proline and L-Kynurenine. These compounds are highlighted throughout the vignette and serve as concrete examples to illustrate the different steps of the workflow.
To support reproducibility and hands-on exploration, example data
files are provided in inst/extdata/standards-mzml.zip.
Two types of files are included:
library(lcmsPlot)
exdir <- tempdir()
# Unzip the file containing the mzML files
utils::unzip(
system.file("extdata", "standards-mzml.zip", package = "lcmsPlot"),
exdir = exdir
)
mzml_dir <- file.path(exdir, "mzml")
samples_metadata <- data.frame(
sample_id = c(
"l-proline-MS1",
"l-proline-MS2",
"l-kynurenine-MS1",
"l-kynurenine-MS2"),
sample_name = c(rep("L-Proline", 2), rep("L-Kynurenine", 2)),
ms_level = c(1, 2, 1, 2)
)The following figure illustrates the presence of the two spiked standards, L-Proline and L-Kynurenine, in the MS1-only samples. For each compound, an extracted ion chromatogram is generated using its expected m/z value and retention time, with narrow tolerances to precisely capture the corresponding signal.
ms1_samples_metadata <- samples_metadata |> dplyr::filter(ms_level == 1)
ms1_raw_files <- file.path(
mzml_dir,
paste0(ms1_samples_metadata$sample_id, ".mzML"))
lcmsPlot(ms1_raw_files, metadata = ms1_samples_metadata) +
lp_chromatogram(
features = data.frame(
sample_id = c("l-proline-MS1", "l-kynurenine-MS1"),
mz = c(116.0703793, 209.091824),
rt = c(425.74, 365.72)
),
ppm = 5,
rt_tol = 5
) +
lp_facets(facets = "sample_name", free_x = TRUE, ncol = 2)Next, we plot the chromatograms together with their corresponding MS2 spectra, extracted from the scan closest to the specified retention time for each compound. This allows direct inspection of both chromatographic behavior and fragmentation patterns in a single visualization.
ms2_samples_metadata <- samples_metadata |> dplyr::filter(ms_level == 2)
ms2_raw_files <- file.path(
mzml_dir,
paste0(ms2_samples_metadata$sample_id, ".mzML"))
lcmsPlot(ms2_raw_files, metadata = ms2_samples_metadata) +
lp_chromatogram(
features = data.frame(
sample_id = c("l-proline-MS2", "l-kynurenine-MS2"),
mz = c(116.0703793, 209.091824),
rt = c(425.74, 365.72)
),
ppm = 5,
rt_tol = 5
) +
lp_spectra(
rt = c("l-proline-MS2" = 425.74, "l-kynurenine-MS2" = 365.72),
mode = "closest",
ms_level = 2) +
lp_facets(facets = "sample_name", free_x = TRUE, ncol = 2)lp_theme() styles every panel of a plot as part of the
pipeline. Its preset sets the overall look:
"minimal" (the default), "classic", or
"publication", which has a white background, axis lines, no
minor grid lines, and an 8 pt base font sized for print. Its
palette colours the series: the default
"okabe_ito" palette stays distinguishable under the common
forms of colour blindness and falls back to viridis when there are more
than 8 groups; "viridis" and "ggplot2" are
also available. base_size and line_width scale
the text and the lines.
lcmsPlot(ms1_raw_files, metadata = ms1_samples_metadata) +
lp_chromatogram(
features = data.frame(
sample_id = c("l-proline-MS1", "l-kynurenine-MS1"),
mz = c(116.0703793, 209.091824),
rt = c(425.74, 365.72)
),
ppm = 5,
rt_tol = 5
) +
lp_arrange(group_by = "sample_name") +
lp_facets(facets = "sample_name", free_x = TRUE, ncol = 2) +
lp_theme(preset = "publication", base_size = 12, line_width = 0.6)A named vector of colours maps each group to the colour of your choice, for example to match the rest of a manuscript. Highlighted peaks take the colour of their trace.
lcmsPlot(ms1_raw_files, metadata = ms1_samples_metadata) +
lp_chromatogram(
features = data.frame(
sample_id = c("l-proline-MS1", "l-kynurenine-MS1"),
mz = c(116.0703793, 209.091824),
rt = c(425.74, 365.72)
),
ppm = 5,
rt_tol = 5
) +
lp_arrange(group_by = "sample_name") +
lp_facets(facets = "sample_name", free_x = TRUE, ncol = 2) +
lp_theme(
preset = "classic",
palette = c("L-Proline" = "#0072B2", "L-Kynurenine" = "#D55E00"))For full control, you can customise the appearance of your plots by
modifying the underlying ggplot2 object. To do this, simply
extract the plot using the lp_get_plot() function, which
returns the raw ggplot2 object, and then apply any desired
theme settings. This gives you complete flexibility to tailor the
visualisation to your needs; for example, adjusting fonts, colors,
backgrounds, grid lines, or margins. By leveraging custom themes, you
can ensure consistency with your project/manuscript’s style guidelines,
improve readability, or highlight specific aspects of your data.
Firstly, define the custom theme using the ggplot2
theme function:
my_custom_theme <- function() {
ggplot2::theme(
# Title
plot.title = ggplot2::element_text(
size = 16,
margin = ggplot2::margin(b = 15)),
# Axis labels
axis.title = ggplot2::element_text(
size = 11,
face = "bold",
color = "#1d293d"),
# Facet strip
strip.text = ggplot2::element_text(
color = "#1d293d",
size = 9,
hjust = 0,
margin = ggplot2::margin(t = 3, r = 10, b = 6, l = 10)
),
strip.background = ggplot2::element_rect(
color = "#90a1b9",
fill = "#e2e8f0",
linewidth = 0.8),
# Box around the panel
panel.border = ggplot2::element_rect(
color = "#90a1b9",
fill = NA,
linewidth = 1),
# Customize grid lines inside the plot
panel.grid.major = ggplot2::element_line(
color = "#e2e8f0",
linewidth = 0.5),
panel.grid.minor = ggplot2::element_line(
color = "#e2e8f0",
linewidth = 0.5)
)
}Generate the plot with lcmsPlot, retrieve the underlying
plot object using lp_get_plot(), and then apply the custom
theme:
lcmsPlot(ms1_raw_files, metadata = ms1_samples_metadata) +
lp_chromatogram(
features = data.frame(
sample_id = c("l-proline-MS1", "l-kynurenine-MS1"),
mz = c(116.0703793, 209.091824),
rt = c(425.74, 365.72)
),
ppm = 5,
rt_tol = 5
) +
lp_facets(facets = "sample_name", free_x = TRUE, ncol = 2) +
lp_get_plot() +
my_custom_theme()sessionInfo()
#> R version 4.6.1 (2026-06-24)
#> Platform: x86_64-pc-linux-gnu
#> Running under: Ubuntu 26.04.1 LTS
#>
#> Matrix products: default
#> BLAS: /usr/lib/x86_64-linux-gnu/openblas-pthread/libblas.so.3
#> LAPACK: /usr/lib/x86_64-linux-gnu/openblas-pthread/libopenblasp-r0.3.32.so; LAPACK version 3.12.0
#>
#> locale:
#> [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C
#> [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8
#> [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8
#> [7] LC_PAPER=en_US.UTF-8 LC_NAME=C
#> [9] LC_ADDRESS=C LC_TELEPHONE=C
#> [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C
#>
#> time zone: Etc/UTC
#> tzcode source: system (glibc)
#>
#> attached base packages:
#> [1] stats graphics grDevices utils datasets methods base
#>
#> other attached packages:
#> [1] lcmsPlot_1.1.21 BiocStyle_2.41.0
#>
#> loaded via a namespace (and not attached):
#> [1] tidyselect_1.2.1 dplyr_1.2.1
#> [3] farver_2.1.2 S7_0.2.2
#> [5] fastmap_1.2.0 lazyeval_0.2.3
#> [7] digest_0.6.39 lifecycle_1.0.5
#> [9] cluster_2.1.8.3 ProtGenerics_1.45.0
#> [11] magrittr_2.0.5 compiler_4.6.1
#> [13] rlang_1.3.0 sass_0.4.10
#> [15] tools_4.6.1 igraph_2.3.4
#> [17] yaml_2.3.12 data.table_1.18.6.1
#> [19] knitr_1.52 labeling_0.4.3
#> [21] S4Arrays_1.13.2 DelayedArray_0.39.8
#> [23] plyr_1.8.9 RColorBrewer_1.1-3
#> [25] abind_1.4-8 BiocParallel_1.47.0
#> [27] withr_3.0.3 purrr_1.2.2
#> [29] BiocGenerics_0.59.12 sys_3.4.3
#> [31] grid_4.6.1 stats4_4.6.1
#> [33] ggplot2_4.0.3 scales_1.4.0
#> [35] MASS_7.3-66 MultiAssayExperiment_1.39.1
#> [37] SummarizedExperiment_1.43.0 cli_3.6.6
#> [39] mzR_2.47.1 rmarkdown_2.32
#> [41] generics_0.1.4 otel_0.2.0
#> [43] rawrr_1.21.0 reshape2_1.4.5
#> [45] ncdf4_1.24 DBI_1.3.0
#> [47] cachem_1.1.0 stringr_1.6.0
#> [49] parallel_4.6.1 AnnotationFilter_1.37.0
#> [51] BiocManager_1.30.27 XVector_0.53.0
#> [53] matrixStats_1.5.0 vctrs_0.7.3
#> [55] Matrix_1.7-6 jsonlite_2.0.0
#> [57] patchwork_1.3.2 IRanges_2.47.5
#> [59] S4Vectors_0.51.10 MsExperiment_1.15.0
#> [61] clue_0.3-68 maketools_1.3.2
#> [63] jquerylib_0.1.4 tidyr_1.3.2
#> [65] glue_1.8.1 codetools_0.2-20
#> [67] QFeatures_1.23.2 Spectra_1.23.6
#> [69] stringi_1.8.9 gtable_0.3.6
#> [71] GenomicRanges_1.65.4 tibble_3.3.1
#> [73] pillar_1.11.1 htmltools_0.5.9
#> [75] Seqinfo_1.3.2 R6_2.6.1
#> [77] evaluate_1.0.5 Biobase_2.73.2
#> [79] lattice_0.23-1 Chromatograms_1.3.5
#> [81] bslib_0.12.0 MetaboCoreUtils_1.21.2
#> [83] Rcpp_1.1.2 SparseArray_1.13.4
#> [85] xfun_0.62 MsCoreUtils_1.25.4
#> [87] fs_2.1.0 MatrixGenerics_1.25.0
#> [89] buildtools_1.0.0 pkgconfig_2.0.3