void AddSolidRoundedRect(float x, float y, float w, float h, float r)
        {
            if (_nextDrawCallIndex < MaxDrawCalls) {

                EnsureRoomForVertices (12);

                var b = _buffers[_currentBufferIndex];
                var i = b.Length;

                // At each corner, we put a little spike so that there
                // is no seam between this and the corner arcs. (See FillRoundedRect)
                // cr = r - ((r/2) + (r*cos45))/2
                // cr = r * (1 - 0.25 - Cos45/2)
                var cr = r * (1 - 0.25f - Cos45/2);

                var ri = x + w;
                var bo = y + h;

                b.Positions[i] = new Vector2 (x + cr, y + cr);
                b.Positions[i + 1] = new Vector2 (x, y + r);
                b.Positions[i + 2] = new Vector2 (x, bo - r);
                b.Positions[i + 3] = new Vector2 (x + cr, bo - cr);
                b.Positions[i + 4] = new Vector2 (x + r, bo);
                b.Positions[i + 5] = new Vector2 (ri - r, bo);
                b.Positions[i + 6] = new Vector2 (ri - cr, bo - cr);
                b.Positions[i + 7] = new Vector2 (ri, bo - r);
                b.Positions[i + 8] = new Vector2 (ri, y + r);
                b.Positions[i + 9] = new Vector2 (ri - cr, y + cr);
                b.Positions[i + 10] = new Vector2 (ri - r, y);
                b.Positions[i + 11] = new Vector2 (x + r, y);

                var col = _color;
                for (var j = 0; j < 12; j++) {
                    b.Colors[i + j] = col;
                }

                b.Length += 12;

                var call = new OpenGLDrawArrayCall {
                    Operation = All.TriangleFan,
                    BufferIndex = (byte)_currentBufferIndex,
                    Offset = (ushort)i,
                    NumVertices = 12,
                    Texture = null,
                };

                _calls[_nextDrawCallIndex] = call;
                _nextDrawCallIndex++;
            }
        }
        void AddShape(OpenGLShape shape, float x, float y)
        {
            var tex = shape.TextureReference;

            if (tex != null && tex.Texture != null && _nextDrawCallIndex < MaxDrawCalls) {

                //
                // Remember which shapes we're drawing so that they
                // can be rendered into their textures
                //
                if (!_frameShapes.ContainsKey (shape)) {
                    _frameShapes.Add (shape, shape);
                }

                //
                // Get a buffer with enough space
                //
                EnsureRoomForVertices (4);
                var b = _buffers[_currentBufferIndex];
                var i = b.Length;

                //
                // The position must be computed such that the point
                // ShapeOffset is aligned to x, y
                //
                var tx = x - tex.ShapeOffset.X;
                var ty = y - tex.ShapeOffset.Y;
                b.Positions[i] = new Vector2 (tx, ty);
                b.Positions[i + 1] = new Vector2 (tx, ty + tex.Height);
                b.Positions[i + 2] = new Vector2 (tx + tex.Width, ty + tex.Height);
                b.Positions[i + 3] = new Vector2 (tx + tex.Width, ty);

                //
                // TexCoords and Color are simple, you should be able to understand them ;-)
                //
                b.TexCoords[i] = new Vector2 (tex.U, tex.V);
                b.TexCoords[i + 1] = new Vector2 (tex.U, tex.V + tex.TexHeight);
                b.TexCoords[i + 2] = new Vector2 (tex.U + tex.TexWidth, tex.V + tex.TexHeight);
                b.TexCoords[i + 3] = new Vector2 (tex.U + tex.TexWidth, tex.V);

                b.Colors[i] = _color;
                b.Colors[i + 1] = _color;
                b.Colors[i + 2] = _color;
                b.Colors[i + 3] = _color;

                b.Length += 4;

                //
                // Record the draw call
                //
                var call = new OpenGLDrawArrayCall {
                    Operation = All.TriangleFan,
                    BufferIndex = (byte)_currentBufferIndex,
                    Offset = (ushort)i,
                    NumVertices = 4,
                    Texture = tex.Texture,
                };
                _calls[_nextDrawCallIndex] = call;
                _nextDrawCallIndex++;
            }
        }
        void AddSolidRect(float x, float y, float width, float height, float alpha = 1)
        {
            if (_nextDrawCallIndex < MaxDrawCalls) {

                EnsureRoomForVertices (4);

                var b = _buffers[_currentBufferIndex];
                var i = b.Length;

                b.Positions[i] = new Vector2 (x, y);
                b.Positions[i + 1] = new Vector2 (x, y + height);
                b.Positions[i + 2] = new Vector2 (x + width, y + height);
                b.Positions[i + 3] = new Vector2 (x + width, y);

                var col = _color;
                if (alpha <= 0.9961f) {
                    col.A = (byte)(col.A * alpha);
                }

                b.Colors[i] = col;
                b.Colors[i + 1] = col;
                b.Colors[i + 2] = col;
                b.Colors[i + 3] = col;

                b.Length += 4;

                var call = new OpenGLDrawArrayCall {
                    Operation = All.TriangleFan,
                    BufferIndex = (byte)_currentBufferIndex,
                    Offset = (ushort)i,
                    NumVertices = 4,
                    Texture = null,
                };

                _calls[_nextDrawCallIndex] = call;
                _nextDrawCallIndex++;
            }
        }
        void AddLine(float sx, float sy, float ex, float ey, float w, float alpha = 1)
        {
            if (_nextDrawCallIndex < MaxDrawCalls) {

                EnsureRoomForVertices (3);

                var b = _buffers[_currentBufferIndex];
                var i = b.Length;

                b.Positions[i] = new Vector2 (sx, sy);
                b.Positions[i + 1] = new Vector2 (ex, ey);
                b.Positions[i + 2] = new Vector2 (w * _zoom, 0); // Used to store info

                var col = _color;
                if (alpha <= 0.9961f) {
                    col.A = (byte)(col.A * alpha);
                }

                b.Colors[i] = col;
                b.Colors[i + 1] = col;

                b.Length += 3;

                var call = new OpenGLDrawArrayCall {
                    Operation = All.Lines,
                    BufferIndex = (byte)_currentBufferIndex,
                    Offset = (ushort)i,
                    NumVertices = 2,
                    Texture = null,
                };

                _calls[_nextDrawCallIndex] = call;
                _nextDrawCallIndex++;
            }
        }