Wie zeichnen Sie Transparent Bild System.Drawing mit?
-
06-07-2019 - |
Frage
Ich versuche, eine transparente GIF von einer ASPX-Seite für die Anzeige auf einer Webseite zurückzukehren. Ich versuche, das Bild zu bekommen Transparenz zu haben, aber ich behalte nur Schwarz Wesen bekommen, wo sollte das Bild transparent sein.
Weiß jemand, was ich falsch mache?
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) _
Handles Me.Load
'' Change the response headers to output a GIF image.
Response.Clear()
Response.ContentType = "image/gif"
Dim width = 110
Dim height = width
'' Create a new 32-bit bitmap image
Dim b = New Bitmap(width, height)
'' Create Grahpics object for drawing
Dim g = Graphics.FromImage(b)
Dim rect = New Rectangle(0, 0, width - 1, height - 1)
'' Fill in with Transparent
Dim tbrush = New System.Drawing.SolidBrush(Color.Transparent)
g.FillRectangle(tbrush, rect)
'' Draw Circle Border
Dim bPen = Pens.Red
g.DrawPie(bPen, rect, 0, 365)
'' Fill in Circle
Dim cbrush = New SolidBrush(Color.LightBlue)
g.FillPie(cbrush, rect, 0, 365)
'' Clean up
g.Flush()
g.Dispose()
'' Make Transparent
b.MakeTransparent()
b.Save(Response.OutputStream, Imaging.ImageFormat.Gif)
Response.Flush()
Response.End()
End Sub
Lösung
Leider gibt es keine einfache Möglichkeit, eine transparente GIF mit einem Bitmap-Objekt zu erstellen. (Siehe dieser KB-Artikel )
Sie können alternativ das PNG-Format verwenden, die Transparenz mit dem Code unterstützt Sie verwenden.
Andere Tipps
Ja, wie Jerome erwähnte, ist es ohnehin nicht transparent GIF mit einem Bitmap-Objekt zu erstellen. Mist!
Nun, wie auch immer, änderte ich meinen Code einen PNG und alle Arbeiten wie erwartet zu erzeugen.
Es gibt eine kleine Arbeit um Ich habe tun müssen, da Sie direkt auf den Output PNG nicht schreiben können. Ich brauchte die PNG zu einem Memorystream zu schreiben, und dann, dass an den Output schreiben.
Hier ist der endgültige Code für meine Implementierung:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) _
Handles Me.Load
'' Change the response headers to output a JPEG image.
Response.Clear()
Response.ContentType = "image/png"
Dim width = 11
Dim height = width
'' Create a new 32-bit bitmap image
Dim b = New Bitmap(width, height)
'' Create Grahpics object for drawing
Dim g = Graphics.FromImage(b)
'' Fill the image with a color to be made Transparent after drawing is finished.
g.Clear(Color.Gray)
'' Get rectangle where the Circle will be drawn
Dim rect = New Rectangle(0, 0, width - 1, height - 1)
'' Draw Circle Border
Dim bPen = Pens.Black
g.DrawPie(bPen, rect, 0, 365)
'' Fill in Circle
Dim cbrush = New SolidBrush(Color.Red)
g.FillPie(cbrush, rect, 0, 365)
'' Clean up
g.Flush()
g.Dispose()
'' Make Transparent
b.MakeTransparent(Color.Gray)
'' Write PNG to Memory Stream then write to OutputStream
Dim ms = New MemoryStream()
b.Save(ms, Imaging.ImageFormat.Png)
ms.WriteTo(Response.OutputStream)
Response.Flush()
Response.End()
End Sub
Es ist möglich aber nicht einfach
Wenn Sie unsicher Code verwendet in Ihrem Projekt sind in der Lage, es gibt ein paar Methoden Zeiger zu verwenden, durch die Farbtabelle zu zerreißen und die Transparenz der Arbeit zu machen.
Ein Beispielformular App von Bob Powell finden Sie hier: http://www.bobpowell.net/giftransparency HTM . Ich verwenden eine Variante dieser Methode auf einem Web-Handler vor ein paar Jahren, die etwa 10 Millionen Mal im Monat getroffen zu werden, und es schien gut zu funktionieren.
Wenn Sie nur eine begrenzte Farbe pallete verwenden Sie die Farbtabelle Verarbeitung nur auf die Farben, die Sie benötigen, reduzieren kann (genau kann mich nicht erinnern, wie ich das getan habe ...).
Dass gesagt wird, png ist eine Metrik crapload einfacher.
Hier ist ein Code ein gif haben (die bereits Transparenz in ihm haben) umgewandelt (soll man es skalieren möchten) in Bitmap und dann richtig gezeigt werden kann, damit die Transparenz ist.
imagePath = System.Web.HttpContext.Current.Request.MapPath(libraryPath + reqImageFile);
System.Drawing.Image image = null;
Bitmap resizedImage = null;
if (reqWidth == 0) { reqWidth = image.Width; }
if (reqHeight == 0) { reqHeight = image.Height; }
image = System.Drawing.Image.FromFile(imagePath);
reqWidth = image.Width;
reqHeight = image.Height;
//here is the transparency 'special' treatment
resizedImage = new Bitmap(reqWidth, reqHeight, PixelFormat.Format8bppIndexed);
ColorPalette pal = resizedImage.Palette;
for (int i = 0; i < pal.Entries.Length; i++)
{
Color col = pal.Entries[i];
pal.Entries[i] = Color.FromArgb(0, col.R, col.G, col.B);
}
resizedImage.Palette = pal;
BitmapData src = ((Bitmap)image).LockBits(new Rectangle(0, 0, reqWidth, reqHeight), ImageLockMode.ReadOnly, image.PixelFormat);
BitmapData dst = resizedImage.LockBits(new Rectangle(0, 0, resizedImage.Width, resizedImage.Height),
ImageLockMode.WriteOnly, resizedImage.PixelFormat);
((Bitmap)image).UnlockBits(src);
resizedImage.UnlockBits(dst);
Viel Glück!
Grégoire Lafortune