1. 程式人生 > >Win8 Metro(C#)數字影象處理--2.40二值影象輪廓提取演算法

Win8 Metro(C#)數字影象處理--2.40二值影象輪廓提取演算法



[函式名稱]

二值影象輪廓提取 ContourExtraction(WriteableBitmap src)

[演算法說明]

  二值影象的輪廓提取對於影象識別,影象分割有著重要意義。該演算法的核心就是將影象目標的內部點消除。所謂內部點,我們要根據當前畫素點的鄰域來進行判斷,假設鄰域視窗為3*3視窗,如果當前畫素P(x,y)的八個鄰域畫素滿足如下條件,則該點即內部點:

  1P(x,y)為目標畫素,假設目標畫素為黑色0,背景畫素為白色255,那麼P(x,y)=0;

  2P(x,y)的八個鄰域畫素均為目標畫素0

  我們把滿足條件的內部點刪除,換為背景點255,即可得到影象輪廓。

  內部點如下圖所示:

[函式程式碼]

        /// <summary>
        /// Contour Extraction process.
        /// </summary>
        /// <param name="src">The source image.</param>
        /// <returns></returns>
        public static WriteableBitmap ContourExtraction(WriteableBitmap src)
        {
            if (src != null)
            {
                int w = src.PixelWidth;
                int h = src.PixelHeight;
                WriteableBitmap srcImage = new WriteableBitmap(w, h);
                byte[] temp = src.PixelBuffer.ToArray();
                byte[] tempMask = (byte[])temp.Clone();
                for (int j = 1; j < h-1; j++)
                {
                    for (int i = 4; i < w*4-4; i+=4)
                    {
                        if ((tempMask[i + j * w * 4] == 0) && (tempMask[i - 4 + j * w * 4] == 0) && (tempMask[i + 4 + j * w * 4] == 0) && (tempMask[i - 4 + (j - 1) * w * 4] == 0)
                            && (tempMask[i - 4 + (j + 1) * w * 4] == 0) && (tempMask[i + (j - 1) * w * 4] == 0) && (tempMask[i + (j + 1) * w * 4] == 0)
                            && (tempMask[i + 4 + (j - 1) * w * 4] == 0) && (tempMask[i + 4 + (j + 1) * w * 4] == 0))
                        {
                            temp[i + j * w * 4] = (byte)255;
                            temp[i + 1 + j * w * 4] = (byte)255;
                            temp[i + 2 + j * w * 4] = (byte)255;
                        }
                    }
                }
                Stream sTemp = srcImage.PixelBuffer.AsStream();
                sTemp.Seek(0, SeekOrigin.Begin);
                sTemp.Write(temp, 0, w * 4 * h);
                return srcImage;
            }
            else
            {
                return null;
            }
        }