Beispiel #1
0
        /// <summary>
        /// Niblackの手法による二値化処理を行う。
        /// </summary>
        /// <param name="imgSrc">入力画像</param>
        /// <param name="imgDst">出力画像</param>
        /// <param name="kernelSize">局所領域のサイズ</param>
        /// <param name="k">係数</param>
#else
        /// <summary>
        /// Binarizes by Niblack's method
        /// </summary>
        /// <param name="src">Input image</param>
        /// <param name="dst">Output image</param>
        /// <param name="kernelSize">Window size</param>
        /// <param name="k">Adequate coefficient</param>
#endif
        public static void Niblack(IplImage src, IplImage dst, int kernelSize, double k)
        {
            if (src == null)
            {
                throw new ArgumentNullException("src");
            }
            if (dst == null)
            {
                throw new ArgumentNullException("dst");
            }

            // グレースケールのみ
            if (src.NChannels != 1)
            {
                throw new ArgumentException("src must be gray scale image");
            }
            if (dst.NChannels != 1)
            {
                throw new ArgumentException("dst must be gray scale image");
            }

            // サイズのチェック
            if (kernelSize < 3)
            {
                throw new ArgumentOutOfRangeException("kernelSize", "size must be 3 and above");
            }
            if (kernelSize % 2 == 0)
            {
                throw new ArgumentOutOfRangeException("kernelSize", "size must be odd number");
            }

            CvRect roi    = src.ROI;
            int    width  = roi.Width;
            int    height = roi.Height;

            if (width != dst.Width || height != dst.Height)
            {
                throw new ArgumentException("src.Size == dst.Size");
            }

            unsafe
            {
                byte *pSrc    = src.ImageDataPtr;
                byte *pDst    = dst.ImageDataPtr;
                int   stepSrc = src.WidthStep;
                int   stepDst = dst.WidthStep;
                //for (int y = 0; y < gray.Height; y++)
                MyParallel.For(0, height, delegate(int y)
                {
                    for (int x = 0; x < width; x++)
                    {
                        double m, s;
                        MeanStddev(src, x + roi.X, y + roi.Y, kernelSize, out m, out s);
                        double threshold = m + k * s;
                        int offsetSrc    = stepSrc * (y + roi.Y) + (x + roi.X);
                        int offsetDst    = stepDst * y + x;
                        if (pSrc[offsetSrc] < threshold)
                        {
                            pDst[offsetDst] = 0;
                        }
                        else
                        {
                            pDst[offsetDst] = 255;
                        }
                    }
                }
                               );
            }
        }
Beispiel #2
0
        /// <summary>
        /// Niblackの手法による二値化処理を行う。
        /// </summary>
        /// <param name="imgSrc">入力画像</param>
        /// <param name="imgDst">出力画像</param>
        /// <param name="kernelSize">局所領域のサイズ</param>
        /// <param name="k">係数</param>
#else
        /// <summary>
        /// Binarizes by Niblack's method
        /// </summary>
        /// <param name="src">Input image</param>
        /// <param name="dst">Output image</param>
        /// <param name="kernelSize">Window size</param>
        /// <param name="k">Adequate coefficient</param>
#endif
        public static void Niblack(Mat src, Mat dst, int kernelSize, double k)
        {
            if (src == null)
            {
                throw new ArgumentNullException("src");
            }
            if (dst == null)
            {
                throw new ArgumentNullException("dst");
            }

            // グレースケールのみ
            if (src.Type() != MatType.CV_8UC1)
            {
                throw new ArgumentException("src must be gray scale image");
            }
            if (dst.Type() != MatType.CV_8UC1)
            {
                throw new ArgumentException("dst must be gray scale image");
            }

            // サイズのチェック
            if (kernelSize < 3)
            {
                throw new ArgumentOutOfRangeException("kernelSize", "size must be 3 and above");
            }
            if (kernelSize % 2 == 0)
            {
                throw new ArgumentOutOfRangeException("kernelSize", "size must be odd number");
            }

            int width  = src.Width;
            int height = src.Height;

            dst.Create(src.Size(), src.Type());

            using (var tSrcMat = new MatOfByte(src))
                using (var tDstMat = new MatOfByte(dst))
                {
                    var tSrc = tSrcMat.GetIndexer();
                    var tDst = tDstMat.GetIndexer();

                    //for (int y = 0; y < gray.Height; y++)
                    MyParallel.For(0, height, delegate(int y)
                    {
                        for (int x = 0; x < width; x++)
                        {
                            double m, s;
                            MeanStddev(src, x, y, kernelSize, out m, out s);
                            double threshold = m + k * s;

                            if (tSrc[y, x] < threshold)
                            {
                                tDst[y, x] = 0;
                            }
                            else
                            {
                                tDst[y, x] = 255;
                            }
                        }
                    }
                                   );
                }
        }