Clone() public method

Clone the unmanaged images.

The method does complete cloning of the object.

public Clone ( ) : UnmanagedImage
return UnmanagedImage
        /// <summary>
        /// Get rectangle contain object in current frame
        /// </summary>
        /// <param name="templateInfo">Tracking template information</param>
        /// <param name="source">Frame</param>
        /// <returns>Rectangle contain object</returns>
        public static Rectangle TemplateColorTracking(ImageStatistics templateInfo, ref UnmanagedImage source)
        {
            UnmanagedImage image = source.Clone();
            // create filter
            EuclideanColorFiltering filter = new EuclideanColorFiltering();
            // set center colol and radius
            filter.CenterColor = new RGB(
                (byte)templateInfo.Red.Mean,
                (byte)templateInfo.Green.Mean,
                (byte)templateInfo.Blue.Mean);
            filter.Radius = 30;
            // apply the filter
            filter.ApplyInPlace(image);

            image = Grayscale.CommonAlgorithms.BT709.Apply(image);

            OtsuThreshold threshold = new OtsuThreshold();
            threshold.ApplyInPlace(image);

            BlobCounter blobCounter = new BlobCounter();
            blobCounter.ObjectsOrder = ObjectsOrder.Size;
            blobCounter.ProcessImage(image);

            Rectangle rect = blobCounter.ObjectsCount > 0 ? blobCounter.GetObjectsRectangles()[0] : Rectangle.Empty;
            return rect;
        }
        /// <summary>
        /// Perform color dithering for the specified image.
        /// </summary>
        /// 
        /// <param name="sourceImage">Source image to do color dithering for.</param>
        /// 
        /// <returns>Returns color dithered image. See <see cref="ColorTable"/> for information about format of
        /// the result image.</returns>
        /// 
        /// <exception cref="UnsupportedImageFormatException">Unsupported pixel format of the source image. It must 24 or 32 bpp color image.</exception>
        /// 
        public unsafe Bitmap Apply( UnmanagedImage sourceImage )
        {
            if ( ( sourceImage.PixelFormat != PixelFormat.Format24bppRgb ) &&
                 ( sourceImage.PixelFormat != PixelFormat.Format32bppRgb ) &&
                 ( sourceImage.PixelFormat != PixelFormat.Format32bppArgb ) &&
                 ( sourceImage.PixelFormat != PixelFormat.Format32bppPArgb ) )
            {
                throw new UnsupportedImageFormatException( "Unsupported pixel format of the source image." );
            }

            cache.Clear( );

            // make a copy of the original image
            UnmanagedImage source = sourceImage.Clone( );

            // get image size
            width  = sourceImage.Width;
            height = sourceImage.Height;
            stride = sourceImage.Stride;
            pixelSize = Bitmap.GetPixelFormatSize( sourceImage.PixelFormat ) / 8;

            int offset = stride - width * pixelSize;

            // create destination image
            Bitmap destImage = new Bitmap( width, height, ( colorTable.Length > 16 ) ?
                PixelFormat.Format8bppIndexed : PixelFormat.Format4bppIndexed );
            // and init its palette
            ColorPalette cp = destImage.Palette;
            for ( int i = 0, n = colorTable.Length; i < n; i++ )
            {
                cp.Entries[i] = colorTable[i];
            }
            destImage.Palette = cp;

            // lock destination image
            BitmapData destData = destImage.LockBits( new Rectangle( 0, 0, width, height ),
                ImageLockMode.ReadWrite, destImage.PixelFormat );

            // pixel values
            int r, g, b;

            // do the job
            byte* ptr = (byte*) source.ImageData.ToPointer( );
            byte* dstBase = (byte*) destData.Scan0.ToPointer( );
            byte colorIndex;

            bool is8bpp = ( colorTable.Length > 16 );

            // for each line
            for ( y = 0; y < height; y++ )
            {
                byte* dst = dstBase + y * destData.Stride;

                // for each pixels
                for ( x = 0; x < width; x++, ptr += pixelSize )
                {
                    r = ptr[RGB.R];
                    g = ptr[RGB.G];
                    b = ptr[RGB.B];

                    // get color from palette, which is the closest to current pixel's value
                    Color closestColor = GetClosestColor( r, g, b, out colorIndex );

                    // do error diffusion
                    Diffuse( r - closestColor.R, g - closestColor.G, b - closestColor.B, ptr );

                    // write color index as pixel's value to destination image
                    if ( is8bpp )
                    {
                        *dst = colorIndex;
                        dst++;
                    }
                    else
                    {
                        if ( x % 2 == 0 )
                        {
                            *dst |= (byte) ( colorIndex << 4 );
                        }
                        else
                        {
                            *dst |= ( colorIndex );
                            dst++;
                        }
                    }
                }
                ptr += offset;
            }

            destImage.UnlockBits( destData );
            source.Dispose( );

            return destImage;
        }
        /// <summary>
        ///   Process the filter on the specified image.
        /// </summary>
        /// 
        /// <param name="sourceData">Source image data.</param>
        /// <param name="destinationData">Destination image data.</param>
        /// 
        protected unsafe override void ProcessFilter(UnmanagedImage sourceData, UnmanagedImage destinationData)
        {
            int width = sourceData.Width;
            int height = sourceData.Height;
            PixelFormat format = sourceData.PixelFormat;
            int pixelSize = System.Drawing.Bitmap.GetPixelFormatSize(format) / 8;

            sourceData.Clone();

            UnmanagedImage temp = UnmanagedImage.Create(width, height, format);

            int lineWidth = width * pixelSize;

            int srcStride = temp.Stride;
            int srcOffset = srcStride - lineWidth;
            int dstStride = destinationData.Stride;
            int dstOffset = dstStride - lineWidth;

            byte* srcStart = (byte*)temp.ImageData.ToPointer();
            byte* dstStart = (byte*)destinationData.ImageData.ToPointer();


            // first
            Convolution c = new Convolution(masks[0]);
            c.Apply(sourceData, destinationData);

            // others
            for (int i = 1; i < masks.Length; i++)
            {
                c.Kernel = masks[i];
                c.Apply(sourceData, temp);

                byte* src = srcStart;
                byte* dst = dstStart;

                for (int y = 0; y < height; y++)
                {
                    for (int x = 0; x < lineWidth; x++, src++, dst++)
                    {
                        if (*src > *dst)
                            *dst = *src;
                    }

                    dst += dstOffset;
                    src += srcOffset;
                }
            }
        }
Beispiel #4
0
        public static Bitmap MatrixBlend(UnmanagedImage uOriginal, Bitmap compare, byte alpha)
        {
            //ref: http://ithoughthecamewithyou.com/post/Fastest-image-merge-(alpha-blend)-in-GDI2b.aspx

            string cacheKey = string.Format("MB_{0}", alpha);

            Stopwatch sw = new Stopwatch();
            sw.Start();

            // for the matrix the range is 0.0 - 1.0
            float alphaNorm = (float)alpha / 255.0F;

            // just change the alpha
            ColorMatrix matrix = new ColorMatrix(new float[][]{
                new float[] {1F, 0, 0, 0, 0},
                new float[] {0, 1F, 0, 0, 0},
                new float[] {0, 0, 1F, 0, 0},
                new float[] {0, 0, 0, alphaNorm, 0},
                new float[] {0, 0, 0, 0, 1F}});

            ImageAttributes imageAttributes = new ImageAttributes();
            imageAttributes.SetColorMatrix(matrix);

            //create a blank bitmap the same size as original
            Bitmap newBitmap = uOriginal.Clone().ToManagedImage();
            sw.Stop();
            _logger.Trace("MatrixBlend_newBitmap [{0}] takes {1}", cacheKey, sw.Elapsed.ToString());

            sw.Restart();
            //get a graphics object from the new image
            using (Graphics g = Graphics.FromImage(newBitmap))
            {
                g.CompositingMode = CompositingMode.SourceOver;
                g.CompositingQuality = CompositingQuality.HighSpeed;

                g.DrawImage(compare,
                    new Rectangle(0, 0, uOriginal.Width, uOriginal.Height),
                    0,
                    0,
                    compare.Width,
                    compare.Height,
                    GraphicsUnit.Pixel,
                    imageAttributes);
            }
            sw.Stop();
            _logger.Trace("MatrixBlend_drawImage [{0}] takes {1}", cacheKey, sw.Elapsed.ToString());

            return newBitmap;
        }