RosettaCodeData/Task/Ray-casting-algorithm/11l/ray-casting-algorithm.11l

67 lines
2.6 KiB
Text
Raw Permalink Normal View History

2024-07-13 15:19:22 -07:00
T Pt((Float x, Float y))
2023-07-01 11:58:00 -04:00
F String()
R Pt(x=#., y=#.).format(.x, .y)
2024-07-13 15:19:22 -07:00
T Edge((Pt a, Pt b))
2023-07-01 11:58:00 -04:00
F String()
R Edge(a=#., b=#.).format(.a, .b)
2024-07-13 15:19:22 -07:00
T Poly = (String name, [Edge] edges)
2023-07-01 11:58:00 -04:00
V _eps = 0.00001
V _huge = 1e+100
V _tiny = 1e-100
F rayintersectseg(=p, edge)
V a = edge.a
V b = edge.b
I a.y > b.y
swap(&a, &b)
I p.y == a.y | p.y == b.y
p = Pt(p.x, p.y + :_eps)
V intersect = 0B
I (p.y > b.y | p.y < a.y) | (p.x > max(a.x, b.x))
R 0B
I p.x < min(a.x, b.x)
intersect = 1B
E
Float m_red, m_blue
I abs(a.x - b.x) > :_tiny
m_red = (b.y - a.y) / Float(b.x - a.x)
E
m_red = :_huge
I abs(a.x - p.x) > :_tiny
m_blue = (p.y - a.y) / Float(p.x - a.x)
E
m_blue = :_huge
intersect = m_blue >= m_red
R intersect
F ispointinside(p, poly)
R sum(poly.edges.map(edge -> Int(rayintersectseg(@p, edge)))) % 2 == 1
F polypp(poly)
print("\n Polygon(name='#.', edges=(".format(poly.name))
print( (poly.edges.map(e -> String(e)).join(",\n ")"\n ))"))
V polys = [
Poly(name' square, edges' [Edge(Pt(0, 0), Pt(10, 0)), Edge(Pt(10, 0), Pt(10, 10)), Edge(Pt(10, 10), Pt(0, 10)), Edge(Pt(0, 10), Pt(0, 0))]),
Poly(name' square_hole, edges' [Edge(Pt(0, 0), Pt(10, 0)), Edge(Pt(10, 0), Pt(10, 10)), Edge(Pt(10, 10), Pt(0, 10)), Edge(Pt(0, 10), Pt(0, 0)), Edge(Pt(2.5, 2.5), Pt(7.5, 2.5)), Edge(Pt(7.5, 2.5), Pt(7.5, 7.5)), Edge(Pt(7.5, 7.5), Pt(2.5, 7.5)), Edge(Pt(2.5, 7.5), Pt(2.5, 2.5))]),
Poly(name' strange, edges' [Edge(Pt(0, 0), Pt(2.5, 2.5)), Edge(Pt(2.5, 2.5), Pt(0, 10)), Edge(Pt(0, 10), Pt(2.5, 7.5)), Edge(Pt(2.5, 7.5), Pt(7.5, 7.5)), Edge(Pt(7.5, 7.5), Pt(10, 10)), Edge(Pt(10, 10), Pt(10, 0)), Edge(Pt(10, 0), Pt(2.5, 2.5))]),
Poly(name' exagon, edges' [Edge(Pt(3, 0), Pt(7, 0)), Edge(Pt(7, 0), Pt(10, 5)), Edge(Pt(10, 5), Pt(7, 10)), Edge(Pt(7, 10), Pt(3, 10)), Edge(Pt(3, 10), Pt(0, 5)), Edge(Pt(0, 5), Pt(3, 0))])]
V testpoints = [Pt(5, 5), Pt(5, 8),
Pt(-10, 5), Pt(0, 5),
Pt(10, 5), Pt(8, 5),
Pt(10, 10)]
print("\n TESTING WHETHER POINTS ARE WITHIN POLYGONS")
L(poly) polys
polypp(poly)
print( testpoints[0.<3].map(p -> #.: #..format(p, I ispointinside(p, @poly) {True} E False)).join("\t"))
print( testpoints[3.<6].map(p -> #.: #..format(p, I ispointinside(p, @poly) {True} E False)).join("\t"))
print( testpoints[6.. ].map(p -> #.: #..format(p, I ispointinside(p, @poly) {True} E False)).join("\t"))