Split `Walk` trait into `Interior` and `Ends` traits

This commit is contained in:
Mikolaj Wielgus 2023-08-28 22:54:03 +02:00
parent 84a7f5d873
commit 79a26cb324
5 changed files with 42 additions and 55 deletions

View File

@ -1,6 +1,8 @@
use petgraph::stable_graph::StableDiGraph;
use crate::graph::{BendIndex, DotIndex, Label, SegIndex, TaggedIndex, TaggedWeight, Walk};
use crate::graph::{
BendIndex, DotIndex, Ends, Interior, Label, SegIndex, TaggedIndex, TaggedWeight,
};
use crate::primitive::{Bend, Dot, Seg};
pub struct Bow {
@ -45,7 +47,7 @@ impl Bow {
}
}
impl Walk for Bow {
impl Interior<TaggedIndex> for Bow {
fn interior(&self) -> Vec<TaggedIndex> {
vec![
TaggedIndex::Seg(self.seg1),
@ -55,20 +57,10 @@ impl Walk for Bow {
TaggedIndex::Seg(self.seg2),
]
}
}
fn closure(&self) -> Vec<TaggedIndex> {
vec![
TaggedIndex::Dot(self.seg1_dot1),
TaggedIndex::Seg(self.seg1),
TaggedIndex::Dot(self.seg1_dot2),
TaggedIndex::Bend(self.bend),
TaggedIndex::Dot(self.seg2_dot1),
TaggedIndex::Seg(self.seg2),
TaggedIndex::Dot(self.seg2_dot2),
]
}
fn ends(&self) -> [DotIndex; 2] {
[self.seg1_dot1, self.seg2_dot2]
impl Ends<DotIndex, DotIndex> for Bow {
fn ends(&self) -> (DotIndex, DotIndex) {
(self.seg1_dot1, self.seg2_dot2)
}
}

View File

@ -4,10 +4,12 @@ use std::marker::PhantomData;
use crate::math::Circle;
pub trait Walk {
fn interior(&self) -> Vec<TaggedIndex>;
fn closure(&self) -> Vec<TaggedIndex>;
fn ends(&self) -> [DotIndex; 2];
pub trait Interior<T> {
fn interior(&self) -> Vec<T>;
}
pub trait Ends<Start, Stop> {
fn ends(&self) -> (Start, Stop);
}
#[derive(Debug, EnumAsInner, Clone, Copy, PartialEq)]

View File

@ -8,8 +8,8 @@ use spade::{DelaunayTriangulation, HasPosition, Point2, Triangulation};
use crate::bow::Bow;
use crate::graph::{
BendIndex, BendWeight, DotIndex, DotWeight, Index, Label, SegIndex, SegWeight, Tag,
TaggedIndex, TaggedWeight, Walk,
BendIndex, BendWeight, DotIndex, DotWeight, Index, Interior, Label, SegIndex, SegWeight, Tag,
TaggedIndex, TaggedWeight,
};
use crate::primitive::Primitive;
use crate::shape::Shape;
@ -29,15 +29,15 @@ impl Layout {
}
}
pub fn remove_open_set(&mut self, open_set: Vec<TaggedIndex>) {
for index in open_set.iter().filter(|index| !index.is_dot()) {
pub fn remove_open_set(&mut self, set: Vec<TaggedIndex>) {
for index in set.iter().filter(|index| !index.is_dot()) {
untag!(index, self.remove(*index));
}
// We must remove the dots only after the segs and bends because we need dots to calculate
// the shapes, which we need to remove the segs and bends from the R-tree.
for index in open_set.iter().filter(|index| index.is_dot()) {
for index in set.iter().filter(|index| index.is_dot()) {
untag!(index, self.remove(*index));
}
}

View File

@ -4,8 +4,8 @@ use petgraph::stable_graph::{NodeIndex, StableDiGraph};
use petgraph::Direction::{Incoming, Outgoing};
use crate::graph::{
BendIndex, BendWeight, DotIndex, DotWeight, Index, Label, SegIndex, SegWeight, Tag,
TaggedIndex, TaggedWeight, Walk,
BendIndex, BendWeight, DotIndex, DotWeight, Ends, Index, Interior, Label, SegIndex, SegWeight,
Tag, TaggedIndex, TaggedWeight,
};
use crate::math::{self, Circle};
use crate::shape::{BendShape, DotShape, SegShape, Shape};
@ -27,8 +27,8 @@ impl<'a, Weight> Primitive<'a, Weight> {
TaggedWeight::Seg(seg) => {
let ends = self.ends();
Shape::Seg(SegShape {
from: self.primitive(ends[0]).weight().circle.pos,
to: self.primitive(ends[1]).weight().circle.pos,
from: self.primitive(ends.0).weight().circle.pos,
to: self.primitive(ends.1).weight().circle.pos,
width: seg.width,
})
}
@ -36,13 +36,13 @@ impl<'a, Weight> Primitive<'a, Weight> {
let ends = self.ends();
let mut bend_shape = BendShape {
from: self.primitive(ends[0]).weight().circle.pos,
to: self.primitive(ends[1]).weight().circle.pos,
from: self.primitive(ends.0).weight().circle.pos,
to: self.primitive(ends.1).weight().circle.pos,
c: Circle {
pos: self.primitive(self.core().unwrap()).weight().circle.pos,
r: self.inner_radius(),
},
width: self.primitive(ends[0]).weight().circle.r * 2.0,
width: self.primitive(ends.0).weight().circle.r * 2.0,
};
if bend.cw {
@ -216,22 +216,16 @@ impl<'a, Weight> Primitive<'a, Weight> {
}
}
impl<'a, Weight> Walk for Primitive<'a, Weight> {
impl<'a, Weight> Interior<TaggedIndex> for Primitive<'a, Weight> {
fn interior(&self) -> Vec<TaggedIndex> {
vec![self.tagged_index()]
}
}
fn closure(&self) -> Vec<TaggedIndex> {
let ends: Vec<TaggedIndex> = self
.ends()
.into_iter()
.map(|end| TaggedIndex::Dot(end))
.collect();
[[self.tagged_index()].as_slice(), ends.as_slice()].concat()
}
fn ends(&self) -> [DotIndex; 2] {
self.graph
impl<'a, Weight> Ends<DotIndex, DotIndex> for Primitive<'a, Weight> {
fn ends(&self) -> (DotIndex, DotIndex) {
let v = self
.graph
.neighbors_undirected(self.index.index)
.filter(|ni| {
self.graph
@ -246,9 +240,8 @@ impl<'a, Weight> Walk for Primitive<'a, Weight> {
})
.filter(|ni| self.graph.node_weight(*ni).unwrap().is_dot())
.map(|ni| DotIndex::new(ni))
.collect::<Vec<DotIndex>>()
.try_into()
.unwrap()
.collect::<Vec<_>>();
(v[0], v[1])
}
}
@ -359,8 +352,8 @@ impl<'a> Bend<'a> {
pub fn cross_product(&self) -> f64 {
let center = self.primitive(self.core().unwrap()).weight().circle.pos;
let ends = self.ends();
let end1 = self.primitive(ends[0]).weight().circle.pos;
let end2 = self.primitive(ends[1]).weight().circle.pos;
let end1 = self.primitive(ends.0).weight().circle.pos;
let end2 = self.primitive(ends.1).weight().circle.pos;
math::cross_product(end1 - center, end2 - center)
}
}

View File

@ -5,7 +5,7 @@ use std::cell::{Ref, RefCell};
use std::rc::Rc;
use crate::astar::astar;
use crate::graph::{BendIndex, DotIndex, SegIndex, TaggedIndex, Walk};
use crate::graph::{BendIndex, DotIndex, Ends, Interior, SegIndex, TaggedIndex};
use crate::graph::{BendWeight, DotWeight, SegWeight, TaggedWeight};
use crate::guide::Guide;
use crate::layout::Layout;
@ -244,7 +244,7 @@ impl Router {
}
fn reroute_outward(&mut self, bend: BendIndex) -> Result<(), ()> {
let mut endss: Vec<[DotIndex; 2]> = vec![];
let mut endss: Vec<(DotIndex, DotIndex)> = vec![];
let mut interiors: Vec<Vec<TaggedIndex>> = vec![];
let cw = self.layout.primitive(bend).weight().cw;
@ -268,7 +268,7 @@ impl Router {
}
for ends in endss {
let mut head = self.draw_start(ends[0]);
let mut head = self.draw_start(ends.0);
let width = 5.0;
if let Some(inner) = maybe_inner {
@ -278,7 +278,7 @@ impl Router {
}
maybe_inner = head.bend;
self.draw_finish(head, ends[1], width)?;
self.draw_finish(head, ends.1, width)?;
self.relax_band(maybe_inner.unwrap());
}
@ -331,8 +331,8 @@ impl Router {
self.layout.remove_open_set(bow.interior());
let head = self.draw_start(ends[0]);
let _ = self.draw_finish(head, ends[1], 5.);
let head = self.draw_start(ends.0);
let _ = self.draw_finish(head, ends.1, 5.0);
}
pub fn move_dot(&mut self, dot: DotIndex, to: Point) -> Result<(), ()> {