예제 #1
0
        public BitmapRenderer(IntPtr dibHandle)
        {
            _dibHandle     = dibHandle;
            _bitmapPointer = Kernel32Native.GlobalLock(dibHandle);

            BitmapInfoHeader bitmapInfo = new BitmapInfoHeader();

            Marshal.PtrToStructure(_bitmapPointer, bitmapInfo);
            log.Debug(bitmapInfo.ToString());

            _rectangle        = new Rectangle();
            _rectangle.X      = _rectangle.Y = 0;
            _rectangle.Width  = bitmapInfo.Width;
            _rectangle.Height = bitmapInfo.Height;

            if (bitmapInfo.SizeImage == 0)
            {
                bitmapInfo.SizeImage = ((((bitmapInfo.Width * bitmapInfo.BitCount) + 31) & ~31) >> 3) * bitmapInfo.Height;
            }


            // The following code only works on x86
            Debug.Assert(Marshal.SizeOf(typeof(IntPtr)) == 4);

            int pixelInfoPointer = bitmapInfo.ClrUsed;

            if ((pixelInfoPointer == 0) && (bitmapInfo.BitCount <= 8))
            {
                pixelInfoPointer = 1 << bitmapInfo.BitCount;
            }

            pixelInfoPointer = (pixelInfoPointer * 4) + bitmapInfo.Size + _bitmapPointer.ToInt32();

            _pixelInfoPointer = new IntPtr(pixelInfoPointer);
        }
예제 #2
0
        public static Bitmap NewBitmapFromHBitmap(IntPtr dibHandle)
        {
            IntPtr           _bitmapPointer;
            IntPtr           _pixelInfoPointer;
            Rectangle        _rectangle;
            BitmapInfoHeader _bitmapInfo;
            Bitmap           bitmap;

            _bitmapPointer = Kernel32Native.GlobalLock(dibHandle);
            try {
                _bitmapInfo = new BitmapInfoHeader();
                Marshal.PtrToStructure(_bitmapPointer, _bitmapInfo);
                log.Debug(_bitmapInfo.ToString());

                _rectangle        = new Rectangle();
                _rectangle.X      = _rectangle.Y = 0;
                _rectangle.Width  = _bitmapInfo.Width;
                _rectangle.Height = _bitmapInfo.Height;

                if (_bitmapInfo.SizeImage == 0)
                {
                    _bitmapInfo.SizeImage = ((((_bitmapInfo.Width * _bitmapInfo.BitCount) + 31) & ~31) >> 3) * _bitmapInfo.Height;
                }


                // compute the offset to the pixel info, which follows the bitmap info header
                {
                    // The following code only works on x86
                    Debug.Assert(Marshal.SizeOf(typeof(IntPtr)) == 4);
                    int pixelInfoPointer = _bitmapInfo.ClrUsed;
                    if ((pixelInfoPointer == 0) && (_bitmapInfo.BitCount <= 8))
                    {
                        pixelInfoPointer = 1 << _bitmapInfo.BitCount;
                    }
                    pixelInfoPointer  = (pixelInfoPointer * 4) + _bitmapInfo.Size + _bitmapPointer.ToInt32();
                    _pixelInfoPointer = new IntPtr(pixelInfoPointer);
                }

                // render to bitmap
                bitmap = new Bitmap(_rectangle.Width, _rectangle.Height);

                using (Graphics graphics = Graphics.FromImage(bitmap)) {
                    IntPtr hdc = graphics.GetHdc();

                    try {
                        Gdi32Native.SetDIBitsToDevice(hdc, 0, 0, _rectangle.Width, _rectangle.Height,
                                                      0, 0, 0, _rectangle.Height, _pixelInfoPointer, _bitmapPointer, 0);
                    }
                    finally {
                        graphics.ReleaseHdc(hdc);
                    }
                }

                bitmap.SetResolution(PpmToDpi(_bitmapInfo.XPelsPerMeter), PpmToDpi(_bitmapInfo.YPelsPerMeter));
            } finally {
                Kernel32Native.GlobalUnlock(dibHandle);
            }
            return(bitmap);
        }
예제 #3
0
 protected virtual void Dispose(bool disposing)
 {
     Kernel32Native.GlobalUnlock(_dibHandle);
 }