Move map-based pathfinding code to Map
.
This commit is contained in:
parent
8db8b72824
commit
1fa48f89ab
10
src/core.rs
10
src/core.rs
|
@ -353,6 +353,16 @@ impl PointLike for IVec2 {
|
|||
}
|
||||
}
|
||||
|
||||
impl PointLike for UVec2 {
|
||||
fn x(&self) -> f32 {
|
||||
self.x as f32
|
||||
}
|
||||
|
||||
fn y(&self) -> f32 {
|
||||
self.y as f32
|
||||
}
|
||||
}
|
||||
|
||||
impl PointLike for (i32, i32) {
|
||||
fn x(&self) -> f32 {
|
||||
self.0 as f32
|
||||
|
|
35
src/map.rs
35
src/map.rs
|
@ -5,11 +5,13 @@ use bevy::prelude::*;
|
|||
pub use here_be_dragons::Map as MapgenMap;
|
||||
use here_be_dragons::{geometry::Rect as MRect, MapFilter, Tile};
|
||||
use maze_generator::{prelude::*, recursive_backtracking::RbGenerator};
|
||||
use pathfinding::prelude::*;
|
||||
use rand::prelude::StdRng;
|
||||
|
||||
use crate::{
|
||||
core::{Obstacle, PointLike, Zone},
|
||||
exploration::Mappable,
|
||||
pathfinding::CostMap,
|
||||
visibility::Visible,
|
||||
};
|
||||
|
||||
|
@ -17,6 +19,39 @@ use crate::{
|
|||
#[require(Transform, SpawnColliders, SpawnPortals)]
|
||||
pub struct Map<D: 'static + Clone + Default + Send + Sync>(pub MapgenMap<D>);
|
||||
|
||||
impl<D: 'static + Clone + Default + Send + Sync> Map<D> {
|
||||
pub fn find_path(
|
||||
&self,
|
||||
start: &UVec2,
|
||||
destination: &UVec2,
|
||||
cost_map: &Option<CostMap>,
|
||||
) -> Option<(Vec<UVec2>, u32)> {
|
||||
astar(
|
||||
&start,
|
||||
|p| {
|
||||
let mut successors: Vec<(UVec2, u32)> = vec![];
|
||||
if let Some(tile) = self.at(p.x as usize, p.y as usize) {
|
||||
if tile.is_walkable() {
|
||||
for tile in self.get_available_exits(p.x as usize, p.y as usize) {
|
||||
let mut cost = tile.2 * 100.;
|
||||
if let Some(cost_map) = cost_map {
|
||||
if let Some(modifier) = cost_map.get(&p.as_ivec2()) {
|
||||
cost *= modifier;
|
||||
}
|
||||
}
|
||||
successors
|
||||
.push((UVec2::new(tile.0 as u32, tile.1 as u32), cost as u32));
|
||||
}
|
||||
}
|
||||
}
|
||||
successors
|
||||
},
|
||||
|p| (p.distance_squared(destination) * 100.) as u32,
|
||||
|p| *p == *destination,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
impl<D: Clone + Default + Send + Sync> From<MapgenMap<D>> for Map<D> {
|
||||
fn from(v: MapgenMap<D>) -> Self {
|
||||
Self(v)
|
||||
|
|
|
@ -5,7 +5,6 @@ use pathfinding::prelude::*;
|
|||
|
||||
use crate::{
|
||||
core::{GlobalTransformExt, Obstacle},
|
||||
map::Map,
|
||||
navigation::{NavigationAction, RotationSpeed, Speed},
|
||||
};
|
||||
|
||||
|
@ -45,39 +44,6 @@ impl Default for PathfindingControlsBundle {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn find_path<D: 'static + Clone + Default + Send + Sync>(
|
||||
start: IVec2,
|
||||
destination: IVec2,
|
||||
map: &Map<D>,
|
||||
cost_map: &Option<CostMap>,
|
||||
) -> Option<(Vec<IVec2>, u32)> {
|
||||
astar(
|
||||
&start,
|
||||
|p| {
|
||||
let mut successors: Vec<(IVec2, u32)> = vec![];
|
||||
if p.x >= 0 && p.y >= 0 {
|
||||
if let Some(tile) = map.at(p.x as usize, p.y as usize) {
|
||||
if tile.is_walkable() {
|
||||
for tile in map.get_available_exits(p.x as usize, p.y as usize) {
|
||||
let mut cost = tile.2 * 100.;
|
||||
if let Some(cost_map) = cost_map {
|
||||
if let Some(modifier) = cost_map.get(p) {
|
||||
cost *= modifier;
|
||||
}
|
||||
}
|
||||
successors
|
||||
.push((IVec2::new(tile.0 as i32, tile.1 as i32), cost as u32));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
successors
|
||||
},
|
||||
|p| (p.distance_squared(destination) * 100) as u32,
|
||||
|p| *p == destination,
|
||||
)
|
||||
}
|
||||
|
||||
fn calculate_path(
|
||||
mut commands: Commands,
|
||||
spatial_query: SpatialQuery,
|
||||
|
|
Loading…
Reference in New Issue
Block a user