mirror of https://codeberg.org/topola/topola.git
Exclude mesh neighbors from collision detection
This commit is contained in:
parent
1a599951cd
commit
4f473bacec
|
|
@ -63,7 +63,7 @@ impl<T> Index<T> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn retag(&self, weight: TaggedWeight) -> TaggedIndex {
|
pub fn retag(&self, weight: &TaggedWeight) -> TaggedIndex {
|
||||||
match weight {
|
match weight {
|
||||||
TaggedWeight::Dot(..) => TaggedIndex::Dot(DotIndex {
|
TaggedWeight::Dot(..) => TaggedIndex::Dot(DotIndex {
|
||||||
index: self.index,
|
index: self.index,
|
||||||
|
|
|
||||||
56
src/main.rs
56
src/main.rs
|
|
@ -177,11 +177,41 @@ fn main() {
|
||||||
})
|
})
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
|
let dot5 = layout
|
||||||
|
.add_dot(DotWeight {
|
||||||
|
net: 0,
|
||||||
|
circle: Circle {
|
||||||
|
pos: (150.5, 100.5).into(),
|
||||||
|
r: 8.0,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let dot6 = layout
|
||||||
|
.add_dot(DotWeight {
|
||||||
|
net: 0,
|
||||||
|
circle: Circle {
|
||||||
|
pos: (190.5, 100.5).into(),
|
||||||
|
r: 8.0,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let dot7 = layout
|
||||||
|
.add_dot(DotWeight {
|
||||||
|
net: 0,
|
||||||
|
circle: Circle {
|
||||||
|
pos: (230.5, 70.5).into(),
|
||||||
|
r: 8.0,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
let barrier1_dot1 = layout
|
let barrier1_dot1 = layout
|
||||||
.add_dot(DotWeight {
|
.add_dot(DotWeight {
|
||||||
net: 0,
|
net: 0,
|
||||||
circle: Circle {
|
circle: Circle {
|
||||||
pos: (250.5, 150.5).into(),
|
pos: (250.5, 250.5).into(),
|
||||||
r: 8.0,
|
r: 8.0,
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
@ -217,16 +247,20 @@ fn main() {
|
||||||
.unwrap();
|
.unwrap();
|
||||||
let _ = layout.add_seg(barrier2_dot1, barrier2_dot2, 16.0);
|
let _ = layout.add_seg(barrier2_dot1, barrier2_dot2, 16.0);
|
||||||
|
|
||||||
|
let head = layout.route_start(dot5);
|
||||||
|
let head = layout.route_around_dot(head, dot6, true, 5.0).unwrap();
|
||||||
|
let _ = layout.route_finish(head, dot7, 5.0);
|
||||||
|
|
||||||
/*render_times(&mut event_pump, &mut canvas, &mut layout, None, -1);
|
/*render_times(&mut event_pump, &mut canvas, &mut layout, None, -1);
|
||||||
|
|
||||||
let head = layout.route_start(dot1_1);
|
let head = layout.route_start(dot1_1);
|
||||||
let head = layout
|
let head = layout
|
||||||
.route_around_dot(head, barrier1_dot1, true, 5.)
|
.route_around_dot(head, barrier1_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let head = layout
|
let head = layout
|
||||||
.route_around_dot(head, barrier2_dot1, true, 5.)
|
.route_around_dot(head, barrier2_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
|
|
@ -236,12 +270,12 @@ fn main() {
|
||||||
|
|
||||||
let head = layout.route_start(dot2_1);
|
let head = layout.route_start(dot2_1);
|
||||||
let head = layout
|
let head = layout
|
||||||
.shove_around_dot(head, barrier1_dot1, true, 5.)
|
.shove_around_dot(head, barrier1_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let head = layout
|
let head = layout
|
||||||
.shove_around_dot(head, barrier2_dot1, true, 5.)
|
.shove_around_dot(head, barrier2_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
|
|
@ -253,16 +287,16 @@ fn main() {
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let head = layout
|
let head = layout
|
||||||
.shove_around_dot(head, barrier1_dot1, true, 5.)
|
.shove_around_dot(head, barrier1_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let head = layout
|
let head = layout
|
||||||
.shove_around_dot(head, barrier2_dot1, true, 5.)
|
.shove_around_dot(head, barrier2_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let _ = layout.route_finish(head, dot3_2, 5.);
|
let _ = layout.route_finish(head, dot3_2, 5.0);
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
|
|
||||||
|
|
@ -270,16 +304,16 @@ fn main() {
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let head = layout
|
let head = layout
|
||||||
.shove_around_dot(head, barrier1_dot1, true, 5.)
|
.shove_around_dot(head, barrier1_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let head = layout
|
let head = layout
|
||||||
.shove_around_dot(head, barrier2_dot1, true, 5.)
|
.shove_around_dot(head, barrier2_dot1, true, 5.0)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, 50);
|
||||||
let _ = layout.route_finish(head, dot4_2, 5.);*/
|
let _ = layout.route_finish(head, dot4_2, 5.0);*/
|
||||||
|
|
||||||
render_times(&mut event_pump, &mut canvas, &mut layout, None, -1);
|
render_times(&mut event_pump, &mut canvas, &mut layout, None, -1);
|
||||||
render_times(
|
render_times(
|
||||||
|
|
|
||||||
32
src/mesh.rs
32
src/mesh.rs
|
|
@ -45,14 +45,14 @@ impl Mesh {
|
||||||
// Unnecessary retag. It should be possible to elide it.
|
// Unnecessary retag. It should be possible to elide it.
|
||||||
let weight = *self.graph.node_weight(index.index).unwrap();
|
let weight = *self.graph.node_weight(index.index).unwrap();
|
||||||
|
|
||||||
let wrapper = RTreeWrapper::new(self.primitive(index).shape(), index.retag(weight));
|
let wrapper = RTreeWrapper::new(self.primitive(index).shape(), index.retag(&weight));
|
||||||
assert!(self.rtree.remove(&wrapper).is_some());
|
assert!(self.rtree.remove(&wrapper).is_some());
|
||||||
self.graph.remove_node(index.index);
|
self.graph.remove_node(index.index);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn add_dot(&mut self, weight: DotWeight) -> Result<DotIndex, ()> {
|
pub fn add_dot(&mut self, weight: DotWeight) -> Result<DotIndex, ()> {
|
||||||
let dot = DotIndex::new(self.graph.add_node(TaggedWeight::Dot(weight)));
|
let dot = DotIndex::new(self.graph.add_node(TaggedWeight::Dot(weight)));
|
||||||
self.fail_and_remove_if_collides(dot)?;
|
//self.fail_and_remove_if_collides_except(dot, &[])?;
|
||||||
|
|
||||||
self.rtree.insert(RTreeWrapper::new(
|
self.rtree.insert(RTreeWrapper::new(
|
||||||
self.primitive(dot).shape(),
|
self.primitive(dot).shape(),
|
||||||
|
|
@ -68,11 +68,11 @@ impl Mesh {
|
||||||
weight: SegWeight,
|
weight: SegWeight,
|
||||||
) -> Result<SegIndex, ()> {
|
) -> Result<SegIndex, ()> {
|
||||||
let seg = SegIndex::new(self.graph.add_node(TaggedWeight::Seg(weight)));
|
let seg = SegIndex::new(self.graph.add_node(TaggedWeight::Seg(weight)));
|
||||||
self.fail_and_remove_if_collides(seg)?;
|
|
||||||
|
|
||||||
self.graph.add_edge(from.index, seg.index, Label::End);
|
self.graph.add_edge(from.index, seg.index, Label::End);
|
||||||
self.graph.add_edge(seg.index, to.index, Label::End);
|
self.graph.add_edge(seg.index, to.index, Label::End);
|
||||||
|
|
||||||
|
//self.fail_and_remove_if_collides_except(seg, &[from.tag(), to.tag()])?;
|
||||||
self.insert_into_rtree(seg.tag());
|
self.insert_into_rtree(seg.tag());
|
||||||
Ok(seg)
|
Ok(seg)
|
||||||
}
|
}
|
||||||
|
|
@ -99,7 +99,7 @@ impl Mesh {
|
||||||
weight: BendWeight,
|
weight: BendWeight,
|
||||||
) -> Result<BendIndex, ()> {
|
) -> Result<BendIndex, ()> {
|
||||||
let bend = BendIndex::new(self.graph.add_node(TaggedWeight::Bend(weight)));
|
let bend = BendIndex::new(self.graph.add_node(TaggedWeight::Bend(weight)));
|
||||||
self.fail_and_remove_if_collides(bend)?;
|
//self.fail_and_remove_if_collides_except(bend, &[from.tag(), to.tag(), core.tag()])?;
|
||||||
|
|
||||||
self.graph.add_edge(from.index, bend.index, Label::End);
|
self.graph.add_edge(from.index, bend.index, Label::End);
|
||||||
self.graph.add_edge(bend.index, to.index, Label::End);
|
self.graph.add_edge(bend.index, to.index, Label::End);
|
||||||
|
|
@ -173,7 +173,7 @@ impl Mesh {
|
||||||
dot_weight.circle.pos = to;
|
dot_weight.circle.pos = to;
|
||||||
*self.graph.node_weight_mut(dot.index).unwrap() = TaggedWeight::Dot(dot_weight);
|
*self.graph.node_weight_mut(dot.index).unwrap() = TaggedWeight::Dot(dot_weight);
|
||||||
|
|
||||||
if let Some(..) = self.detect_collision(&self.primitive(dot).shape()) {
|
if let Some(..) = self.detect_collision_except(dot, &[]) {
|
||||||
// Restore original state.
|
// Restore original state.
|
||||||
*self.graph.node_weight_mut(dot.index).unwrap() = TaggedWeight::Dot(old_weight);
|
*self.graph.node_weight_mut(dot.index).unwrap() = TaggedWeight::Dot(old_weight);
|
||||||
self.insert_into_rtree(dot.tag());
|
self.insert_into_rtree(dot.tag());
|
||||||
|
|
@ -209,20 +209,34 @@ impl Mesh {
|
||||||
Bow::new(bend, &self.graph)
|
Bow::new(bend, &self.graph)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fail_and_remove_if_collides<Weight: std::marker::Copy>(
|
fn fail_and_remove_if_collides_except<Weight: std::marker::Copy>(
|
||||||
&mut self,
|
&mut self,
|
||||||
index: Index<Weight>,
|
index: Index<Weight>,
|
||||||
|
except: &[TaggedIndex],
|
||||||
) -> Result<(), ()> {
|
) -> Result<(), ()> {
|
||||||
/*if self.detect_collision(&self.primitive(index).shape()) {
|
if let Some(..) = self.detect_collision_except(index, except) {
|
||||||
self.remove(index);
|
self.remove(index);
|
||||||
return Err(());
|
return Err(());
|
||||||
}*/
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
fn detect_collision(&self, shape: &Shape) -> Option<TaggedIndex> {
|
fn detect_collision_except<Weight: std::marker::Copy>(
|
||||||
|
&self,
|
||||||
|
index: Index<Weight>,
|
||||||
|
except: &[TaggedIndex],
|
||||||
|
) -> Option<TaggedIndex> {
|
||||||
|
let primitive = self.primitive(index);
|
||||||
|
let shape = primitive.shape();
|
||||||
|
|
||||||
self.rtree
|
self.rtree
|
||||||
.locate_in_envelope_intersecting(&shape.envelope())
|
.locate_in_envelope_intersecting(&shape.envelope())
|
||||||
|
.filter(|wrapper| {
|
||||||
|
!primitive
|
||||||
|
.neighbors()
|
||||||
|
.any(|neighbor| neighbor == wrapper.data)
|
||||||
|
})
|
||||||
|
.filter(|wrapper| !except.contains(&wrapper.data))
|
||||||
.filter(|wrapper| shape.intersects(wrapper.geom()))
|
.filter(|wrapper| shape.intersects(wrapper.geom()))
|
||||||
.map(|wrapper| wrapper.data)
|
.map(|wrapper| wrapper.data)
|
||||||
.next()
|
.next()
|
||||||
|
|
|
||||||
|
|
@ -49,6 +49,12 @@ impl<'a, Weight> Primitive<'a, Weight> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn neighbors(&self) -> impl Iterator<Item = TaggedIndex> + '_ {
|
||||||
|
self.graph
|
||||||
|
.neighbors_undirected(self.index.index)
|
||||||
|
.map(|index| Index::<Label>::new(index).retag(self.graph.node_weight(index).unwrap()))
|
||||||
|
}
|
||||||
|
|
||||||
pub fn next(&self) -> Option<TaggedIndex> {
|
pub fn next(&self) -> Option<TaggedIndex> {
|
||||||
self.graph
|
self.graph
|
||||||
.neighbors_directed(self.index.index, Outgoing)
|
.neighbors_directed(self.index.index, Outgoing)
|
||||||
|
|
@ -58,7 +64,7 @@ impl<'a, Weight> Primitive<'a, Weight> {
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.is_end()
|
.is_end()
|
||||||
})
|
})
|
||||||
.map(|ni| Index::<Label>::new(ni).retag(*self.graph.node_weight(ni).unwrap()))
|
.map(|ni| Index::<Label>::new(ni).retag(self.graph.node_weight(ni).unwrap()))
|
||||||
.next()
|
.next()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -98,7 +104,7 @@ impl<'a, Weight> Primitive<'a, Weight> {
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.is_end()
|
.is_end()
|
||||||
})
|
})
|
||||||
.map(|ni| Index::<Label>::new(ni).retag(*self.graph.node_weight(ni).unwrap()))
|
.map(|ni| Index::<Label>::new(ni).retag(self.graph.node_weight(ni).unwrap()))
|
||||||
.next()
|
.next()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -144,7 +150,7 @@ impl<'a, Weight> Primitive<'a, Weight> {
|
||||||
|
|
||||||
pub fn tagged_index(&self) -> TaggedIndex {
|
pub fn tagged_index(&self) -> TaggedIndex {
|
||||||
self.index
|
self.index
|
||||||
.retag(*self.graph.node_weight(self.index.index).unwrap())
|
.retag(self.graph.node_weight(self.index.index).unwrap())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn tagged_weight(&self) -> TaggedWeight {
|
pub fn tagged_weight(&self) -> TaggedWeight {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue