A game framework written with osu! in mind.
at master 67 lines 3.4 kB view raw
1// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. 2// See the LICENCE file in the repository root for full licence text. 3 4using System; 5using osu.Framework.Graphics.Primitives; 6using osuTK; 7 8namespace osu.Framework.Extensions.PolygonExtensions 9{ 10 public static class PolygonExtensions 11 { 12 /// <summary> 13 /// Computes the axes for each edge in a polygon. 14 /// </summary> 15 /// <param name="polygon">The polygon to compute the axes of.</param> 16 /// <param name="normalize">Whether the normals should be normalized. Allows computation of the exact intersection point.</param> 17 /// <returns>The axes of the polygon.</returns> 18 public static Span<Vector2> GetAxes<TPolygon>(TPolygon polygon, bool normalize = false) 19 where TPolygon : IPolygon 20 { 21 var axisVertices = polygon.GetAxisVertices(); 22 return getAxes(axisVertices, new Vector2[axisVertices.Length], normalize); 23 } 24 25 /// <summary> 26 /// Computes the axes for each edge in a polygon. 27 /// </summary> 28 /// <param name="polygon">The polygon to compute the axes of.</param> 29 /// <param name="buffer">A buffer to be used as storage for the axes. Must have a length of at least the count of vertices in <paramref name="polygon"/>.</param> 30 /// <param name="normalize">Whether the normals should be normalized. Allows computation of the exact intersection point.</param> 31 /// <returns>The axes of the polygon. Returned as a slice of <paramref name="buffer"/>.</returns> 32 public static Span<Vector2> GetAxes<TPolygon>(this TPolygon polygon, Span<Vector2> buffer, bool normalize = false) 33 where TPolygon : IPolygon 34 => getAxes(polygon.GetAxisVertices(), buffer, normalize); 35 36 /// <summary> 37 /// Computes the axes for a set of vertices. 38 /// </summary> 39 /// <param name="vertices">The vertices to compute the axes for.</param> 40 /// <param name="buffer">A buffer to be used as storage for the axes. Must have a length of at least the count of <paramref name="vertices"/>.</param> 41 /// <param name="normalize">Whether the normals should be normalized. Allows computation of the exact intersection point.</param> 42 /// <returns>The axes represented by <paramref name="vertices"/>. Returned as a slice of <paramref name="buffer"/>.</returns> 43 private static Span<Vector2> getAxes(ReadOnlySpan<Vector2> vertices, Span<Vector2> buffer, bool normalize = false) 44 { 45 if (buffer.Length < vertices.Length) 46 throw new ArgumentException($"Axis buffer must have a length of {vertices.Length}, but was {buffer.Length}.", nameof(buffer)); 47 48 for (int i = 0; i < vertices.Length; i++) 49 { 50 // Construct an edge between two sequential points 51 Vector2 v1 = vertices[i]; 52 Vector2 v2 = vertices[i == vertices.Length - 1 ? 0 : i + 1]; 53 Vector2 edge = v2 - v1; 54 55 // Find the normal to the edge 56 Vector2 normal = new Vector2(-edge.Y, edge.X); 57 58 if (normalize) 59 normal = Vector2.Normalize(normal); 60 61 buffer[i] = normal; 62 } 63 64 return buffer.Slice(0, vertices.Length); 65 } 66 } 67}