Give an image a transparent background in C#

[transparent]

The Bitmap class’s MakeTransparent method changes all of the pixels with a given color to the transparent color A = 0, R = 0, G = 0, B = 0. When the program starts, the following code makes the background transparent for the two images stored in the program’s Smile and Frown resources.

// The images.
private Bitmap SmileBitmap, FrownBitmap;

// Make the images' backgrounds transparent.
private void Form1_Load(object sender, EventArgs e)
{
    SmileBitmap = Properties.Resources.Smile;
    SmileBitmap.MakeTransparent(SmileBitmap.GetPixel(0, 0));

    FrownBitmap = Properties.Resources.Frown;
    FrownBitmap.MakeTransparent(FrownBitmap.GetPixel(0, 0));
}

The code saves the Smile resource in a Bitmap variable. It then uses the Bitmap object’s MakeTransparent method to make all of its pixels that match the color of the pixel in the upper left corner transparent. The code then repeats those steps for the Frown image.

The following Paint event handler displays the two images.

// Draw the two images overlapping.
private void Form1_Paint(object sender, PaintEventArgs e)
{
    e.Graphics.DrawImage(FrownBitmap, 30, 30);
    e.Graphics.DrawImage(SmileBitmap, 95, 85);
}

This code simply draws the two images overlapping so you can see that they have transparent backgrounds.


Download Example   Follow me on Twitter   RSS feed   Donate




This entry was posted in graphics, image processing and tagged , , , , , , , , , , , , . Bookmark the permalink.

15 Responses to Give an image a transparent background in C#

  1. kaliprasad m says:

    Hello,

    Is there a way make the gray transparent to White ?

    • RodStephens says:

      I’m not sure what you’re asking. In this example, the background is transparent. It is drawn over a gray background, so that is what is showing through. if you display it on a white background, then the white would show through.

      If you’re asking whether you can make the white pixels in the image transparent, simply call the bitmap’s MakeTransparent method and pass it the color Color.White.

  2. Nick says:

    Rod, first I want to thank you for giving us so much stuff for free. You’re amazing… I think this is the best site we can learn C#.

    This question is for drawing in pictureBox Paint event not for png image with is surrounded by transparent pixels.

    The MakeTransparent method works well if the drawing has set e.Graphics.SmoothingMode = SmoothingMode.None but for SmoothingMode.AntiAlias the white (or any other color) pixels on the background Form will be blended with the color of the Pen.
    The solution would be to create a transparent background first and then to draw. How can we do this because the PictureBox control inherits the Form color.
    How can we make a drawing surface like glass before we get drawn?

    Here is the image to understand what is the issue:

    • RodStephens says:

      Yes, this is a problem and you’ve pinpointed it nicely. I think you have three main options.

      First, you can make the original background that you turn transparent match the background that you draw the image on top of. Either change the original background or change the new background. Of course that will only work if you have control of either the original background or the final background.

      Second, you can write code to hunt down all of the anti-aliased pixels and adjust them. For example, suppose as in this example you drew a black line over a white background. Then the anti-aliased pixels are a mix of white and black. Find them and convert the whiteness into transparency. For example, if a pixel is 50% white (so its red, green, and blue components are 128), then change it so it is 100% black (RGB = 0, 0, 0) and alpha is 128 so it is half transparent. That should work as long as the non-anti-aliased pixels are not shades of gray. Unfortunately it requires you to examine every pixel and that will be slow.

      The best solution is to draw the original image with a transparent background. Before you start drawing, clear the image with the Transparent color. Then draw on it. In that case, the anti-aliased pixels will be semi-transparent (like the result of the second option). Of course, this only works if you have control over the original drawing. In other words, if you draw it. If you’re getting it from somewhere else and it was already drawn with a non-transparent background, then this won’t work.

  3. Nick says:

    Thank you for your answer but it seems that none of your indications works.

    Many colors have a certain amount of white in their composition. In my example I used black, but for other colors it is very difficult to detect only the edges and replace the white with its transparent equivalent of pen color.

    Also, if I clear the image with the Transparent color, behind the image is the color of the Form that makes things go wrong.

    • RodStephens says:

      Take a look at this example.

      Use transparency when drawing with anti-aliasing in C#

      The form’s color should not show through if you set the PictureBox control's BackColor property or clear the background in the Paint event handler.

      I'm still not sure how you're drawing. Are you drawing the original image? Or did you get it somewhere?

      If you got it somewhere so you don't have control over it and it has lots of anti-aliased colors, then I don't think there is an easy solution for you. You could convert every pixel within about 3 pixels of a transparent pixel. That would be hard and erode your image so it would become smaller, but it might provide a slightly better result. Overall, however, you may just be stuck without a good solution.

  4. Nick says:

    Thank you Rod.
    I use your code from “Let the user draw polygons, move them, and add points to them in C#”.
    Finally I save the drawing as .png image and I load in Paint.Net editor.

  5. dillikumar C says:

    I am looking insted of black and white imge to color image using c# can you help me on this

    • RodStephens says:

      This example works with colored images. The MakeTransparent method makes all of the pixels of a given color transparent. This example makes the pixels that have the same color as the pixel in the upper left corner transparent. That works well for bmp and png files with solid backgrounds.

      If you have an image where the background is not a solid color, try this example:

      Give an image an improved transparent background in C#

      Be sure to save the result as a png. The jpg format does not support transparency.

  6. Tina says:

    Is there a way to take a jpg saved as CMYK that has black text and a white background, strip out the white background, and save it in a CMYK image format that supports transparencies?

    • RodStephens says:

      C# doesn’t work naturally with CMYK images, but you should be able to do that with RGBA images. You should be able to load the image and use MakeTransparent as shown in this post. Then save the result in a format that supports transparency such as .png.

      However, if you’re using a jpg file, then many of the “white” pixels may not be white, they may only be close to white. The MakeTransparent method only converts pixels that match exactly, so some of the background pixels will not be converted to transparent.

      To avoid that, first perform binary contrast enhancement as described in this post: Perform binary contrast enhancement more quickly in C#.

      Alternatively you can loop through the pixels as in binary contrast enhancement and just set the alpha component of the whitish pixels to 0 so they are transparent. Then you don’t need to use the MakeTransparent method.

      • Tina says:

        Thanks, Rod. What about a .tiff image that has a transparent background? I know you can export a .tiff image in PhotoShop with a transparent background, but I’m not sure if GDI recognizes that.

        I’m trying to figure out a way to get some images embedded in a PDF, and our printer is asking us to embed CMYK images instead of RGB programmatically (they say that an RGB black is not a “true” black as it would be in CMYK). It just may be a limitation of C# and GDI, as you suggested.

        • RodStephens says:

          Same thing. It’s not really a CMYK image or RGB image. Those are just ways of looking at the image when you have it loaded into memory. If you really want to, you can convert the RGB values into CMYK values within your program, but how you look at it should have nothing to do with how they look at it.

          And sorry, RGB (0, 0, 0) is black and that’s all there is to it. There’s no blacker than not having any color in a pixel.

          It sounds like they really just want a tiff file. You can save your image in tiff format if you like. See Save images with an appropriate format depending on the file name’s extension in C#.

          So make the image, set whatever pixels you want to transparent, and save it as a tiff file or whatever format they want. Be sure not to use a lossy compression format like jpg or some pixels may be changed so they are not truly transparent, black, or whatever.

          Tiff can be lossy or lossless. I think the .NET libraries use a lossless compression so you should be okay. The bmp and png formats are always lossless, so you could see if the printer can read them if you have trouble with tiff.

          • Tina says:

            Thanks. Unfortunately, they are saying RGB black is not the same as CMYK black. If the image gets saved in a PDF as RGB, that 0,0,0 value is translated back to CMYK as 75C, 68M, 67Y and 90K. In CMYK terms, that’s a dull gray color, not a CMYK “true black.” It’s frustrating. They are telling me this is because RBG is a “subtractive” color model while CMYK is an “additive” color model. I appreciate the insight, however, and will investigate alternatives.

          • RodStephens says:

            You might try an online conversion tool like https://www.rgb2cmyk.org/.

Comments are closed.