Search code examples
asp.netvb.netsystem.drawing

Drawing.Font appears thinner with each use


I am dynamically adding text to an existing image. What I am finding strange though is that with each use of the pen/brush/font I am using, the text appears to get thinner.

It may be easier to see a snippet of the code.

There are some variables in use in the code below, that are not declared in the code below - this is a snippet of a large chunk of code much of which is irrelevant to the question. This part is what writes the text.

Ultimately all the resources are created as using blocks.

then we get down to the AddTextToGraphicsPath() method - which is shown below. This simply applies the text to the path.

Using fiTextFont As New Font("Arial"), FontStyle.Bold)
Using brush As Brush = New SolidBrush(ColorTranslator.FromHtml("#000000"))
    Using pen As Pen = New Pen(ColorTranslator.FromHtml("transparent"))
        Using oImage As Image = Image.FromFile(fName)
          Using grfx As Graphics = Graphics.FromImage(oImage)
            For i As Integer = 0 To loopCount
                Using gPath As GraphicsPath = New GraphicsPath()
                    grfx.SmoothingMode = Drawing2D.SmoothingMode.HighQuality
                    grfx.TextRenderingHint = Drawing.Text.TextRenderingHint.ClearTypeGridFit
                    grfx.CompositingQuality = CompositingQuality.HighQuality
                    Dim sFormat As New StringFormat(StringFormat.GenericTypographic)
                    sFormat.Alignment = StringAlignment.Center
                    Dim textSplit() As String = fiText.Split(vbCrLf)
                    AddTextToGraphicsPath(gPath, grfx, textSplit(0).Replace(vbLf, ""), fiTextFont, fxPos, fyPos, pen, brush, Nothing, sFormat)
                    AddTextToGraphicsPath(gPath, grfx, textSplit(1).Replace(vbLf, ""), fiTextFont, fxPos, fyPos + fiTextFont.Size - 2, pen, brush, Nothing, sFormat)
                End Using
            Next
          End Using
        End Using
    End Using
End Using

End Using

And here is the method which applies the text to the path.

Private Shared Sub AddTextToGraphicsPath(ByRef gPath As GraphicsPath, ByRef grfx As Graphics, ByRef text As String, ByRef font As Font, ByRef x As Single, ByRef y As Single, ByRef pen As Pen, ByRef brush As Brush, ByRef matrix As Matrix, ByRef sFormat As StringFormat)
    gPath.AddString(text, font.FontFamily, font.Style, font.Size, New PointF(x, y), sFormat)
    If (matrix IsNot Nothing) Then gPath.Transform(matrix)
    grfx.DrawPath(pen, gPath)
    grfx.FillPath(brush, gPath)
End Sub

Eveything works perfectly well - text is applied in the correct position and with the correct font etc, though the second line seems to be a lot lighter in weight.

If i set the font to Bold the first line is bold, second "appears" to be regular, though stepping through the code i can see that the font does not change.

And the resulting image looks a little something like the example below:

My image - with apparent thinner second line...

UPDATE

I have now tried the same code, but created new font,pen, brush for each of the calls to AddTestToGraphicsPath and it still does the same; so wondering if this is an issue with GraphicsPath.AddString() ?


Solution

  • Ok - This had been driving me mad for the last couple of days.

    Typically, within an hour or so of posting this question I managed to resolve the issue.

    I needed to perform a reset on the GraphicsPath before applying my string.

    Not 100% sure WHY this causes an issue, though it for sure resolved the issue.

    I believe that the reason it happens is that the strings path data from the first path is still present when adding the second string. the grfx.FillPath method is then applying a fill twice to the first one.

    So just before adding the string I simply put gPath.Reset() - this ensures that the graphicspath - which is passed by ByRef is reset for the next string to be added.