3

按照此处的代码,我试图弯曲矩形的边缘,使其不完全是正方形。

它现在的样子的一个例子:

在此处输入图像描述

我正在寻找它做什么:

在此处输入图像描述

使用此代码:

Using br As New SolidBrush(solidBGColor)
   Dim r As New RectangleF(0, 0, myPictureBox.Width, myPictureBox.Height)
   Dim gp As New System.Drawing.Drawing2D.GraphicsPath()
   Dim d As Integer = 5

   gp.AddArc(r.X, r.Y, imgSizeWH(0), imgSizeWH(1), 180, 90)
   gp.AddArc(r.X + r.Width - d, r.Y, imgSizeWH(0), imgSizeWH(1), 270, 90)
   gp.AddArc(r.X + r.Width - d, r.Y + r.Height - d, imgSizeWH(0), imgSizeWH(1), 0, 90)
   gp.AddArc(r.X, r.Y + r.Height - d, imgSizeWH(0), imgSizeWH(1), 90, 90)

   g.FillPath(br, gp)
End Using

我有一个看起来不正确的图像:

在此处输入图像描述

完整代码:

Private Function CreateLabeledAvatar(av As Image, text As String) As Image
    Dim imgSizeWH() As Integer = {800, 800}
    Dim bmp As New Bitmap(imgSizeWH(0), imgSizeWH(1))
    Dim solidBGColor As Color = DirectCast(New ColorConverter().ConvertFromString("#" + _BackgroundColours(New Random().[Next](0, _BackgroundColours.Count - 1))), Color)

    Using g As Graphics = Graphics.FromImage(bmp)
        Using br As New SolidBrush(solidBGColor)
            Dim r As New RectangleF(0, 0, myPictureBox.Width, myPictureBox.Height)
            Dim gp As New System.Drawing.Drawing2D.GraphicsPath()
            Dim d As Integer = 5

            gp.AddArc(r.X, r.Y, imgSizeWH(0), imgSizeWH(1), 180, 90)
            gp.AddArc(r.X + r.Width - d, r.Y, imgSizeWH(0), imgSizeWH(1), 270, 90)
            gp.AddArc(r.X + r.Width - d, r.Y + r.Height - d, imgSizeWH(0), imgSizeWH(1), 0, 90)
            gp.AddArc(r.X, r.Y + r.Height - d, imgSizeWH(0), imgSizeWH(1), 90, 90)

            g.FillPath(br, gp)
            'g.FillRectangle(br, 0, 0, bmp.Width, bmp.Height)
        End Using

        g.InterpolationMode = Drawing2D.InterpolationMode.HighQualityBicubic
        g.CompositingQuality = CompositingQuality.HighQuality
        g.TextRenderingHint = TextRenderingHint.AntiAlias
        g.SmoothingMode = SmoothingMode.HighQuality
        g.DrawImage(av, 0, 0, bmp.Width, bmp.Height)

        Using fnt As New Font("Arial", 132, FontStyle.Bold, GraphicsUnit.Pixel)
            TextRenderer.DrawText(g, text, fnt, New Rectangle(0, 0, imgSizeWH(0), imgSizeWH(1)),
                  Color.WhiteSmoke, TextFormatFlags.HorizontalCenter Or TextFormatFlags.VerticalCenter)
        End Using
    End Using

    Return bmp
End Function
4

1 回答 1

3

GraphicsPath只是一些弧线,没有线使它成为一个真正的圆角矩形。如果尺寸为 800x800,您可能需要更大的d(直径);并且由于您正在处理图像,因此您应该使用图像大小而不是 a 的大小PictureBox(这可能是圆比图像大的原因)。将其用于 GP 块:

' use the actual size, not those array values
Dim rect As New Rectangle(0, 0, bmp.Width, bmp.Height)

Using gp As New GraphicsPath
    ' arc radius is specified, but we use it as diameter
    Dim d As Int32 = radius * 2

    gp.StartFigure()
    ' top left
    ' LRTB creates a temp rect rather than calculating Size
    '   complete with typos and miscalcs
    gp.AddArc(Rectangle.FromLTRB(rect.Left, rect.Top,
                             rect.Left + d, rect.Top + d), 180, 90)
    gp.AddLine(rect.Left + d, rect.Top, rect.Right - d, rect.Top)

    ' top right
    gp.AddArc(Rectangle.FromLTRB(rect.Right - d, rect.Top,
                            rect.Right, rect.Top + d), -90, 90)
    gp.AddLine(rect.Right, rect.Top + d, rect.Right, rect.Bottom - d)

    ' bottom right
    gp.AddArc(Rectangle.FromLTRB(rect.Right - d, rect.Bottom - d,
                            rect.Right, rect.Bottom), 0, 90)
    gp.AddLine(rect.Right - d, rect.Bottom, rect.Left + d, rect.Bottom)

    ' bottom left
    gp.AddArc(Rectangle.FromLTRB(rect.Left, rect.Bottom - d,
                            rect.Left + d, rect.Bottom), 90, 90)
    gp.AddLine(rect.Left, rect.Bottom - d, rect.Left, rect.Top + d)

    gp.CloseFigure()
    Using p As New Pen(BackColor), br = New SolidBrush(BackColor)
        g.DrawPath(p, gp)
        g.FillPath(br, gp)
    End Using
End Using

请注意,在较小的图像上尝试此操作时,它可以帮助创建更大的图像,例如最终尺寸的 2、4 或 8 倍,绘制圆角矩形(使用半径 * {2、4 或 8})然后缩小结果。这使得更好的角落。1

使用 250x250 图像和 42 半径的结果:

在此处输入图像描述

Picturebox 有一个固定的边框并且在一个面板上(黄色),以证明透明度和边缘。使用较小的直径进行较小的切割。此外,为了获得最大的灵活性,我的类别允许指定所有硬编码的字体、大小和颜色参数——图像显示了用于文本颜色的 MistyRose。

1超大有助于处理小图像锐利的曲线。我的 250 图像曲线非常小(半径 == 8)看起来有点糟糕。

于 2016-04-05T19:58:41.173 回答