diff --git a/Quik/VertexGenerator/VertexCommandEngine.cs b/Quik/VertexGenerator/VertexCommandEngine.cs index 2d827ae..e62ad30 100644 --- a/Quik/VertexGenerator/VertexCommandEngine.cs +++ b/Quik/VertexGenerator/VertexCommandEngine.cs @@ -30,9 +30,10 @@ namespace Quik.VertexGenerator switch(name) { - case Command.Line: LineProc(queue); break; - default: - break; + case Command.Line: LineProc(queue); break; + case Command.Bezier: BezierProc(queue); break; + case Command.Rectangle: RectangleProc(queue); break; + default: break; } } @@ -389,6 +390,610 @@ namespace Quik.VertexGenerator return new LineInfo(vbase, 0, 1, index - 2, index - 1); } + private readonly List RectangleList = new List(); + private void RectangleProc(CommandQueue queue) + { + Frame frame = queue.Dequeue(); + RectangleList.Clear(); + if (frame.Type == FrameType.IVec1) + { + int count = (int)frame; + for (int i = 0; i < count; i++) + { + frame = queue.Dequeue(); + RectangleList.Add((QuikRectangle)frame); + } + } + else + { + RectangleList.Add((QuikRectangle)frame); + } + + float stroke = Style.StrokeWidth ?? 1.0f; + float radius = (float?)Style["radius"] ?? 0.0f; // TODO: not this. + DrawQueue.StartDrawCall(Viewport); + for (int i = 0; i < RectangleList.Count; i++) + { + QuikRectangle outer = RectangleList[i]; + QuikRectangle inner = new QuikRectangle( + outer.Right - stroke, outer.Top - stroke, + outer.Left + stroke, outer.Bottom + stroke); + + GenerateRectangleBase(inner, Math.Max(radius - stroke, 0.0f)); + + if (stroke == 0.0f) + continue; + if (radius == 0.0f) + { + GenerateRectangleStripStraight(outer); + } + else if (radius < stroke) + { + GenerateRectangleStripNarrow(outer, radius); + } + else + { + GenerateRectangleStripWide(outer, radius); + } + } + DrawQueue.EndDrawCall(); + } + + private void GenerateRectangleBase(in QuikRectangle rectangle, float radius) + { + /* + +--j-------i--+ + |NW| N |NE| + k--d-------c--h + | | | | + |W | C | E| + | | | | + l--a-------b--g + |SW| S |SE| + +--e-------f--+ + + a b c d e f g h i j k l + 0 1 2 3 4 5 6 7 8 9 10 11 + */ + + DrawQueue.RestoreOffset(); + + // Draw center rectangle. + + QuikVec2 aPos, bPos, cPos, dPos; + + QuikVertex v = FillVertex; + aPos = v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + bPos = v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + cPos = v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Top - radius); + DrawQueue.AddVertex(v); + dPos = v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Top - radius); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(0); DrawQueue.AddElement(1); DrawQueue.AddElement(2); + DrawQueue.AddElement(1); DrawQueue.AddElement(2); DrawQueue.AddElement(3); + + if (radius == 0.0f) + return; + + // Draw south rectangle. + + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Bottom); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Bottom); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(4); DrawQueue.AddElement(5); DrawQueue.AddElement(1); + DrawQueue.AddElement(4); DrawQueue.AddElement(1); DrawQueue.AddElement(0); + + // Draw east rectangle. + + v.Position = new QuikVec2(rectangle.Right, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Top - radius); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(1); DrawQueue.AddElement(6); DrawQueue.AddElement(7); + DrawQueue.AddElement(1); DrawQueue.AddElement(7); DrawQueue.AddElement(3); + + // Draw north rectangle. + + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Top); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Top); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(3); DrawQueue.AddElement(2); DrawQueue.AddElement(8); + DrawQueue.AddElement(3); DrawQueue.AddElement(8); DrawQueue.AddElement(0); + + // Draw west rectangle. + + v.Position = new QuikVec2(rectangle.Left, rectangle.Top - radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(11); DrawQueue.AddElement(0); DrawQueue.AddElement(3); + DrawQueue.AddElement(11); DrawQueue.AddElement(3); DrawQueue.AddElement(10); + + // Draw north east corner. + + int resolution = GetRoundingResolution(radius, 0.5f * MathF.PI); + int previous = 7, current = 12; + + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = MathF.Cos(theta) * radius; + float yoff = MathF.Sin(theta) * radius; + + v.Position = cPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(2); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(2); DrawQueue.AddElement(previous); DrawQueue.AddElement(8); + + // Draw the north west corner. + + previous = 9; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Sin(theta) * radius; + float yoff = MathF.Cos(theta) * radius; + + v.Position = dPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(3); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(3); DrawQueue.AddElement(previous); DrawQueue.AddElement(10); + + // Draw south west corner. + + previous = 11; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Cos(theta) * radius; + float yoff = -MathF.Sin(theta) * radius; + + v.Position = aPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(0); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(0); DrawQueue.AddElement(previous); DrawQueue.AddElement(4); + + // Draw the south east corner. + + previous = 5; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Sin(theta) * radius; + float yoff = MathF.Cos(theta) * radius; + + v.Position = bPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(1); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(1); DrawQueue.AddElement(previous); DrawQueue.AddElement(6); + } + + private void GenerateRectangleStripStraight(in QuikRectangle rectangle) + { + /* + h---------g + |\ N /| + | \ / | + | d---c | + |W | | E| + | a---b | + | / \ | + |/ S \| + e---------f + + a b c d e f g h + 0 1 2 3 4 5 6 7 + */ + + QuikVertex v = StrokeVertex; + float stroke = Style.StrokeWidth ?? 1.0f; + + DrawQueue.RestoreOffset(); + + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + + v.Position = new QuikVec2(rectangle.Left, rectangle.Bottom); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Bottom); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Top); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left, rectangle.Top); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(4); DrawQueue.AddElement(5); DrawQueue.AddElement(1); // SSW + DrawQueue.AddElement(4); DrawQueue.AddElement(1); DrawQueue.AddElement(0); // SSE + DrawQueue.AddElement(1); DrawQueue.AddElement(5); DrawQueue.AddElement(6); // SEE + DrawQueue.AddElement(1); DrawQueue.AddElement(6); DrawQueue.AddElement(2); // NEE + DrawQueue.AddElement(3); DrawQueue.AddElement(2); DrawQueue.AddElement(6); // NNE + DrawQueue.AddElement(3); DrawQueue.AddElement(6); DrawQueue.AddElement(7); // NNW + DrawQueue.AddElement(4); DrawQueue.AddElement(0); DrawQueue.AddElement(3); // NWW + DrawQueue.AddElement(4); DrawQueue.AddElement(3); DrawQueue.AddElement(7); // SWW + } + + private void GenerateRectangleStripNarrow(in QuikRectangle rectangle, float radius) + { + /* + v-j---i-u + | | | | + x-w | N | t-s + | \| |/ | + k---d---c---h + | | | | + | W | | E | + | | | | + l---a---b---g + | /| |\ | + m-n | S | q-r + | | | | + o-e---f-p + + a b c d e f g h i j + 00: 0 1 2 3 4 5 6 7 8 9 + k l m n o p q r s t + 10: 0 1 2 3 4 5 6 7 8 9 + u v w x + 20: 0 1 2 3 + */ + QuikVertex v = StrokeVertex; + QuikVec2 nPos, qPos, tPos, wPos; + float stroke = Style.StrokeWidth ?? 1.0f; + + DrawQueue.RestoreOffset(); + + // a-b-c-d + + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + + // ef-gh-ij-kl + + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Bottom); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Bottom); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Top); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Top); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + + // mno + + v.Position = new QuikVec2(rectangle.Left, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + nPos = v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Bottom); + DrawQueue.AddVertex(v); + + // pqr + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Bottom); + DrawQueue.AddVertex(v); + qPos = v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + + // stu + v.Position = new QuikVec2(rectangle.Right, rectangle.Top - radius); + DrawQueue.AddVertex(v); + tPos = v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Top - radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Top); + DrawQueue.AddVertex(v); + + // vwx + + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Top); + DrawQueue.AddVertex(v); + wPos = v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Top - radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left, rectangle.Top - radius); + DrawQueue.AddVertex(v); + + // E + DrawQueue.AddElement(1); DrawQueue.AddElement(6); DrawQueue.AddElement(7); + DrawQueue.AddElement(1); DrawQueue.AddElement(7); DrawQueue.AddElement(2); + + // N + DrawQueue.AddElement(3); DrawQueue.AddElement(2); DrawQueue.AddElement(8); + DrawQueue.AddElement(3); DrawQueue.AddElement(8); DrawQueue.AddElement(9); + + // W + DrawQueue.AddElement(11); DrawQueue.AddElement(0); DrawQueue.AddElement(3); + DrawQueue.AddElement(11); DrawQueue.AddElement(3); DrawQueue.AddElement(10); + + // S + DrawQueue.AddElement(4); DrawQueue.AddElement(5); DrawQueue.AddElement(1); + DrawQueue.AddElement(4); DrawQueue.AddElement(1); DrawQueue.AddElement(0); + + // NEE + DrawQueue.AddElement(2); DrawQueue.AddElement(7); DrawQueue.AddElement(18); + DrawQueue.AddElement(2); DrawQueue.AddElement(18); DrawQueue.AddElement(19); + // NNE + DrawQueue.AddElement(2); DrawQueue.AddElement(19); DrawQueue.AddElement(20); + DrawQueue.AddElement(2); DrawQueue.AddElement(20); DrawQueue.AddElement(8); + + // NNW + DrawQueue.AddElement(22); DrawQueue.AddElement(3); DrawQueue.AddElement(19); + DrawQueue.AddElement(22); DrawQueue.AddElement(19); DrawQueue.AddElement(21); + // NWW + DrawQueue.AddElement(10); DrawQueue.AddElement(3); DrawQueue.AddElement(22); + DrawQueue.AddElement(10); DrawQueue.AddElement(22); DrawQueue.AddElement(23); + + // SWW + DrawQueue.AddElement(12); DrawQueue.AddElement(13); DrawQueue.AddElement(0); + DrawQueue.AddElement(12); DrawQueue.AddElement(0); DrawQueue.AddElement(11); + // SSW + DrawQueue.AddElement(14); DrawQueue.AddElement(4); DrawQueue.AddElement(0); + DrawQueue.AddElement(14); DrawQueue.AddElement(0); DrawQueue.AddElement(13); + + // NE + + int resolution = GetRoundingResolution(radius, 0.5f * MathF.PI); + int previous = 18, current = 24; + + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = MathF.Cos(theta) * radius; + float yoff = MathF.Sin(theta) * radius; + + v.Position = tPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(19); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(19); DrawQueue.AddElement(previous); DrawQueue.AddElement(20); + + // NW + + previous = 21; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Sin(theta) * radius; + float yoff = MathF.Cos(theta) * radius; + + v.Position = wPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(22); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(22); DrawQueue.AddElement(previous); DrawQueue.AddElement(23); + + // SW + + previous = 12; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Cos(theta) * radius; + float yoff = -MathF.Sin(theta) * radius; + + v.Position = nPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(23); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(23); DrawQueue.AddElement(previous); DrawQueue.AddElement(14); + + // SE + + previous = 15; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Sin(theta) * radius; + float yoff = MathF.Cos(theta) * radius; + + v.Position = qPos + new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + DrawQueue.AddElement(16); DrawQueue.AddElement(previous); DrawQueue.AddElement((previous = current++)); + } + DrawQueue.AddElement(16); DrawQueue.AddElement(previous); DrawQueue.AddElement(17); + } + + private void GenerateRectangleStripWide(in QuikRectangle rectangle, float radius) + { + /* + l---k + | N | + i---j + p---o h---g + | W | | E | + m---n e---f + d---c + | S | + a---b + + a b c d e f g h i j + 00: 0 1 2 3 4 5 6 7 8 9 + k l m n o p q r s t + 10: 0 1 2 3 4 5 + */ + + QuikVertex v = StrokeVertex; + float stroke = Style.StrokeWidth ?? 1.0f; + float innerRadius = radius - stroke; + DrawQueue.RestoreOffset(); + + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Bottom); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Bottom); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Bottom + stroke); + DrawQueue.AddVertex(v); + + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Top - radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right, rectangle.Top - radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - stroke, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Top - stroke); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Right - radius, rectangle.Top); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + radius, rectangle.Top); + DrawQueue.AddVertex(v); + + v.Position = new QuikVec2(rectangle.Left, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Top - radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left + stroke, rectangle.Top - radius); + DrawQueue.AddVertex(v); + v.Position = new QuikVec2(rectangle.Left, rectangle.Bottom + radius); + DrawQueue.AddVertex(v); + + // S + DrawQueue.AddElement(0); DrawQueue.AddElement(1); DrawQueue.AddElement(2); + DrawQueue.AddElement(0); DrawQueue.AddElement(2); DrawQueue.AddElement(3); + // E + DrawQueue.AddElement(4); DrawQueue.AddElement(5); DrawQueue.AddElement(6); + DrawQueue.AddElement(4); DrawQueue.AddElement(6); DrawQueue.AddElement(7); + // N + DrawQueue.AddElement(8); DrawQueue.AddElement(9); DrawQueue.AddElement(10); + DrawQueue.AddElement(8); DrawQueue.AddElement(10); DrawQueue.AddElement(11); + // W + DrawQueue.AddElement(12); DrawQueue.AddElement(13); DrawQueue.AddElement(14); + DrawQueue.AddElement(12); DrawQueue.AddElement(14); DrawQueue.AddElement(15); + + // Draw NE arc. + int resolution = GetRoundingResolution(radius, 0.5f * MathF.PI); + int current = 16; + + QuikVec2 center = new QuikVec2(rectangle.Right - radius, rectangle.Top - radius); + int s1 = 7, s2 = 6; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = MathF.Cos(theta); + float yoff = MathF.Sin(theta); + + v.Position = center + radius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + v.Position = center + innerRadius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 0); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 1); + + s1 = current; s2 = current + 1; + current += 2; + } + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(10); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(9); + + // Draw NW arc + center = new QuikVec2(rectangle.Left + radius, rectangle.Top - radius); + s1 = 8; s2 = 11; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Sin(theta); + float yoff = MathF.Cos(theta); + + v.Position = center + radius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + v.Position = center + innerRadius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 0); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 1); + + s1 = current; s2 = current + 1; + current += 2; + } + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(15); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(14); + + // Draw SW arc + center = new QuikVec2(rectangle.Left + radius, rectangle.Bottom + radius); + s1 = 13; s2 = 12; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = -MathF.Cos(theta); + float yoff = -MathF.Sin(theta); + + v.Position = center + radius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + v.Position = center + innerRadius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 0); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 1); + + s1 = current; s2 = current + 1; + current += 2; + } + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(0); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(3); + + // Draw SW arc + center = new QuikVec2(rectangle.Right - radius, rectangle.Bottom + radius); + s1 = 2; s2 = 1; + for (int i = 0; i < resolution - 1; i++) + { + float theta = (i + 1.0f) / (resolution + 1); + float xoff = MathF.Sin(theta); + float yoff = -MathF.Cos(theta); + + v.Position = center + radius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + v.Position = center + innerRadius * new QuikVec2(xoff, yoff); + DrawQueue.AddVertex(v); + + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 0); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(current + 1); + + s1 = current; s2 = current + 1; + current += 2; + } + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(5); + DrawQueue.AddElement(s1); DrawQueue.AddElement(s2); DrawQueue.AddElement(4); + } + private struct LineInfo { public int BaseOffset { get; }