climniche compares current and projected climate at each
location with one current climatic niche reference. This vignette
defines that reference, the four reported quantities and the fitting and
projection workflow.
Current climatic niche reference
Let \(c_i\) and \(f_i\) denote current and projected climate at location \(i\). A non-negative weight \(w_i\) determines how much that location contributes to the current climatic niche reference. Its centre is
\[ \mu=\frac{\sum_i w_i c_i}{\sum_i w_i}. \]
Distance is measured under a positive semidefinite climatic metric \(A\):
\[ d_A(x,y)=\sqrt{(x-y)^\mathsf{T}A(x-y)}. \]
If \(r_{0i}=d_A(c_i,\mu)\), the weighted quantile
\[ B_q=Q_q^w(r_0) \]
defines the empirical radial boundary. The transformation, metric, centre and boundary are fitted from current climate and remain fixed when projected conditions are evaluated.
Reported quantities
At each location, climniche calculates
\[ \begin{aligned} D_i &= d_A(f_i,c_i),\\ R_i &= d_A(f_i,\mu)-d_A(c_i,\mu),\\ C_i &= \sqrt{\max(0,D_i^2-R_i^2)},\\ E_i &= \max(0,d_A(f_i,\mu)-B_q). \end{aligned} \]
Climatic Displacement (\(D_i\)) is the magnitude of local climatic change. Niche Distance Shift (\(R_i\)) is negative when projected climate moves towards the reference centre and positive when it moves away. Climatic Reconfiguration (\(C_i\)) describes displacement that is not expressed as a change in distance from the centre. The three quantities satisfy \(D_i^2=R_i^2+C_i^2\).
If \(r_{1i}=d_A(f_i,\mu)\) and \(\theta_i\) is the angle between the centred current and projected vectors, then
\[ C_i^2=2r_{0i}r_{1i}\{1-\cos(\theta_i)\}. \]
Climatic Reconfiguration is derived from Climatic Displacement and Niche Distance Shift. It is not a strict orthogonal projection or an independently estimated ecological process. Niche Boundary Exceedance (\(E_i\)) is separate from this decomposition and measures projected distance beyond \(B_q\).
Workflow
Every input interface follows four steps.
- Match current and projected climatic variables and locations, then convert occurrence, range or SDM data to non-negative reference weights.
- Fit preprocessing and standardisation to current climate, construct the climatic metric and estimate the weighted niche centre and boundary.
- Hold the fitted reference fixed while calculating the four quantities and climatic-variable contributions for projected conditions.
- Return location-level values, weighted summaries, maps and reports from the same fitted reference.
fit_climniche() accepts matrices and data frames.
fit_climniche_raster() accepts RasterLayer,
RasterStack and RasterBrick objects, whereas
fit_climniche_terra() accepts SpatRaster
objects. The current reference can also be fitted with
fit_climniche_reference() and reused with
project_climniche(). fit_climniche_series()
applies one fitted reference to an ordered set of projections.
library(climniche)
sim <- simulate_climniche(n = 200, p = 6, seed = 7)
fit <- fit_climniche(
current = sim[["current"]],
future = sim[["future_away"]],
occupied = sim[["occupied"]],
sensitivity = sim[["sensitivity"]]
)
head(climniche_table(fit))
#> cell occupied_weight current_niche_distance future_niche_distance
#> 1 3 1 1.859389 2.270787
#> 2 4 1 1.537120 1.933105
#> 3 6 1 2.031325 2.430480
#> 4 9 1 1.598781 1.990040
#> 5 17 1 1.944319 2.357542
#> 6 18 1 1.535579 1.947860
#> climate_change_amount niche_distance_change climate_reconfiguration
#> 1 0.4139168 0.4113980 0.04559401
#> 2 0.3988632 0.3959852 0.04782874
#> 3 0.4002497 0.3991546 0.02958838
#> 4 0.3939472 0.3912592 0.04594166
#> 5 0.4155508 0.4132233 0.04392064
#> 6 0.4143586 0.4122815 0.04143662
#> composition_change change_alignment niche_boundary_exceedance
#> 1 0.04559401 0.9939147 0.36874556
#> 2 0.04782874 0.9927844 0.03106366
#> 3 0.02958838 0.9972638 0.52843849
#> 4 0.04594166 0.9931767 0.08799862
#> 5 0.04392064 0.9943989 0.45550087
#> 6 0.04143662 0.9949873 0.04581913
#> outside_niche_exceedance current_niche_percentile future_niche_percentile
#> 1 0.36874556 0.8500000 1.0000000
#> 2 0.03106366 0.4166667 0.9666667
#> 3 0.52843849 1.0000000 1.0000000
#> 4 0.08799862 0.5166667 0.9833333
#> 5 0.45550087 0.9833333 1.0000000
#> 6 0.04581913 0.4000000 0.9833333
#> percentile_change radial_direction
#> 1 0.15000000 Away from realised niche centre
#> 2 0.55000000 Away from realised niche centre
#> 3 0.00000000 Away from realised niche centre
#> 4 0.46666667 Limited Niche Distance Shift
#> 5 0.01666667 Away from realised niche centre
#> 6 0.58333333 Away from realised niche centre
#> boundary_status
#> 1 Beyond empirical niche boundary
#> 2 Beyond empirical niche boundary
#> 3 Beyond empirical niche boundary
#> 4 Beyond empirical niche boundary
#> 5 Beyond empirical niche boundary
#> 6 Beyond empirical niche boundaryInterpreting equal climatic displacement
Four two-variable examples start one unit from a fixed centre. The towards and away examples have the same Climatic Displacement but opposite Niche Distance Shift. The fourth example changes climatic configuration while retaining the same niche distance.
current <- matrix(
rep(c(1, 0), 4),
ncol = 2,
byrow = TRUE,
dimnames = list(
c("unchanged", "towards centre", "away from centre", "same niche distance"),
c("climate 1", "climate 2")
)
)
future <- rbind(
unchanged = c(1, 0),
`towards centre` = c(0, 0),
`away from centre` = c(2, 0),
`same niche distance` = c(0, 1)
)
colnames(future) <- colnames(current)
geometry_fit <- fit_climniche(
current = current,
future = future,
occupied = rep(1, nrow(current)),
center = c(0, 0),
A = diag(2),
scale = FALSE,
preprocess = FALSE,
boundary = 0.95,
tolerance = 0
)
geometry_table <- data.frame(
path = rownames(current),
`Climatic Displacement` = geometry_fit[["climate_change_amount"]],
`Niche Distance Shift` = geometry_fit[["niche_distance_change"]],
`Climatic Reconfiguration` =
geometry_fit[["climate_reconfiguration"]],
`Niche Boundary Exceedance` =
geometry_fit[["niche_boundary_exceedance"]],
check.names = FALSE
)
knitr::kable(geometry_table, digits = 3)| path | Climatic Displacement | Niche Distance Shift | Climatic Reconfiguration | Niche Boundary Exceedance |
|---|---|---|---|---|
| unchanged | 0.000 | 0 | 0.000 | 0 |
| towards centre | 1.000 | -1 | 0.000 | 0 |
| away from centre | 1.000 | 1 | 0.000 | 1 |
| same niche distance | 1.414 | 0 | 1.414 | 0 |
The towards and away examples both have \(D_i=1\), with \(R_i=-1\) and \(R_i=1\), respectively. Moving to \((0,1)\) leaves niche distance unchanged, so \(R_i=0\) and all displacement is represented by Climatic Reconfiguration. Only the away example lies beyond the fitted boundary.
Using SDM outputs
Binary SDM output can define zero-one reference weights. Continuous
suitability values can remain continuous;
occupied_threshold sets values at or below a cutoff to zero
without converting larger values to one. These weights define how
current locations contribute to the climatic niche reference. They are
not a projected suitability response, and the four
climniche quantities remain distances and positions in
climatic space.