I’m trying to create a real grayscale image, but when my designer checks the file he is saying that the image remains RGB.
You can see the photoshop print here:
I’ve tried 2 methods so far:
1) Using the MakeGrayScale3 method:
public static Image MakeGrayscale3(Image original)
{
//create a blank bitmap the same size as original
Bitmap newBitmap = new Bitmap(original.Width, original.Height);
newBitmap.SetResolution(original.HorizontalResolution, original.VerticalResolution);
//get a graphics object from the new image
Graphics g = Graphics.FromImage(newBitmap);
//create the grayscale ColorMatrix
ColorMatrix colorMatrix = new ColorMatrix(
new float[][]
{
new float[] {.3f, .3f, .3f, 0, 0},
new float[] {.59f, .59f, .59f, 0, 0},
new float[] {.11f, .11f, .11f, 0, 0},
new float[] {0, 0, 0, 1, 0},
new float[] {0, 0, 0, 0, 1}
});
//create some image attributes
ImageAttributes attributes = new ImageAttributes();
//set the color matrix attribute
attributes.SetColorMatrix(colorMatrix);
//draw the original image on the new image
//using the grayscale color matrix
g.DrawImage(original, new Rectangle(0, 0, original.Width, original.Height),
0, 0, original.Width, original.Height, GraphicsUnit.Pixel, attributes);
//dispose the Graphics object
g.Dispose();
return newBitmap;
}
2) Using the ImageMagick.Net library with this code:
using (MagickImage image = new MagickImage(file))
{
image.ColorSpace = ColorSpace.GRAY;
image.Write(originalFile);
}
If anyone had this problem before or have a clue of what to do to change that..
Thanks!
Original Image:
Result Image (ImageMagick):
Result Image (MakeGrayscale3):
3
Answers
Thanks for all answers but after read the topic that Hans mentioned there they talk about the FreeImageNET library that I'm using to solve my problem.
Using this code I've managed to save the image as a grayscale image:
The issue is this line:
If you look at the MSDN page it says:
So, you’re just creating another color image. What you need to do is to use a different constructor to force a different format:
But then that gives you another issue – you can’t paint to bitmaps with that pixel format with a
Graphics
object. There is aPixelFormat.Format16bppGrayScale
which appears to work even less.So, my suggestion would be to to this manually. Use LockBits to get access to the raw bitmap and do the conversion yourself. It is a little bit more work (i.e. you can’t use the
ColorMatrix
stuff, and you have to take care to check if the source bitmap is 24 bit or 32 bit), but it will work just fine.One issue to be aware of is that it’s not a “real” grayscale format, it’s 8 bit indexed. So you will also have to create a palette. Simply map each of the 256 values to the same, i.e. 0 -> 0, 100 -> 100, 255 -> 255.
The grayscale format used by jpeg isn’t available in the classic
System.Drawing
classes. It is, however, available inSystem.Windows.Media
. You need to addPresentationCore
andWindowsBase
as references for using them (this will not be portable on Linux).As a bonus, this does the grayscale conversion automatically.
If you’re actually starting from
Image
/Bitmap
class, there are some solutions around for converting between them.Also you should pay attention to: