从VB.NET保存PNG消除了阴影

时间:2014-07-20 23:44:15

标签: vb.net transparency gdi+ alphablending bitblt

我一直试图解决.NET(所有版本)本身不支持TRUE透明度的古老问题,并且在阅读了数千篇文章,问题/答案,论坛,msdn文章等之后,空手而归除了能够通过使用整个表单来执行此操作,其中没有可见的控件(请参阅http://www.codeproject.com/Articles/1822/Per-Pixel-Alpha-Blend-in-C

我已经部分放弃了这个搜索,而是决定通过使用MDIParent / Client情况来满足,其中每个图形/文本都直接绘制到表单上。

我遇到的问题是,当我以透明度保存时,我最终会在任何阴影周围出现斑点,我相信(但不确定)是PNG以较低的分辨率或损失保存Alpha通道或其他东西,MakeTransparent(在这里插入颜色),只是不满意。如果你能说明这个过程发生了如此严重的错误......请告诉我。

输入图像

enter image description here

输出图像

enter image description here

我使用的代码如下:

    Imports Graphics

    Public Class PictureForm
        Private Declare Auto Function BitBlt Lib "gdi32.dll" (ByVal _
            hdcDest As IntPtr, ByVal nXDest As Integer, ByVal _
            nYDest As Integer, ByVal nWidth As Integer, ByVal _
            nHeight As Integer, ByVal hdcSrc As IntPtr, ByVal nXSrc _
            As Integer, ByVal nYSrc As Integer, ByVal dwRop As  _
            System.Int32) As Boolean
        Private Const SRCCOPY As Integer = &HCC0020

        Public Graphic As Drawing.Graphics
        Private Sub PictureForm_Load(sender As Object, e As EventArgs) Handles MyBase.Load
            Me.Show()
            Graphic = Me.CreateGraphics
            Graphic.CompositingQuality = Drawing2D.CompositingQuality.HighQuality

            Graphic.DrawImage(Image.FromFile("C:\Users\Daniel\Downloads\PNG-icon.png"), 35, 22)

            Dim bmp As Bitmap = GetFormImage()
            bmp.MakeTransparent(Color.White)
            bmp.Save("test.png", System.Drawing.Imaging.ImageFormat.Png)
            bmp.Dispose()       

        End Sub

        Public Function GetFormImage() As Bitmap
            ' Get this form's Graphics object.
            Dim me_gr As Drawing.Graphics = Me.CreateGraphics

            ' Make a Bitmap to hold the image.
            Dim bm As New Bitmap(Me.ClientSize.Width, Me.ClientSize.Height, me_gr)
            Dim bm_gr As Drawing.Graphics = Drawing.Graphics.FromImage(bm)
            Dim bm_hdc As IntPtr = bm_gr.GetHdc

            ' Get the form's hDC. We must do this after 
            ' creating the new Bitmap, which uses me_gr.
            Dim me_hdc As IntPtr = me_gr.GetHdc

            ' BitBlt the form's image onto the Bitmap.
            BitBlt(bm_hdc, 0, 0, Me.ClientSize.Width, _
                Me.ClientSize.Height, _
                me_hdc, 0, 0, SRCCOPY)
            me_gr.ReleaseHdc(me_hdc)
            bm_gr.ReleaseHdc(bm_hdc)

            ' Return the result.
            Return bm
        End Function

    End Class

另外,您会注意到第一张图片中的字母在输出中没有呈现透明。

1 个答案:

答案 0 :(得分:0)

问题在于您将图形“存储”在表单上 - 没有alpha存在。

你可以通过保留一个你做所有绘画的屏幕外位图来轻松解决这个问题,当你修改它时,你也可以将它绘制到表格中。

然后你将不再需要GetFormImage方法 - 你只需直接保存你的屏幕外位图(它带有alpha信息)。

PS。你缺少几个.Dispose()调用。