Skip to content

Instantly share code, notes, and snippets.

@robban
Forked from ChrisBarker-NOAA/poly_clockwise.py
Last active December 22, 2022 15:35
Show Gist options
  • Save robban/c5718d68be29c6752fdb0beeb568cec4 to your computer and use it in GitHub Desktop.
Save robban/c5718d68be29c6752fdb0beeb568cec4 to your computer and use it in GitHub Desktop.
clockwise tests for polygons
#!/usr/bin/env python
"""
code for checking if a polygon is cockwise or counter-clockwise
There are two versions:
is_clockwise_convex only works for convex polygons -- but is faster,
it only needs to check three points.
is_clockwise checks all points, but works for convex and cocave
(note: that's the same as the area calculation)
from:
http://paulbourke.net/geometry/clockwise/
"""
def is_clockwise(poly):
"""
returns True if the polygon is clockwise ordered, false if not
expects a sequence of tuples, or something like it (Nx2 array for instance),
of the points:
[ (x1, y1), (x2, y2), (x3, y3), ...(xi, yi) ]
See: http://paulbourke.net/geometry/clockwise/
"""
total = poly[-1][0] * poly[0][1] - poly[0][0] * poly[-1][1] # last point to first point
for i in range(len(poly) - 1):
total += poly[i][0] * poly[i + 1][1] - poly[i + 1][0] * poly[i][1]
if total <= 0:
return True
else:
return False
def is_clockwise_convex(poly):
"""
returns True if the polygon is clockwise ordered, false if not
expects a sequence of tuples, or something like it, of the points:
[ (x1, y1), (x2, y2), (x3, y3), ...(xi, yi) ]
This only works for concave polygons. See:
http://paulbourke.net/geometry/clockwise/
"""
x0 = poly[0][0]
y0 = poly[0][1]
x1 = poly[1][0]
y1 = poly[1][1]
x2 = poly[2][0]
y2 = poly[2][1]
cp = (x1 - x0) * (y2 - y1) - (y1 - y0) * (x2 - x1)
if cp <= 0:
return True
else:
return False
#!/usr/bin/env python
import unittest
import numpy as np
from poly_clockwise import is_clockwise_convex, is_clockwise
class TestClockwise(unittest.TestCase):
# CCW
triangle_ccw = np.array(((-2, -2),
(3, 3),
(0, 4)),
dtype=np.float64)
# CW
triangle_cw = triangle_ccw[::-1]
# counter clockwise polygon:
polygon_ccw = np.array(((-5, -2),
(3, -1),
(5, -1),
(5, 4),
(3, 0),
(0, 0),
(-2, 2),
(-5, 2),
), dtype=np.float64)
# clockwise polygon:
polygon_cw = polygon_ccw[::-1]
def test_convex_cw(self):
assert is_clockwise_convex(self.triangle_cw)
def test_convex_ccw(self):
assert not is_clockwise_convex(self.triangle_ccw)
def test_any_cw(self):
assert is_clockwise(self.triangle_cw)
def test_any_ccw(self):
assert not is_clockwise(self.triangle_ccw)
def test_poly_cw(self):
assert is_clockwise(self.polygon_cw)
def test_poly_ccw(self):
assert not is_clockwise(self.polygon_ccw)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment