pngcs icon indicating copy to clipboard operation
pngcs copied to clipboard

How to load .png image into object of Bitmap class?

Open ArsenShnurkov opened this issue 9 years ago • 2 comments

I want to avoid unmanaged code from libgdiplus and libpng in mono.

I.e. something like http://stackoverflow.com/a/6809677/1709408

public static void LoadThroughPngcs(this Bitmap bmp, string filename)
{
    if (bmp == null) throw new ArgumentNullException("bmp");
    // read bmpWidth, bmpHeight
    var data = bmp.LockBits(
        new Rectangle(0, 0, bmpWidth, bmpHeight),
        System.Drawing.Imaging.ImageLockMode.ReadWrite,
        System.Drawing.Imaging.PixelFormat.Format32bppArgb);

    var line = data.Scan0;
    var eof = line + data.Height * data.Stride;
    while(line != eof)
    {
        var pixelAlpha = line + 3;
        var eol = pixelAlpha + data.Width * 4;
        while(pixelAlpha != eol)
        {
            System.Runtime.InteropServices.Marshal.WriteByte(
                pixelAlpha, alpha);
            pixelAlpha += 4;
        }
        line += data.Stride;
    }
    bmp.UnlockBits(data);
}

but with reading pixels through libcs

ArsenShnurkov avatar Feb 19 '16 12:02 ArsenShnurkov

May be something should have property of type IEnumerable<KeyValuePair<Point, Color> >. KeyValuePair instead of Pair, because the former is value type, and the later is reference type...

Or it is better to have a class which converts pixel sequential number into coordinates and vice versa.

ArsenShnurkov avatar Feb 19 '16 15:02 ArsenShnurkov

   public static Bitmap LoadPng(string fileName)
    {
        PngReader pngr = FileHelper.CreatePngReader(fileName);
        pngr.SetUnpackedMode(true);
        int channels = pngr.ImgInfo.Channels;
        int bmpWidth = pngr.ImgInfo.Cols;
        int bmpHeight = pngr.ImgInfo.Rows;
        Bitmap bmp = new Bitmap(bmpWidth, bmpHeight, PixelFormat.Format32bppArgb);
        int A = 255;
        for (int y = 0; y 

My picture have 3 channels. How to get global transparency info in pngcs? PngChunkTRNS trns = pngr.GetMetadata().GetTRNS(); // transparency metadata, can be null

pngr.ImgInfo {ImageInfo [cols=16, rows=16, bitDepth=8, channels=3, bitspPixel=24, bytesPixel=3, bytesPerRow=48, samplesPerRow=48, samplesPerRowP=48, alpha=False, greyscale=False, indexed=False, packed=False]} Hjg.Pngcs.ImageInfo

pngr.GetMetadata().GetTRNS() {chunk id= tRNS (len=6 off=33) c=PngChunkTRNS} Hjg.Pngcs.Chunks.PngChunkTRNS

So, I receive image without transparency at the end (lose alpha value of image) may be this will work, may be not:

var trns = pngr.GetMetadata ().GetTRNS ();
if (trns != null) {
    int[] rgb = trns.GetRGB ();
    var tc = Color.FromArgb (0, rgb [0], rgb [1], rgb [2]);
    bmp.MakeTransparent (tc);
}

ArsenShnurkov avatar Feb 20 '16 10:02 ArsenShnurkov