Skip to contents

Plotting with marea

A comprehensive guide to visualizing ecosystem data

Introduction

The marea package provides a unified plotting interface for ecosystem data in Atlantic Canada. This vignette demonstrates how to create effective visualizations using the built-in plotting functions and how to customize them for your specific needs.

Quick Start: Basic Plotting

All marea datasets work the same way - simply use the plot() function, the S3 plotting methods for the EA_data and EA_st classes will give you a default starting point.

# Load and plot North Atlantic Oscillation index
data(nao)
plot(nao)

Time Series Data: The ea_data Class

Available Plot Styles

The ea_data class supports several plotting styles:

Default Style

Basic line plot with points:

plot(nao, style = "default")

### Ribbon Style

Shows uncertainty bounds (requires lower and upper columns):

data("grey_seals")
plot(grey_seals, style = "ribbon")

Plain Style

Simple line without points:

plot(nao, style = "plain")

Anomaly Style

Bar plot with color-coded positive/negative values:

data(nao)

plot(nao, style = "anomaly")
#> Warning: Style 'anomaly' is intended for anomaly data, but data_type is: North
#> Atlantic Oscillation Index

Biomass Style

Special style for biomass data with bold lines and uncertainty:

plot(grey_seals, style = "biomass")
#> Warning: Style 'biomass' is intended for biomass data, but data_type is: Grey
#> Seal Abundance

Customizing Time Series Plots

Since all plots return ggplot2 objects, you can easily customize them:

# Start with base plot
p <- plot(nao, style = "plain")

# Add custom elements
p +
  geom_hline(yintercept = 0, linetype = "dashed", color = "red") +
  geom_smooth(method = "loess", se = TRUE, alpha = 0.3) +
  labs(
    title = "North Atlantic Oscillation Index",
    subtitle = "With trend line and zero reference",
    caption = "Data source: NOAA"
  ) +
  theme_minimal()

Working with subset of time series data

# Start with ea_data object
marea::azmp_bottom_temperature # this data contains time series bottom temperature for multiple regions

# filter bottom temperature for one region
bottom_temp_cs <- azmp_bottom_temperature[azmp_bottom_temperature@data$region == "Cabot Strait"]

# Add custom elements
plot(bottom_temp_cs) +
  labs(title = "Bottom Temperature for the Cabot Strait")

Working with Multiple Variables

Compare different indices:

# Load multiple climate indices
data(nao)
data(oni)

# Create comparison plot
nao_recent <- nao@data[nao@data$year >= 2000, ]
oni_recent <- oni@data[oni@data$year >= 2000 & oni@data$month == 1, ] # January only

# Combine data
combined_data <- data.frame(
  year = nao_recent$year,
  NAO = nao_recent$value,
  ONI = oni_recent$value[match(nao_recent$year, oni_recent$year)]
)

ea_df <- ea_data(
  data = combined_data,
  value_col = "NAO",
  data_type = "Climate Indices Comparison",
  region = "North Atlantic",
  location_descriptor = "Global",
  units = "Index Value"
)

plot(ea_df, style = "default") +
  geom_line(aes(y = ONI), color = "blue") +
  labs(
    title = "Climate Indices: NAO vs ONI",
    y = "Index Value",
    x = "Year"
  ) +
  theme_minimal()

Spatial Data: The ea_spatial Class

Spatial data in marea is represented by the ea_spatial class, which allows for visualizing geographic data such as temperature, salinity, and other oceanographic variables.

Loading and subsetting spatial data

data(glorys_bottom_temperature)
glorys_2024 <- ea.subset.spatial(glorys_bottom_temperature, "year", 2024)

Available Spatial Plot Styles

Fill Style

Color-coded spatial maps:

plot(glorys_2024, style = "fill")

Contour Style

Contour lines showing value gradients:

plot(glorys_2024, style = "contour")

Customizing Spatial Maps

Add coastlines and improve styling:

p <- plot(glorys_2024, style = "fill")

# Customize the map
p +
  scale_fill_viridis_c(name = "Temperature\n(°C)") +
  labs(
    title = "Bottom Temperature in the Maritimes Region",
    subtitle = "GLORYS Reanalysis Data"
  ) +
  theme_void() +
  theme(
    legend.position = "bottom",
    legend.key.width = unit(1.5, "cm")
  )

Temporal Filtering for Spatial Data

Filter spatial data by time periods:

# Filter for specific months if time dimension exists
winter_data <- glorys_2024[
  glorys_2024@data$month %in% c(12, 1, 2),
]

plot(winter_data, style = "fill") +
  labs(title = "2024 Winter Bottom Temperature")

Specialized Visualizations

Climate Index Comparisons

Create correlation plots:

# Example correlation plot (if sufficient data overlap exists)
recent_nao <- ea.subset(nao, "year", c(1990:2024))

# Add trend analysis
p <- plot(recent_nao, style = "plain") +
  labs(x = "Year", y = "NAO Index") +
  ggtitle("NAO Index Over Time (1990 - Present)")

# Add regression line
lm_fit <- lm(value ~ year, data = recent_nao@data)
p <- p +
  geom_smooth(method = "lm", se = FALSE, color = "red", linetype = "dashed") +
  theme_minimal()

# Add text with trend
slope <- round(coef(lm_fit)[2], 4)

p <- p +
  geom_text(
    aes(
      x = 2000, y = max(recent_nao@data$value),
      label = paste("Trend:", slope, "per year")
    ),
    color = "red", hjust = 0
  )

print(p)

Multi-panel Comparisons

This example shows how to compare multiple datasets side by side using base R graphics. This is useful for visualizing trends across different datasets in a single view.

Compare different datasets side by side:

# Create a multi-panel plot
par(mfrow = c(2, 2))

# Panel 1: NAO
plot(nao@data$year, nao@data$value,
  type = "l",
  main = "North Atlantic Oscillation",
  xlab = "Year", ylab = "Index"
)

# Panel 2: Grey Seals
plot(grey_seals@data$year, grey_seals@data$value,
  type = "l",
  main = "Grey Seal Abundance",
  xlab = "Year", ylab = "Count"
)

# Panel 3: ONI (subset)
oni_subset <- oni@data[oni@data$month == 1, ] # January only
plot(oni_subset$year, oni_subset$value,
  type = "l",
  main = "Oceanic Niño Index (January)",
  xlab = "Year", ylab = "Temperature Anomaly (°C)"
)

# Panel 4: Bottom Temperature
if (exists("azmp_bottom_temperature")) {
  data(azmp_bottom_temperature)
  bottom_temp_eb <- azmp_bottom_temperature[azmp_bottom_temperature@data$region == "Emerald Basin"]
  plot(bottom_temp_eb@data$year, bottom_temp_eb@data$value,
    type = "p",
    main = "Emerald Basin Bottom Temperature",
    xlab = "Year", ylab = "Temperature (°C)"
  )
}

# Reset to single panel
par(mfrow = c(1, 1))

You can also use patchwork:

# Panel 1: NAO
p1 <- plot(nao) +
  labs(title = "NAO") +
  ylab("NAO")

# Panel 2: Grey Seals
p2 <- plot(grey_seals) +
  labs(title = "Grey seals") +
  ylab("abundance")

# Panel 3: ONI (subset)
oni_subset <- oni[oni@data$month == 1] # January only
p3 <- plot(oni_subset) +
  labs(title = "ONI") +
  ylab("ONI")

# Panel 4: Bottom Temperature
bottom_temp_eb <- azmp_bottom_temperature[azmp_bottom_temperature@data$region == "Emerald Basin"]
p4 <- plot(bottom_temp_eb) +
  labs(title = "Emerald Basin") +
  ylab("bottom temp (degC)")

# Reset to single panel
require(patchwork)

(p1 + p2) / (p3 + p4)

Advanced Customization

Since our ea class objectse are consistent in their structure and naming, it is easier for you to create your own custom function as well.

Plotting functions can be a great way to produce publication quality plots with consistnet theme and colour elements.

Custom Color Schemes

Apply custom color palettes:

# Custom color scheme for temperature data
custom_temp_plot <- function(data_obj) {
  p <- plot(data_obj, style = "fill")

  p +
    scale_fill_gradient2(
      low = "blue", mid = "white", high = "red",
      midpoint = mean(data_obj@data$value, na.rm = TRUE),
      name = "Temperature\n(°C)"
    ) +
    theme_minimal()
}

# Apply to spatial data
if (exists("glorys_2024")) {
  custom_temp_plot(glorys_2024)
}

Adding Annotations

Add reference lines and annotations:

p <- plot(nao, style = "default")

p +
  geom_hline(yintercept = c(-1, 1), linetype = "dashed", alpha = 0.5) +
  annotate("text",
    x = 1960, y = 1.2, label = "Positive phase",
    hjust = 0, size = 3
  ) +
  annotate("text",
    x = 1960, y = -1.2, label = "Negative phase",
    hjust = 0, size = 3
  ) +
  labs(
    title = "North Atlantic Oscillation with Phase Indicators",
    caption = "Dashed lines show ±1 standard deviation"
  )

Working with Uncertainty

Confidence Intervals

Display and customize uncertainty bounds:

# Plot with custom confidence styling
p <- plot(grey_seals, style = "default")

p +
  geom_ribbon(aes(ymin = lower, ymax = upper), alpha = 0.3, fill = "lightblue") +
  geom_line(color = "darkblue") +
  geom_point(color = "darkblue") +
  labs(
    title = "Grey Seal Abundance with 95% Confidence Intervals",
    y = "Abundance (thousands)"
  ) +
  theme_bw()

Export and Saving

High-Quality Output

Save plots for publications:

# Create publication-ready plot
pub_plot <- plot(grey_seals, style = "ribbon") +
  labs(
    title = "Grey Seal Population Trends",
    subtitle = "Sable Island, Nova Scotia",
    x = "Year",
    y = "Estimated Abundance (thousands)",
    caption = "Data source: DFO Science"
  ) +
  theme_bw() +
  theme(
    plot.title = element_text(size = 14, face = "bold"),
    plot.subtitle = element_text(size = 12),
    axis.title = element_text(size = 12),
    axis.text = element_text(size = 10)
  )

# Save as high-resolution PNG
ggsave("grey_seals_trends.png", pub_plot,
  width = 8, height = 6, dpi = 300
)

# Save as PDF for vector graphics
ggsave("grey_seals_trends.pdf", pub_plot,
  width = 8, height = 6
)

Tips and best practices

  1. Check Data structure first
# Always inspect your data first
ea.print(nao)
ea.summary(nao)
str(nao@data)
  1. Use Appropriate Styles
  • Time series: Use “default” or “ribbon” for most cases
  • Anomalies: Use “anomaly” style for climate indices
  • Biomass: Use “biomass” style for population data
  • Spatial: Use “fill” for continuous fields, “bubble” for point data
  1. Customize gradually
# Start simple
p1 <- plot(nao)

# Add one element at a time
p2 <- p1 + theme_minimal()
p3 <- p2 + labs(title = "Custom Title")
p4 <- p3 + geom_smooth(method = "loess", se = FALSE)

# Final result
p4
#> `geom_smooth()` using formula = 'y ~ x'

  1. Consistent styling
# Create a custom theme for all your plots
my_theme <- theme_bw() +
  theme(
    plot.title = element_text(size = 14, face = "bold", colour = "darkblue"),
    axis.title = element_text(size = 12),
    legend.position = "bottom"
  )

# Apply to any plot
plot(nao) + my_theme

Getting Help

Plot Method Documentation

# Get help on plotting functions
?`plot,ea_data,missing-method`
?`plot,ea_spatial,missing-method`

Citation

# Cite the package in your work
citation("marea")
#> To cite marea in publications use:
#> 
#>   Jamie C. Tam, Benoit Casault, Stephanie Clay et al. (). marea:
#>   Maritime Ecosystem Approach R Package. R package version 1.0.0.9000.
#>   https://doi.org/10.5281/zenodo.15706086
#> 
#> A BibTeX entry for LaTeX users is
#> 
#>   @Manual{,
#>     title = {marea: Maritime Ecosystem Approach R Package},
#>     author = {Jamie C. Tam and Benoit Casault and Stephanie Clay and Adam Cook and Remi Daigle and Andrew M. Edwards and Jaimie Harbin and Brad Hubley and Keith David and Mike McMahon and Emily A. O'Grady},
#>     note = {R package version 1.0.0.9000},
#>     url = {https://github.com/MarEcosystemApproaches/marea},
#>     doi = {10.5281/zenodo.15706086},
#>   }
#> 
#> We appreciate citations as they help us secure funding for continued
#> development.