Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion geo-benches/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ num-traits = "0.2"
pretty_env_logger = "0.4"
rand = "0.10.0"
rand_distr = "0.6.0"
rstar = "0.12.0"
rstar = "0.13.0"
serde = "1.0.137"
serde_derive = "1.0.137"
serde_json = "1.0.81"
Expand Down
4 changes: 4 additions & 0 deletions geo-types/CHANGES.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# Changes

## Unreleased

- Add support for `rstar` 0.13 via the `rstar_0_13` feature, alongside the existing `rstar` versions.

## 0.7.19 - 2026-04-15

- POSSIBLY BREAKING: `Triangle::from([a, b, c])` now enforces CCW winding (same as `Triangle::new`).
Expand Down
4 changes: 3 additions & 1 deletion geo-types/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,15 @@ edition = "2021"
default = ["std"]
std = ["approx?/std", "num-traits/std", "serde?/std"]
multithreading = ["rayon"]
serde = [ "dep:serde", "rstar_0_8?/serde", "rstar_0_9?/serde", "rstar_0_10?/serde", "rstar_0_11?/serde", "rstar_0_12?/serde"]
serde = [ "dep:serde", "rstar_0_8?/serde", "rstar_0_9?/serde", "rstar_0_10?/serde", "rstar_0_11?/serde", "rstar_0_12?/serde", "rstar_0_13?/serde"]

rstar = ["rstar_0_8"]
rstar_0_8 = ["dep:rstar_0_8", "approx"]
rstar_0_9 = ["dep:rstar_0_9", "approx"]
rstar_0_10 = ["dep:rstar_0_10", "approx"]
rstar_0_11 = ["dep:rstar_0_11", "approx"]
rstar_0_12 = ["dep:rstar_0_12", "approx"]
rstar_0_13 = ["dep:rstar_0_13", "approx"]

# Deprecated feature flags with "use-" prefix from the days before `dep:`
use-rstar = ["rstar"]
Expand All @@ -43,6 +44,7 @@ rstar_0_9 = { package = "rstar", version = "0.9", optional = true }
rstar_0_10 = { package = "rstar", version = "0.10", optional = true }
rstar_0_11 = { package = "rstar", version = "0.11", optional = true }
rstar_0_12 = { package = "rstar", version = "0.12", optional = true }
rstar_0_13 = { package = "rstar", version = "0.13", optional = true }
serde = { version = "1", optional = true, default-features = false, features = ["alloc", "derive"] }
spade_2 = { package = "spade", version = "2", optional = true }

Expand Down
36 changes: 36 additions & 0 deletions geo-types/src/geometry/coord.rs
Original file line number Diff line number Diff line change
Expand Up @@ -503,6 +503,42 @@ where
}
}

#[cfg(feature = "rstar_0_13")]
impl<T> ::rstar_0_13::Point for Coord<T>
where
T: ::num_traits::Float + ::rstar_0_13::RTreeNum,
{
type Scalar = T;

const DIMENSIONS: usize = 2;

#[inline]
fn generate(mut generator: impl FnMut(usize) -> Self::Scalar) -> Self {
coord! {
x: generator(0),
y: generator(1),
}
}

#[inline]
fn nth(&self, index: usize) -> Self::Scalar {
match index {
0 => self.x,
1 => self.y,
_ => unreachable!(),
}
}

#[inline]
fn nth_mut(&mut self, index: usize) -> &mut Self::Scalar {
match index {
0 => &mut self.x,
1 => &mut self.y,
_ => unreachable!(),
}
}
}

#[cfg(feature = "spade_2")]
impl<T> ::spade_2::HasPosition for Coord<T>
where
Expand Down
6 changes: 5 additions & 1 deletion geo-types/src/geometry/line.rs
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,8 @@ mod approx_integration {
feature = "rstar_0_9",
feature = "rstar_0_10",
feature = "rstar_0_11",
feature = "rstar_0_12"
feature = "rstar_0_12",
feature = "rstar_0_13"
))]
macro_rules! impl_rstar_line {
($rstar:ident) => {
Expand Down Expand Up @@ -289,6 +290,9 @@ impl_rstar_line!(rstar_0_11);
#[cfg(feature = "rstar_0_12")]
impl_rstar_line!(rstar_0_12);

#[cfg(feature = "rstar_0_13")]
impl_rstar_line!(rstar_0_13);

#[cfg(test)]
mod test {
use super::*;
Expand Down
6 changes: 5 additions & 1 deletion geo-types/src/geometry/line_string.rs
Original file line number Diff line number Diff line change
Expand Up @@ -542,7 +542,8 @@ mod approx_integration {
feature = "rstar_0_9",
feature = "rstar_0_10",
feature = "rstar_0_11",
feature = "rstar_0_12"
feature = "rstar_0_12",
feature = "rstar_0_13"
))]
macro_rules! impl_rstar_line_string {
($rstar:ident) => {
Expand Down Expand Up @@ -599,6 +600,9 @@ impl_rstar_line_string!(rstar_0_11);
#[cfg(feature = "rstar_0_12")]
impl_rstar_line_string!(rstar_0_12);

#[cfg(feature = "rstar_0_13")]
impl_rstar_line_string!(rstar_0_13);

#[cfg(test)]
mod test {
use super::*;
Expand Down
5 changes: 4 additions & 1 deletion geo-types/src/geometry/multi_polygon.rs
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,8 @@ mod approx_integration {
feature = "rstar_0_9",
feature = "rstar_0_10",
feature = "rstar_0_11",
feature = "rstar_0_12"
feature = "rstar_0_12",
feature = "rstar_0_13"
))]
macro_rules! impl_rstar_multi_polygon {
($rstar:ident) => {
Expand Down Expand Up @@ -275,6 +276,8 @@ impl_rstar_multi_polygon!(rstar_0_10);
impl_rstar_multi_polygon!(rstar_0_11);
#[cfg(feature = "rstar_0_12")]
impl_rstar_multi_polygon!(rstar_0_12);
#[cfg(feature = "rstar_0_13")]
impl_rstar_multi_polygon!(rstar_0_13);

#[cfg(test)]
mod test {
Expand Down
29 changes: 29 additions & 0 deletions geo-types/src/geometry/point.rs
Original file line number Diff line number Diff line change
Expand Up @@ -784,6 +784,35 @@ where
}
}

#[cfg(feature = "rstar_0_13")]
impl<T> ::rstar_0_13::Point for Point<T>
where
T: ::num_traits::Float + ::rstar_0_13::RTreeNum,
{
type Scalar = T;

const DIMENSIONS: usize = 2;

fn generate(mut generator: impl FnMut(usize) -> Self::Scalar) -> Self {
Point::new(generator(0), generator(1))
}

fn nth(&self, index: usize) -> Self::Scalar {
match index {
0 => self.0.x,
1 => self.0.y,
_ => unreachable!(),
}
}
fn nth_mut(&mut self, index: usize) -> &mut Self::Scalar {
match index {
0 => &mut self.0.x,
1 => &mut self.0.y,
_ => unreachable!(),
}
}
}

impl<T: CoordNum> AsRef<Coord<T>> for Point<T> {
fn as_ref(&self) -> &Coord<T> {
&self.0
Expand Down
6 changes: 5 additions & 1 deletion geo-types/src/geometry/polygon.rs
Original file line number Diff line number Diff line change
Expand Up @@ -651,7 +651,8 @@ mod approx_integration {
feature = "rstar_0_9",
feature = "rstar_0_10",
feature = "rstar_0_11",
feature = "rstar_0_12"
feature = "rstar_0_12",
feature = "rstar_0_13"
))]
macro_rules! impl_rstar_polygon {
($rstar:ident) => {
Expand Down Expand Up @@ -683,6 +684,9 @@ impl_rstar_polygon!(rstar_0_11);
#[cfg(feature = "rstar_0_12")]
impl_rstar_polygon!(rstar_0_12);

#[cfg(feature = "rstar_0_13")]
impl_rstar_polygon!(rstar_0_13);

#[cfg(test)]
mod tests {
use super::*;
Expand Down
6 changes: 5 additions & 1 deletion geo-types/src/geometry/triangle.rs
Original file line number Diff line number Diff line change
Expand Up @@ -235,7 +235,8 @@ mod approx_integration {
feature = "rstar_0_9",
feature = "rstar_0_10",
feature = "rstar_0_11",
feature = "rstar_0_12"
feature = "rstar_0_12",
feature = "rstar_0_13"
))]
macro_rules! impl_rstar_triangle {
($rstar:ident) => {
Expand Down Expand Up @@ -268,3 +269,6 @@ impl_rstar_triangle!(rstar_0_11);

#[cfg(feature = "rstar_0_12")]
impl_rstar_triangle!(rstar_0_12);

#[cfg(feature = "rstar_0_13")]
impl_rstar_triangle!(rstar_0_13);
19 changes: 18 additions & 1 deletion geo-types/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@
//! - `use-rstar_0_10`: Allows geometry types to be inserted into [rstar] R*-trees (`rstar v0.10`)
//! - `use-rstar_0_11`: Allows geometry types to be inserted into [rstar] R*-trees (`rstar v0.11`)
//! - `use-rstar_0_12`: Allows geometry types to be inserted into [rstar] R*-trees (`rstar v0.12`)
//! - `rstar_0_13`: Allows geometry types to be inserted into [rstar] R*-trees (`rstar v0.13`)
//!
//! This library can be used in `#![no_std]` environments if the default `std` feature is disabled. At
//! the moment, the `arbitrary` and `use-rstar_0_8` features require `std`. This may change in a
Expand Down Expand Up @@ -144,7 +145,8 @@ mod arbitrary;
feature = "rstar_0_9",
feature = "rstar_0_10",
feature = "rstar_0_11",
feature = "rstar_0_12"
feature = "rstar_0_12",
feature = "rstar_0_13"
))]
#[doc(hidden)]
pub mod private_utils;
Expand Down Expand Up @@ -388,6 +390,21 @@ mod tests {
assert_relative_eq!(25.999999999999996, l.distance_2(&Point::new(4.0, 10.0)));
}

#[cfg(feature = "rstar_0_13")]
#[test]
/// ensure Line's SpatialObject impl is correct
fn line_test_0_13() {
use rstar_0_13::primitives::Line as RStarLine;
use rstar_0_13::{PointDistance, RTreeObject};

let rl = RStarLine::new(Point::new(0.0, 0.0), Point::new(5.0, 5.0));
let l = Line::new(coord! { x: 0.0, y: 0.0 }, coord! { x: 5., y: 5. });
assert_eq!(rl.envelope(), l.envelope());
// difference in 15th decimal place
assert_relative_eq!(26.0, rl.distance_2(&Point::new(4.0, 10.0)));
assert_relative_eq!(25.999999999999996, l.distance_2(&Point::new(4.0, 10.0)));
}

#[test]
fn test_rects() {
let r = Rect::new(coord! { x: -1., y: -1. }, coord! { x: 1., y: 1. });
Expand Down
1 change: 1 addition & 0 deletions geo/CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

## Unreleased

- Update the `rstar` dependency to 0.13.
- Unpin the `earcut` dependency now that the upstream semver violation has been reverted.
- <https://github.com/georust/geo/pull/1533>
- Added `Earcutter` and `TriangulateEarcut::earcut_triangulation_ref` to avoid per-call memory allocations across multiple triangulations.
Expand Down
4 changes: 2 additions & 2 deletions geo/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -31,13 +31,13 @@ __allow_deprecated_features = []
earcut = { version = "0.4.9", optional = true }
spade = { version = "2.10.0", optional = true }
float_next_after = "2.0.0"
geo-types = { version = "0.7.19", features = ["approx", "rstar_0_12"] }
geo-types = { version = "0.7.19", features = ["approx", "rstar_0_13"] }
geographiclib-rs = { version = "0.2.3", default-features = false }
log = "0.4.11"
num-traits = "0.2"
proj = { version = "0.31.0", optional = true }
robust = "1.1.0"
rstar = "0.12.0"
rstar = "0.13.0"
serde = { version = "1.0", optional = true, features = ["derive"] }
i_overlay = { version = "4.5.1, < 4.6.0", default-features = false }
sif-itree = "0.4.0"
Expand Down
10 changes: 7 additions & 3 deletions geo/src/algorithm/concave_hull.rs
Original file line number Diff line number Diff line change
Expand Up @@ -366,7 +366,7 @@ where
let bbox = AABB::from_corners(point!([min_x, min_y]), point!([max_x, max_y]));

// Iterate over all lines in the hull which intersect with the bounding box
let hull_lines = current_hull_tree.locate_in_envelope_intersecting(&bbox);
let hull_lines = current_hull_tree.locate_in_envelope_intersecting(bbox);
for hull_line in hull_lines {
// Skip lines which share an endpoint
if hull_line.start == line.start
Expand Down Expand Up @@ -633,7 +633,7 @@ where
#[cfg(test)]
mod tests {
use super::*;
use crate::{coord, line_string, polygon};
use crate::{Relate, coord, line_string, polygon};

#[test]
fn test_concavity() {
Expand Down Expand Up @@ -723,6 +723,10 @@ mod tests {
]
.into();
let hull = mp.concave_hull();
// The bottom edge runs straight from (0, 0) to (4, 0). The intermediate
// points (2, 0) and (3, 0) are collinear, so whether they are retained as
// explicit vertices depends on R-tree iteration order, which changed in
// rstar 0.13. Compare topologically rather than by exact vertex list.
let correct_hull = polygon![
(x: 4.0, y: 0.0),
(x: 4.0, y: 5.0),
Expand All @@ -734,7 +738,7 @@ mod tests {
(x: 3.0, y: 0.0),
(x: 4.0, y: 0.0),
];
assert_eq!(hull, correct_hull);
assert!(hull.relate(&correct_hull).is_equal_topo());
}

#[test]
Expand Down
4 changes: 2 additions & 2 deletions geo/src/algorithm/euclidean_distance.rs
Original file line number Diff line number Diff line change
Expand Up @@ -500,12 +500,12 @@ where
geom2
.points()
.fold(<T as Bounded>::max_value(), |acc, point| {
let nearest = tree_a.nearest_neighbor(&point).unwrap();
let nearest = tree_a.nearest_neighbor(point).unwrap();
#[allow(deprecated)]
acc.min(nearest.euclidean_distance(&point))
})
.min(geom1.points().fold(Bounded::max_value(), |acc, point| {
let nearest = tree_b.nearest_neighbor(&point).unwrap();
let nearest = tree_b.nearest_neighbor(point).unwrap();
#[allow(deprecated)]
acc.min(nearest.euclidean_distance(&point))
}))
Expand Down
4 changes: 2 additions & 2 deletions geo/src/algorithm/k_nearest_concave_hull.rs
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ where
{
let mut dataset: rstar::RTree<Coord<T>> = rstar::RTree::new();
for coord in coords {
let closest = dataset.nearest_neighbor(coord);
let closest = dataset.nearest_neighbor(*coord);
if let Some(closest) = closest
&& coords_are_equal(coord, closest)
{
Expand Down Expand Up @@ -257,7 +257,7 @@ where
T: GeoFloat + RTreeNum,
{
dataset
.nearest_neighbor_iter(base_coord)
.nearest_neighbor_iter(*base_coord)
.take(candidate_no as usize)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -448,11 +448,11 @@ fn nearest_neighbour_distance<F: GeoFloat>(geom1: &LineString<F>, geom2: &LineSt
geom2
.points()
.fold(Bounded::max_value(), |acc: F, point| {
let nearest = tree_a.nearest_neighbor(&point).unwrap();
let nearest = tree_a.nearest_neighbor(point).unwrap();
acc.min(Euclidean.distance(nearest as &Line<F>, &point))
})
.min(geom1.points().fold(Bounded::max_value(), |acc, point| {
let nearest = tree_b.nearest_neighbor(&point).unwrap();
let nearest = tree_b.nearest_neighbor(point).unwrap();
acc.min(Euclidean.distance(nearest as &Line<F>, &point))
}))
}
Expand Down
2 changes: 1 addition & 1 deletion geo/src/algorithm/outlier_detection.rs
Original file line number Diff line number Diff line change
Expand Up @@ -212,7 +212,7 @@ where
.iter()
.map(|point| {
let neighbours = tree
.nearest_neighbor_iter_with_distance_2(point)
.nearest_neighbor_iter_with_distance_2(*point)
.take(k_neighbours)
.collect::<Vec<_>>();
let kth_dist = neighbours.last().map(|(_, d)| *d).unwrap();
Expand Down
2 changes: 1 addition & 1 deletion geo/src/algorithm/simplify_vw.rs
Original file line number Diff line number Diff line change
Expand Up @@ -415,7 +415,7 @@ where
orig[triangle.right],
)
.bounding_rect();
tree.locate_in_envelope_intersecting(&rstar::AABB::from_corners(
tree.locate_in_envelope_intersecting(rstar::AABB::from_corners(
bounding_rect.min().into(),
bounding_rect.max().into(),
))
Expand Down
2 changes: 1 addition & 1 deletion geo/src/algorithm/triangulate_delaunay.rs
Original file line number Diff line number Diff line change
Expand Up @@ -629,7 +629,7 @@ pub(crate) fn snap_or_register_point<T: SpadeTriangulationFloat>(
snap_radius: T,
) -> Coord<T> {
known_points
.nearest_neighbor(&point)
.nearest_neighbor(point)
// only snap if closest is within snap radius
.filter(|nearest_point| Euclidean.distance(**nearest_point, point) < snap_radius)
.cloned()
Expand Down