Skip to content

Commit

Permalink
intermediate type for searching with layers
Browse files Browse the repository at this point in the history
  • Loading branch information
mockersf committed Jul 17, 2024
1 parent d1caa77 commit 0c80260
Show file tree
Hide file tree
Showing 3 changed files with 211 additions and 121 deletions.
23 changes: 13 additions & 10 deletions src/async_helpers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ use glam::Vec2;

use crate::{
instance::{InstanceStep, SearchInstance},
Mesh, Path,
Mesh, Path, PolygonInMesh, POLYGON_NOT_FOUND,
};

/// A future that will resolve to a [`Option<Path>`].
Expand All @@ -17,7 +17,7 @@ pub struct FuturePath<'m> {
pub(crate) to: Vec2,
pub(crate) mesh: &'m Mesh,
pub(crate) instance: Option<SearchInstance<'m>>,
pub(crate) ending_polygon: isize,
pub(crate) ending_polygon: PolygonInMesh,
}

impl<'m> fmt::Debug for FuturePath<'m> {
Expand Down Expand Up @@ -51,18 +51,21 @@ impl<'m> Future for FuturePath<'m> {
let start = Instant::now();

let starting_polygon_index = self.mesh.get_point_location(self.from);
if starting_polygon_index == u32::MAX {
if starting_polygon_index == POLYGON_NOT_FOUND {
return Poll::Ready(None);
}
let ending_polygon = self.mesh.get_point_location(self.to);
if ending_polygon == u32::MAX {
if ending_polygon == POLYGON_NOT_FOUND {
return Poll::Ready(None);
}
if let Some(islands) = self.mesh.layers[0].islands.as_ref() {
let start_island = islands.get(starting_polygon_index as usize);
let end_island = islands.get(ending_polygon as usize);
if start_island.is_some() && end_island.is_some() && start_island != end_island {
return Poll::Ready(None);
if starting_polygon_index.layer == ending_polygon.layer {
if let Some(islands) = self.mesh.layers[0].islands.as_ref() {
let start_island = islands.get(starting_polygon_index.polygon as usize);
let end_island = islands.get(ending_polygon.polygon as usize);
if start_island.is_some() && end_island.is_some() && start_island != end_island
{
return Poll::Ready(None);
}
}
}

Expand Down Expand Up @@ -95,7 +98,7 @@ impl<'m> Future for FuturePath<'m> {
#[cfg(feature = "stats")]
start,
));
self.ending_polygon = ending_polygon as isize;
self.ending_polygon = ending_polygon;
cx.waker().wake_by_ref();
Poll::Pending
}
Expand Down
62 changes: 38 additions & 24 deletions src/instance.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ use hashbrown::{hash_map::Entry, HashMap};

use crate::{
helpers::{heuristic, line_intersect_segment, turning_point, Vec2Helper},
Mesh, Path, Root, SearchNode,
Mesh, Path, PolygonInMesh, Root, SearchNode, POLYGON_NOT_FOUND,
};

#[derive(PartialEq, Eq, Clone, Copy, Debug)]
Expand Down Expand Up @@ -42,7 +42,7 @@ pub(crate) struct SearchInstance<'m> {
pub(crate) root_history: HashMap<Root, f32>,
pub(crate) from: Vec2,
pub(crate) to: Vec2,
pub(crate) polygon_to: isize,
pub(crate) polygon_to: PolygonInMesh,
pub(crate) mesh: &'m Mesh,
#[cfg(feature = "stats")]
pub(crate) start: Instant,
Expand Down Expand Up @@ -71,19 +71,20 @@ pub(crate) enum InstanceStep {
impl<'m> SearchInstance<'m> {
pub(crate) fn setup(
mesh: &'m Mesh,
from: (Vec2, u32),
to: (Vec2, u32),
from: (Vec2, PolygonInMesh),
to: (Vec2, PolygonInMesh),
#[cfg(feature = "stats")] start: Instant,
) -> Self {
let starting_polygon = &mesh.layers[0].polygons[from.1 as usize];
let starting_polygon =
&mesh.layers[from.1.layer as usize].polygons[from.1.polygon as usize];

let mut search_instance = SearchInstance {
queue: BinaryHeap::with_capacity(15),
node_buffer: Vec::with_capacity(10),
root_history: HashMap::with_capacity(10),
from: from.0,
to: to.0,
polygon_to: to.1 as isize,
polygon_to: to.1,
mesh,
#[cfg(feature = "stats")]
start,
Expand All @@ -109,8 +110,8 @@ impl<'m> SearchInstance<'m> {
root: from.0,
interval: (Vec2::new(0.0, 0.0), Vec2::new(0.0, 0.0)),
edge: (0, 0),
polygon_from: -1,
polygon_to: from.1 as isize,
polygon_from: POLYGON_NOT_FOUND,
polygon_to: from.1,
f: 0.0,
g: 0.0,
};
Expand All @@ -126,17 +127,22 @@ impl<'m> SearchInstance<'m> {
} else {
continue;
};
let other_side = *start
let other_side = start
.polygons
.iter()
.find(|i| **i != -1 && **i != from.1 as isize && end.polygons.contains(*i))
.unwrap_or(&isize::MAX);

if other_side == to.1 as isize
|| (other_side != isize::MAX
&& !search_instance.mesh.layers[0]
.filter(|i| **i != -1 && end.polygons.contains(*i))
.map(|i| PolygonInMesh {
layer: (*i >> 24) as u8,
polygon: ((*i << 8) >> 8) as u32,
})
.find(|poly| poly != &from.1)
.unwrap_or(POLYGON_NOT_FOUND);

if other_side == to.1
|| (other_side != POLYGON_NOT_FOUND
&& !search_instance.mesh.layers[other_side.layer as usize]
.polygons
.get(other_side as usize)
.get(other_side.polygon as usize)
.unwrap()
.is_one_way)
{
Expand Down Expand Up @@ -233,7 +239,8 @@ impl<'m> SearchInstance<'m> {
pub(crate) fn edges_between(&self, node: &SearchNode) -> SmallVec<[Successor; 10]> {
let mut successors = SmallVec::new();

let polygon = &self.mesh.layers[0].polygons[node.polygon_to as usize];
let polygon = &self.mesh.layers[node.polygon_to.layer as usize].polygons
[node.polygon_to.polygon as usize];

// if node.interval.0.distance(node.root) < 1.0e-5
// || node.interval.1.distance(node.root) < 1.0e-5
Expand Down Expand Up @@ -399,7 +406,7 @@ impl<'m> SearchInstance<'m> {
pub(crate) fn add_node(
&mut self,
root: Vec2,
other_side: isize,
other_side: PolygonInMesh,
start: (Vec2, u32),
end: (Vec2, u32),
node: &SearchNode,
Expand Down Expand Up @@ -516,19 +523,26 @@ impl<'m> SearchInstance<'m> {
println!("v {successor:?}");
}

let other_side = *start
let other_side = start
.polygons
.iter()
.find(|i| **i != -1 && **i != node.polygon_to && end.polygons.contains(*i))
.unwrap_or(&isize::MAX);
// .map(|i| dbg!(i))
.filter(|i| **i != -1 && end.polygons.contains(*i))
.map(|i| PolygonInMesh {
layer: (*i >> 24) as u8,
polygon: ((*i << 8) >> 8) as u32,
})
// .map(|i| dbg!(i))
.find(|poly| poly != &node.polygon_to)
.unwrap_or(POLYGON_NOT_FOUND);

#[cfg(debug_assertions)]
if self.debug {
println!("| going to {other_side:?}");
}

// prune edges that don't have a polygon on the other side: cul de sac pruning
if other_side == isize::MAX {
if other_side == POLYGON_NOT_FOUND {
#[cfg(debug_assertions)]
if self.debug {
println!("x cul de sac");
Expand All @@ -539,9 +553,9 @@ impl<'m> SearchInstance<'m> {

// prune edges that only lead to one other polygon, and not the target: dead end pruning
if self.polygon_to != other_side
&& self.mesh.layers[0]
&& self.mesh.layers[other_side.layer as usize]
.polygons
.get(other_side as usize)
.get(other_side.polygon as usize)
.unwrap()
.is_one_way
{
Expand Down
Loading

0 comments on commit 0c80260

Please sign in to comment.