/// <summary> /// Renders the glyph to the render surface in font units relative to a bottom left origin at (0,0) /// </summary> /// <param name="surface">The surface.</param> /// <param name="pointSize">Size of the point.</param> /// <param name="location">The location.</param> /// <param name="dpi">The dpi.</param> /// <exception cref="System.NotSupportedException">Too many control points</exception> public void RenderTo(IGlyphRenderer surface, float pointSize, Vector2 location, Vector2 dpi) { location = location * dpi; int pointIndex = 0; var scaleFactor = (float)(this.sizeOfEm * 72f); surface.BeginGlyph(); Vector2 firstPoint = Vector2.Zero; Vector2 scale = new Vector2(1, -1); for (int i = 0; i < this.endPoints.Length; i++) { int nextContour = this.endPoints[i] + 1; bool isFirstPoint = true; ControlPointCollection points = new ControlPointCollection(); bool justFromCurveMode = false; for (; pointIndex < nextContour; ++pointIndex) { var point = location + (scale * ((this.controlPoints[pointIndex] * pointSize * dpi) / scaleFactor)); // scale each point as we go, w will now have the correct relative point size if (this.onCurves[pointIndex]) { // on curve if (justFromCurveMode) { points = DrawPoints(surface, points, point); } else { if (isFirstPoint) { isFirstPoint = false; firstPoint = point; surface.MoveTo(firstPoint); } else { surface.LineTo(point); } } } else { switch (points.Count) { case 0: points.Add(point); break; case 1: // we already have prev second control point // so auto calculate line to // between 2 point Vector2 mid = (points.SecondControlPoint + point) / 2; surface.QuadraticBezierTo( points.SecondControlPoint, mid); points.SecondControlPoint = point; //replace 2nd break; default: throw new NotSupportedException("Too many control points"); } } justFromCurveMode = !this.onCurves[pointIndex]; } // close figure // if in curve mode if (justFromCurveMode) { DrawPoints(surface, points, firstPoint); } surface.EndFigure(); } surface.EndGlyph(); }