Skip to content

Commit 2720df1

Browse files
authored
Merge pull request #168 from ScriptLineStudios/polygon.as_segments
Polygon `as_segments()`
2 parents 8162911 + 5ab8139 commit 2720df1

File tree

5 files changed

+69
-2
lines changed

5 files changed

+69
-2
lines changed

docs/polygon.rst

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -157,6 +157,15 @@ Polygon Methods
157157

158158
.. ## Polygon.collidepoint ##
159159
160+
.. method:: as_segments
161+
162+
| :sl:`returns the line segments of the polygon`
163+
| :sg:`as_segments() -> list[Line]`
164+
165+
Returns a list of the line segments of the polygon given as self.
166+
167+
.. ## Polygon.as_segments ##
168+
160169
.. method:: copy
161170

162171
| :sl:`returns a copy of the polygon`

geometry.pyi

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -215,6 +215,8 @@ class Polygon:
215215
@overload
216216
def move(self, move_by: Coordinate) -> Polygon: ...
217217
@overload
218+
def as_segments(self) -> List[Line]: ...
219+
@overload
218220
def move_ip(self, x: float, y: float) -> None: ...
219221
@overload
220222
def move_ip(self, move_by: Coordinate) -> None: ...

src_c/geometry.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -581,3 +581,4 @@ MODINIT_DEFINE(geometry)
581581
}
582582
return module;
583583
}
584+

src_c/polygon.c

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -773,6 +773,33 @@ pg_polygon_move(pgPolygonObject *self, PyObject *const *args, Py_ssize_t nargs)
773773
return (PyObject *)ret;
774774
}
775775

776+
static PyObject *
777+
pg_polygon_as_segments(pgPolygonObject *self, PyObject *_null) {
778+
double *vertices = self->polygon.vertices;
779+
Py_ssize_t verts_num = self->polygon.verts_num;
780+
Py_ssize_t verts_num_double = verts_num * 2;
781+
782+
PyObject *list = PyList_New(verts_num);
783+
if (!list) {
784+
return NULL;
785+
}
786+
787+
for (Py_ssize_t i = 0; i < verts_num; i++) {
788+
Py_ssize_t i2 = i * 2;
789+
PyObject *line = pgLine_New4(vertices[i2], vertices[i2 + 1],
790+
vertices[(i2 + 2) % verts_num_double],
791+
vertices[(i2 + 3) % verts_num_double]);
792+
if (!line) {
793+
Py_DECREF(list);
794+
return NULL;
795+
}
796+
797+
PyList_SET_ITEM(list, i, line);
798+
}
799+
800+
return list;
801+
}
802+
776803
static PyObject *
777804
pg_polygon_move_ip(pgPolygonObject *self, PyObject *const *args,
778805
Py_ssize_t nargs)
@@ -1135,6 +1162,7 @@ pg_polygon_is_convex(pgPolygonObject *self, PyObject *_null)
11351162
}
11361163

11371164
static struct PyMethodDef pg_polygon_methods[] = {
1165+
{"as_segments", (PyCFunction)pg_polygon_as_segments, METH_NOARGS, NULL},
11381166
{"move", (PyCFunction)pg_polygon_move, METH_FASTCALL, NULL},
11391167
{"move_ip", (PyCFunction)pg_polygon_move_ip, METH_FASTCALL, NULL},
11401168
{"rotate", (PyCFunction)pg_polygon_rotate, METH_O, NULL},
@@ -1454,4 +1482,4 @@ static PyTypeObject pgPolygon_Type = {
14541482
.tp_getset = pg_polygon_getsets,
14551483
.tp_init = (initproc)pg_polygon_init,
14561484
.tp_new = pg_polygon_new,
1457-
};
1485+
};

test/test_polygon.py

Lines changed: 28 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
from pygame import Vector2, Vector3, Rect
55

66
import geometry
7-
from geometry import Polygon
7+
from geometry import Polygon, Line
88

99
import math
1010

@@ -582,6 +582,33 @@ def test__repr__(self):
582582
self.assertEqual(repr(polygon), p_repr)
583583
self.assertEqual(polygon.__repr__(), p_repr)
584584

585+
def test_as_segments(self):
586+
"""Checks whether polygon segments are correct"""
587+
poly = Polygon([(0, 0), (1, 0), (1, 1), (0, 1)])
588+
self.assertEqual(
589+
poly.as_segments(),
590+
[
591+
Line((0, 0), (1, 0)),
592+
Line((1, 0), (1, 1)),
593+
Line((1, 1), (0, 1)),
594+
Line((0, 1), (0, 0)),
595+
],
596+
)
597+
poly = Polygon([(123.23, 35.6), (56.4, 87.45), (43.1, 12.3)])
598+
self.assertEqual(
599+
poly.as_segments(),
600+
[
601+
Line((123.23, 35.6), (56.4, 87.45)),
602+
Line((56.4, 87.45), (43.1, 12.3)),
603+
Line((43.1, 12.3), (123.23, 35.6)),
604+
],
605+
)
606+
poly = Polygon([[1, 2], [3, 4], [5, 6]])
607+
self.assertEqual(
608+
poly.as_segments(),
609+
[Line((1, 2), (3, 4)), Line((3, 4), (5, 6)), Line((5, 6), (1, 2))],
610+
)
611+
585612
def test_move_xy(self):
586613
"""Checks whether polygon move function works correctly with an x-y pair."""
587614
poly = Polygon(_some_vertices.copy())

0 commit comments

Comments
 (0)