mirror of https://codeberg.org/topola/topola.git
Use `Vector2<i64>` instead of `[i64; 2]` in `navmesher.rs`
This commit is contained in:
parent
41dd0a91f8
commit
50b7dc26b0
|
|
@ -9,17 +9,18 @@ use crate::{
|
||||||
math,
|
math,
|
||||||
Board,
|
Board,
|
||||||
primitives::{Joint, JointId, Polygon, PolygonId, Segment, SegmentId, Via, ViaId},
|
primitives::{Joint, JointId, Polygon, PolygonId, Segment, SegmentId, Via, ViaId},
|
||||||
|
Vector2,
|
||||||
};
|
};
|
||||||
|
|
||||||
#[derive(Clone, Debug, Getters)]
|
#[derive(Clone, Debug, Getters)]
|
||||||
pub struct LayerNavmesher {
|
pub struct LayerNavmesher {
|
||||||
boundary: Vec<[i64; 2]>,
|
boundary: Vec<Vector2<i64>>,
|
||||||
navmeshes: Vec<RecordingTriangulator<i64>>,
|
navmeshes: Vec<RecordingTriangulator<i64>>,
|
||||||
inflation_factors: Vec<f64>,
|
inflation_factors: Vec<f64>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl LayerNavmesher {
|
impl LayerNavmesher {
|
||||||
pub fn new(boundary: impl IntoIterator<Item = [i64; 2]>) -> Self {
|
pub fn new(boundary: impl IntoIterator<Item = Vector2<i64>>) -> Self {
|
||||||
Self {
|
Self {
|
||||||
boundary: boundary.into_iter().collect(),
|
boundary: boundary.into_iter().collect(),
|
||||||
navmeshes: vec![RecordingTriangulator::new()],
|
navmeshes: vec![RecordingTriangulator::new()],
|
||||||
|
|
@ -27,31 +28,33 @@ impl LayerNavmesher {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn insert_polygon(&mut self, polygon: impl IntoIterator<Item = [i64; 2]>) {
|
pub fn insert_polygon(&mut self, polygon: impl IntoIterator<Item = Vector2<i64>>) {
|
||||||
let polygon: Vec<[i64; 2]> = polygon.into_iter().collect();
|
let polygon: Vec<Vector2<i64>> = polygon.into_iter().collect();
|
||||||
|
|
||||||
for i in 0..self.navmeshes.len() {
|
for i in 0..self.navmeshes.len() {
|
||||||
self.navmeshes[i].insert_polygon_and_rebuild(
|
self.navmeshes[i].insert_polygon_and_rebuild(
|
||||||
Self::inflate_polygon(polygon.clone(), self.inflation_factors[i]),
|
Self::inflate_polygon(polygon.clone(), self.inflation_factors[i])
|
||||||
self.boundary.clone(),
|
.into_iter()
|
||||||
|
.map(Into::into),
|
||||||
|
self.boundary.iter().cloned().map(Into::into),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn inflate_polygon(
|
fn inflate_polygon(
|
||||||
polygon: impl IntoIterator<Item = [i64; 2]>,
|
polygon: Vec<Vector2<i64>>,
|
||||||
inflation_factor: f64,
|
inflation_factor: f64,
|
||||||
) -> impl IntoIterator<Item = [i64; 2]> {
|
) -> impl IntoIterator<Item = Vector2<i64>> {
|
||||||
let polygon: Vec<[i64; 2]> = polygon.into_iter().collect();
|
|
||||||
|
|
||||||
// Centroid.
|
// Centroid.
|
||||||
let cx = polygon.iter().map(|p| p[0] as f64).sum::<f64>() / polygon.len() as f64;
|
let cx = polygon.iter().map(|p| p.x as f64).sum::<f64>() / polygon.len() as f64;
|
||||||
let cy = polygon.iter().map(|p| p[1] as f64).sum::<f64>() / polygon.len() as f64;
|
let cy = polygon.iter().map(|p| p.y as f64).sum::<f64>() / polygon.len() as f64;
|
||||||
|
|
||||||
polygon.into_iter().map(move |[px, py]| {
|
polygon.into_iter().map(move |p| {
|
||||||
|
let px = p.x as f64;
|
||||||
|
let py = p.y as f64;
|
||||||
// Delta.
|
// Delta.
|
||||||
let dx = px as f64 - cx;
|
let dx = px - cx;
|
||||||
let dy = py as f64 - cy;
|
let dy = py - cy;
|
||||||
let d = (dx * dx + dy * dy).sqrt();
|
let d = (dx * dx + dy * dy).sqrt();
|
||||||
|
|
||||||
// Normalize delta.
|
// Normalize delta.
|
||||||
|
|
@ -59,14 +62,14 @@ impl LayerNavmesher {
|
||||||
let ny = dy / d;
|
let ny = dy / d;
|
||||||
|
|
||||||
// Shift away from centroid.
|
// Shift away from centroid.
|
||||||
let fx = px as f64 + nx * inflation_factor;
|
let fx = px + nx * inflation_factor;
|
||||||
let fy = py as f64 + ny * inflation_factor;
|
let fy = py + ny * inflation_factor;
|
||||||
|
|
||||||
// Round away from centroid.
|
// Round away from centroid.
|
||||||
let rx = if fx >= cx { fx.ceil() } else { fx.floor() };
|
let rx = if fx >= cx { fx.ceil() } else { fx.floor() };
|
||||||
let ry = if fy >= cy { fy.ceil() } else { fy.floor() };
|
let ry = if fy >= cy { fy.ceil() } else { fy.floor() };
|
||||||
|
|
||||||
[rx as i64, ry as i64]
|
Vector2::new(rx as i64, ry as i64)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -77,8 +80,8 @@ pub struct Navmesher {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Navmesher {
|
impl Navmesher {
|
||||||
pub fn new(boundary: impl IntoIterator<Item = [i64; 2]>, layer_count: usize) -> Self {
|
pub fn new(boundary: impl IntoIterator<Item = Vector2<i64>>, layer_count: usize) -> Self {
|
||||||
let boundary: Vec<[i64; 2]> = boundary.into_iter().collect();
|
let boundary: Vec<Vector2<i64>> = boundary.into_iter().collect();
|
||||||
|
|
||||||
Self {
|
Self {
|
||||||
layers: std::iter::repeat_with(|| LayerNavmesher::new(boundary.clone()))
|
layers: std::iter::repeat_with(|| LayerNavmesher::new(boundary.clone()))
|
||||||
|
|
@ -87,7 +90,7 @@ impl Navmesher {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn insert_polygon(&mut self, layer: usize, polygon: impl IntoIterator<Item = [i64; 2]>) {
|
pub fn insert_polygon(&mut self, layer: usize, polygon: impl IntoIterator<Item = Vector2<i64>>) {
|
||||||
self.layers[layer].insert_polygon(polygon);
|
self.layers[layer].insert_polygon(polygon);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -101,7 +104,11 @@ pub struct NavmesherBoard {
|
||||||
impl NavmesherBoard {
|
impl NavmesherBoard {
|
||||||
pub fn with_board(board: Board) -> Self {
|
pub fn with_board(board: Board) -> Self {
|
||||||
let mut navmesher = Navmesher::new(
|
let mut navmesher = Navmesher::new(
|
||||||
board.layout().boundary().clone(),
|
board
|
||||||
|
.layout()
|
||||||
|
.boundary()
|
||||||
|
.iter()
|
||||||
|
.map(|p| Vector2::new(p[0], p[1])),
|
||||||
*board.layout().layer_count(),
|
*board.layout().layer_count(),
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
@ -129,20 +136,20 @@ impl NavmesherBoard {
|
||||||
navmesher.insert_polygon(joint.layer, Self::joint_circumscribed_octagon(joint));
|
navmesher.insert_polygon(joint.layer, Self::joint_circumscribed_octagon(joint));
|
||||||
}
|
}
|
||||||
|
|
||||||
fn joint_circumscribed_octagon(joint: Joint) -> [[i64; 2]; 8] {
|
fn joint_circumscribed_octagon(joint: Joint) -> [Vector2<i64>; 8] {
|
||||||
let cx = joint.position.x;
|
let cx = joint.position.x;
|
||||||
let cy = joint.position.y;
|
let cy = joint.position.y;
|
||||||
let r = joint.radius as i64;
|
let r = joint.radius as i64;
|
||||||
|
|
||||||
[
|
[
|
||||||
[cx + r, cy + r / 2],
|
Vector2::new(cx + r, cy + r / 2),
|
||||||
[cx + r / 2, cy + r],
|
Vector2::new(cx + r / 2, cy + r),
|
||||||
[cx - r / 2, cy + r],
|
Vector2::new(cx - r / 2, cy + r),
|
||||||
[cx - r, cy + r / 2],
|
Vector2::new(cx - r, cy + r / 2),
|
||||||
[cx - r, cy - r / 2],
|
Vector2::new(cx - r, cy - r / 2),
|
||||||
[cx - r / 2, cy - r],
|
Vector2::new(cx - r / 2, cy - r),
|
||||||
[cx + r / 2, cy - r],
|
Vector2::new(cx + r / 2, cy - r),
|
||||||
[cx + r, cy - r / 2],
|
Vector2::new(cx + r, cy - r / 2),
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -169,9 +176,7 @@ impl NavmesherBoard {
|
||||||
endpoints[1].x,
|
endpoints[1].x,
|
||||||
endpoints[1].y,
|
endpoints[1].y,
|
||||||
segment.half_width,
|
segment.half_width,
|
||||||
)
|
),
|
||||||
.into_iter()
|
|
||||||
.map(Into::into),
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -186,9 +191,6 @@ impl NavmesherBoard {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn insert_polygon_in_navmesher(navmesher: &mut Navmesher, polygon: Polygon) {
|
fn insert_polygon_in_navmesher(navmesher: &mut Navmesher, polygon: Polygon) {
|
||||||
navmesher.insert_polygon(
|
navmesher.insert_polygon(polygon.layer, polygon.vertices);
|
||||||
polygon.layer,
|
|
||||||
polygon.vertices.into_iter().map(Into::into),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue