61 lines
2.2 KiB
Python
61 lines
2.2 KiB
Python
from shapely.geometry import Polygon
|
|
|
|
from inire.geometry.collision import CollisionEngine
|
|
from inire.geometry.primitives import Port
|
|
|
|
|
|
def test_collision_detection() -> None:
|
|
# Clearance = 2um
|
|
engine = CollisionEngine(clearance=2.0)
|
|
|
|
# 10x10 um obstacle at (10,10)
|
|
obstacle = Polygon([(10, 10), (20, 10), (20, 20), (10, 20)])
|
|
engine.add_static_obstacle(obstacle)
|
|
|
|
# 1. Direct hit
|
|
test_poly = Polygon([(12, 12), (13, 12), (13, 13), (12, 13)])
|
|
assert engine.is_collision(test_poly, net_width=2.0)
|
|
|
|
# 2. Far away
|
|
test_poly_far = Polygon([(0, 0), (5, 0), (5, 5), (0, 5)])
|
|
assert not engine.is_collision(test_poly_far, net_width=2.0)
|
|
|
|
# 3. Near hit (within clearance)
|
|
# Obstacle edge at x=10.
|
|
# test_poly edge at x=9.
|
|
# Distance = 1.0 um.
|
|
# Required distance (Wi+C)/2 = 2.0. Collision!
|
|
test_poly_near = Polygon([(8, 10), (9, 10), (9, 15), (8, 15)])
|
|
assert engine.is_collision(test_poly_near, net_width=2.0)
|
|
|
|
|
|
def test_safety_zone() -> None:
|
|
# Use zero clearance for this test to verify the 2nm port safety zone
|
|
# against the physical obstacle boundary.
|
|
engine = CollisionEngine(clearance=0.0)
|
|
|
|
obstacle = Polygon([(10, 10), (20, 10), (20, 20), (10, 20)])
|
|
engine.add_static_obstacle(obstacle)
|
|
|
|
# Port exactly on the boundary
|
|
start_port = Port(10.0, 12.0, 0)
|
|
|
|
# Move starting from this port that overlaps the obstacle by 1nm
|
|
# (Inside the 2nm safety zone)
|
|
test_poly = Polygon([(9.999, 11.9995), (10.001, 11.9995), (10.001, 12.0005), (9.999, 12.0005)])
|
|
|
|
assert not engine.is_collision(test_poly, net_width=0.001, start_port=start_port)
|
|
|
|
|
|
def test_configurable_max_net_width() -> None:
|
|
# Large max_net_width (10.0) -> large pre-dilation (6.0)
|
|
engine = CollisionEngine(clearance=2.0, max_net_width=10.0)
|
|
|
|
obstacle = Polygon([(20, 20), (25, 20), (25, 25), (20, 25)])
|
|
engine.add_static_obstacle(obstacle)
|
|
|
|
test_poly = Polygon([(15, 20), (16, 20), (16, 25), (15, 25)])
|
|
# physical check: dilated test_poly by C/2 = 1.0.
|
|
# Dilated test_poly bounds: (14, 19, 17, 26).
|
|
# obstacle: (20, 20, 25, 25). No physical collision.
|
|
assert not engine.is_collision(test_poly, net_width=2.0)
|