使用ObjectListView自定义渲染器时的像素化文本

涟漪

我在网上找到了一个示例,该示例说明如何使用ObjectListView创建名片listview项。它演示了如何使用自定义渲染器手动绘制控件中的每个Tile。

该示例涉及创建缓冲的图形并手动绘制每个项目。我有这项工作,但是,我发现我在图块上绘制的所有文本都看起来像是像素化的(无论使用什么设置),尤其是当我绘制小文本时。例如,在常规形式上使用默认系统字体看起来不错,但在我的渲染器中看起来很枯燥。

代码如下:

Imports BrightIdeasSoftware
Imports System.Drawing.Drawing2D
Imports System.IO

Public Class StoreListRenderer
    Inherits AbstractRenderer
    Public Overrides Function RenderItem(e As DrawListViewItemEventArgs, g As Graphics, itemBounds As Rectangle, rowObject As Object) As Boolean
        ' If we're in any other view than Tile, return false to say that we haven't done
        ' the rendereing and the default process should do it's stuff
        Dim olv As ObjectListView = TryCast(e.Item.ListView, ObjectListView)
        If olv Is Nothing OrElse olv.View <> View.Tile Then
            Return False
        End If

        ' Use buffered graphics to kill flickers
        Dim buffered As BufferedGraphics = BufferedGraphicsManager.Current.Allocate(g, itemBounds)
        g = buffered.Graphics
        g.Clear(olv.BackColor)
        g.SmoothingMode = ObjectListView.SmoothingMode
        g.TextRenderingHint = ObjectListView.TextRenderingHint

        If e.Item.Selected Then
            Me.BorderPen = Pens.White
            Me.HeaderBackBrush = New SolidBrush(olv.HighlightBackgroundColorOrDefault)
        Else
            Me.BorderPen = New Pen(Color.FromArgb(&H33, &H33, &H33))
            Me.HeaderBackBrush = New SolidBrush(Color.FromArgb(&H33, &H33, &H33))
        End If

        DrawStoreCard(g, itemBounds, rowObject, olv, DirectCast(e.Item, OLVListItem))

        ' Finally render the buffered graphics
        buffered.Render()
        buffered.Dispose()

        ' Return true to say that we've handled the drawing
        Return True
    End Function

    Friend BorderPen As New Pen(Color.FromArgb(&H33, &H33, &H33))
    Friend TextBrush As Brush = New SolidBrush(Color.FromArgb(&H22, &H22, &H22))
    Friend HeaderTextBrush As Brush = Brushes.AliceBlue
    Friend HeaderBackBrush As Brush = New SolidBrush(Color.FromArgb(&H33, &H33, &H33))
    Friend BackBrush As Brush = Brushes.LemonChiffon
    Friend BackgroundBrush As Brush = New SolidBrush(Color.FromArgb(38, 38, 38))

    Public Sub DrawStoreCard(g As Graphics, itemBounds As Rectangle, rowObject As Object, olv As ObjectListView, item As OLVListItem)
        Try
            Dim _store As StoreObject = TryCast(rowObject, StoreObject)

            ' Allow a border around the card
            itemBounds.Inflate(-5, -5)
            g.FillRectangle(BackgroundBrush, itemBounds)

            Dim ColouredPanelRect As Rectangle = New Rectangle(itemBounds.Left + 7, itemBounds.Top + 7, 70, 70)
            g.FillRectangle(Brushes.IndianRed, ColouredPanelRect)

            Dim fmt As New StringFormat()
            fmt.Alignment = StringAlignment.Center
            fmt.LineAlignment = StringAlignment.Center

            For i As Integer = 0 To olv.Columns.Count - 1
                Dim column As OLVColumn = olv.GetColumn(i)
                If column.IsTileViewColumn Then

                    'Draw Store Number
                    Using font As New Font(fontMgr("Mentone Lig"), 36, FontStyle.Regular, GraphicsUnit.Pixel)
                        g.TextRenderingHint = Drawing.Text.TextRenderingHint.AntiAliasGridFit
                        g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
                        g.DrawString(_store.StoreID, font, BackgroundBrush, ColouredPanelRect, fmt)
                    End Using

                    'Draw Store Name
                    Using string_format As New StringFormat()
                        string_format.Alignment = StringAlignment.Center
                        string_format.LineAlignment = StringAlignment.Near
                        g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
                        g.TextRenderingHint = Drawing.Text.TextRenderingHint.AntiAliasGridFit
                        g.DrawString(_store.StoreName.ToUpper, New Font("Segoe UI", 9, FontStyle.Regular), Brushes.White, itemBounds, string_format)
                    End Using

...

我尝试过围绕AntiAlias和ClearType玩,但是两者都具有相同的影响。

更新

这是我在以下情况下使用相同大小的相同字体的结果:

在此处输入图片说明

顶部的文本表示放置在表单上的普通标签。底部的文本是使用上面的代码绘制到列表视图项上的文本(在“平铺”模式下)。您可以轻松地识别出差异,并发现它不那么平滑。同样,我使文本越大,它变得越不平滑。我尝试了所有设置,目前设置为:

g.TextRenderingHint = Drawing.Text.TextRenderingHint.ClearTypeGridFit
g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
g.CompositingQuality = Drawing2D.CompositingQuality.HighQuality
g.PixelOffsetMode = PixelOffsetMode.HighQuality

谢谢

涟漪

好的,我最后通过重新研究示例来解决了这个问题。问题是我从代码中删除了比例缩放元素,这似乎导致文本像素化。

通过重新添加以下代码,它已纠正了文本的平滑度:

Dim size As SizeF = g.MeasureString(txt, font, CInt(itemBounds.Width), fmt)
g.TextRenderingHint = Drawing.Text.TextRenderingHint.ClearTypeGridFit

因此,我的总体代码如下所示:

Using font As New Font("Segoe UI", 9, FontStyle.Regular)
     ' Measure the height of the title
     txt = column.GetStringValue(rowObject)
     Dim size As SizeF = g.MeasureString(txt, font, CInt(itemBounds.Width), fmt)
     g.TextRenderingHint = Drawing.Text.TextRenderingHint.ClearTypeGridFit
     g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
     g.CompositingQuality = Drawing2D.CompositingQuality.HighQuality
     g.PixelOffsetMode = PixelOffsetMode.HighQuality
     g.DrawString(txt, font, Brushes.LightGray, itemBounds, fmt)
End Using

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章