From ce27f04165523067e0f736d548e7a1e6dde92c03 Mon Sep 17 00:00:00 2001 From: Samyak Datta Date: Tue, 3 Mar 2015 17:44:37 +0530 Subject: [PATCH 1/2] Added module for Ni-Black thresholding Added doxygen comments and parameter descriptions. Added sample code demonstrating Niblack thresholding. --- modules/ximgproc/include/opencv2/ximgproc.hpp | 3 + .../include/opencv2/ximgproc/niblack.hpp | 88 +++++++++++++++ .../ximgproc/samples/niblack_thresholding.cpp | 58 ++++++++++ modules/ximgproc/src/niblack_thresholding.cpp | 100 ++++++++++++++++++ 4 files changed, 249 insertions(+) create mode 100644 modules/ximgproc/include/opencv2/ximgproc/niblack.hpp create mode 100644 modules/ximgproc/samples/niblack_thresholding.cpp create mode 100644 modules/ximgproc/src/niblack_thresholding.cpp diff --git a/modules/ximgproc/include/opencv2/ximgproc.hpp b/modules/ximgproc/include/opencv2/ximgproc.hpp index 69c0e7fe7..c62552fb8 100644 --- a/modules/ximgproc/include/opencv2/ximgproc.hpp +++ b/modules/ximgproc/include/opencv2/ximgproc.hpp @@ -40,6 +40,7 @@ #include "ximgproc/edge_filter.hpp" #include "ximgproc/structured_edge_detection.hpp" #include "ximgproc/seeds.hpp" +#include "ximgproc/niblack.hpp" /** @defgroup ximgproc Extended Image Processing @{ @@ -51,6 +52,8 @@ which somehow takes into account pixel affinities in natural images. @defgroup ximgproc_filters Filters @defgroup ximgproc_superpixel Superpixels + + @defgroup ximgproc_niblack Niblack Thresholding @} */ diff --git a/modules/ximgproc/include/opencv2/ximgproc/niblack.hpp b/modules/ximgproc/include/opencv2/ximgproc/niblack.hpp new file mode 100644 index 000000000..b093b4934 --- /dev/null +++ b/modules/ximgproc/include/opencv2/ximgproc/niblack.hpp @@ -0,0 +1,88 @@ +/*M/////////////////////////////////////////////////////////////////////////////////////// +// +// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING. +// +// By downloading, copying, installing or using the software you agree to this license. +// If you do not agree to this license, do not download, install, +// copy or use the software. +// +// +// License Agreement +// For Open Source Computer Vision Library +// +// Copyright (C) 2014, Beat Kueng (beat-kueng@gmx.net), Lukas Vogel, Morten Lysgaard +// Third party copyrights are property of their respective owners. +// +// Redistribution and use in source and binary forms, with or without modification, +// are permitted provided that the following conditions are met: +// +// * Redistribution's of source code must retain the above copyright notice, +// this list of conditions and the following disclaimer. +// +// * Redistribution's in binary form must reproduce the above copyright notice, +// this list of conditions and the following disclaimer in the documentation +// and/or other materials provided with the distribution. +// +// * The name of the copyright holders may not be used to endorse or promote products +// derived from this software without specific prior written permission. +// +// This software is provided by the copyright holders and contributors "as is" and +// any express or implied warranties, including, but not limited to, the implied +// warranties of merchantability and fitness for a particular purpose are disclaimed. +// In no event shall the Intel Corporation or contributors be liable for any direct, +// indirect, incidental, special, exemplary, or consequential damages +// (including, but not limited to, procurement of substitute goods or services; +// loss of use, data, or profits; or business interruption) however caused +// and on any theory of liability, whether in contract, strict liability, +// or tort (including negligence or otherwise) arising in any way out of +// the use of this software, even if advised of the possibility of such damage. +// +//M*/ + +#ifndef __OPENCV_NIBLACK_HPP__ +#define __OPENCV_NIBLACK_HPP__ +#ifdef __cplusplus + +#include + +namespace cv +{ + namespace ximgproc + { + //! @addtogroup ximgproc_niblack + //! @{ + + /** @brief Apply Niblack thresholding to input image. + + The function transforms a grayscale image to a binary image according to the formulae: +- **THRESH_BINARY** + \f[dst(x,y) = \fork{\texttt{maxValue}}{if \(src(x,y) > T(x,y)\)}{0}{otherwise}\f] +- **THRESH_BINARY_INV** + \f[dst(x,y) = \fork{0}{if \(src(x,y) > T(x,y)\)}{\texttt{maxValue}}{otherwise}\f] + where \f$T(x,y)\f$ is a threshold calculated individually for each pixel. + + The threshold value \f$T(x, y)\f$ is the mean minus \f$ delta \f$ times standard deviation + of \f$\texttt{blockSize} \times\texttt{blockSize}\f$ neighborhood of \f$(x, y)\f$. + + @param _src Source 8-bit single-channel image. + @param _dst Destination image of the same size and the same type as src. + @param maxValue Non-zero value assigned to the pixels for which the condition is satisfied + @param type Thresholding type that must be either THRESH_BINARY or THRESH_BINARY_INV, + see cv::ThresholdTypes. + @param blockSize Size of a pixel neighborhood that is used to calculate a threshold value for the + pixel: 3, 5, 7, and so on. + @param delta Constant multiplied with the standard deviation and subtracted from the mean. + Normally, it is taken to be a real number between 0 and 1. + + @sa threshold, adaptiveThreshold + */ + CV_EXPORTS_W + void niBlackThreshold( InputArray _src, OutputArray _dst, double maxValue, + int type, int blockSize, double delta ); + + //! @} + } +} + +#endif +#endif diff --git a/modules/ximgproc/samples/niblack_thresholding.cpp b/modules/ximgproc/samples/niblack_thresholding.cpp new file mode 100644 index 000000000..67f09b7e3 --- /dev/null +++ b/modules/ximgproc/samples/niblack_thresholding.cpp @@ -0,0 +1,58 @@ +/* + * Sample C++ to demonstrate Niblack thresholding. + * + */ + +#include +#include + +#include "opencv2/highgui.hpp" +#include "opencv2/core.hpp" +#include "opencv2/imgproc.hpp" + +#include "opencv2/ximgproc.hpp" + +using namespace std; +using namespace cv; +using namespace cv::ximgproc; + +Mat_ src, dst; + +const int k_max_value = 10; +int k_from_slider = 0; +double k_actual = 0.0; + +void on_trackbar(int, void*); + +int main(int argc, char** argv) +{ + /* + * Read filename from the command-line and load + * corresponding gray-scale image. + */ + if(argc != 2) + { + cout << "Usage: ./niblack_thresholding [IMAGE]\n"; + return 1; + } + const char* filename = argv[1]; + src = imread(filename, 1); + + namedWindow("k-slider", 1); + string trackbar_name = "k"; + createTrackbar(trackbar_name, "k-slider", &k_from_slider, k_max_value, on_trackbar); + on_trackbar(k_from_slider, 0); + + imshow("Source", src); + waitKey(0); + + return 0; +} + +void on_trackbar(int, void*) +{ + k_actual = (double)k_from_slider/k_max_value; + niBlackThreshold(src, dst, 255, THRESH_BINARY, 3, k_actual); + + imshow("Destination", dst); +} diff --git a/modules/ximgproc/src/niblack_thresholding.cpp b/modules/ximgproc/src/niblack_thresholding.cpp new file mode 100644 index 000000000..58b618e57 --- /dev/null +++ b/modules/ximgproc/src/niblack_thresholding.cpp @@ -0,0 +1,100 @@ +/*M/////////////////////////////////////////////////////////////////////////////////////// +// +// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING. +// +// By downloading, copying, installing or using the software you agree to this license. +// If you do not agree to this license, do not download, install, +// copy or use the software. +// +// +// License Agreement +// For Open Source Computer Vision Library +// +// Copyright (C) 2014, Beat Kueng (beat-kueng@gmx.net), Lukas Vogel, Morten Lysgaard +// Third party copyrights are property of their respective owners. +// +// Redistribution and use in source and binary forms, with or without modification, +// are permitted provided that the following conditions are met: +// +// * Redistribution's of source code must retain the above copyright notice, +// this list of conditions and the following disclaimer. +// +// * Redistribution's in binary form must reproduce the above copyright notice, +// this list of conditions and the following disclaimer in the documentation +// and/or other materials provided with the distribution. +// +// * The name of the copyright holders may not be used to endorse or promote products +// derived from this software without specific prior written permission. +// +// This software is provided by the copyright holders and contributors "as is" and +// any express or implied warranties, including, but not limited to, the implied +// warranties of merchantability and fitness for a particular purpose are disclaimed. +// In no event shall the Intel Corporation or contributors be liable for any direct, +// indirect, incidental, special, exemplary, or consequential damages +// (including, but not limited to, procurement of substitute goods or services; +// loss of use, data, or profits; or business interruption) however caused +// and on any theory of liability, whether in contract, strict liability, +// or tort (including negligence or otherwise) arising in any way out of +// the use of this software, even if advised of the possibility of such damage. +// +//M*/ + + +#include "precomp.hpp" +#include + +namespace cv { +namespace ximgproc { + +void niBlackThreshold( InputArray _src, OutputArray _dst, double maxValue, + int type, int blockSize, double delta ) +{ + Mat src = _src.getMat(); + CV_Assert( src.type() == CV_8UC1 ); + CV_Assert( blockSize % 2 == 1 && blockSize > 1 ); + Size size = src.size(); + + _dst.create( size, src.type() ); + Mat dst = _dst.getMat(); + + if( maxValue < 0 ) + { + dst = Scalar(0); + return; + } + + // Calculate and store the mean and mean of squares in the neighborhood + // of each pixel and store them in Mat mean and sqmean. + Mat_ mean(size), sqmean(size); + + if( src.data != dst.data ) + mean = dst; + + boxFilter( src, mean, CV_64F, Size(blockSize, blockSize), + Point(-1,-1), true, BORDER_REPLICATE ); + sqrBoxFilter( src, sqmean, CV_64F, Size(blockSize, blockSize), + Point(-1,-1), true, BORDER_REPLICATE ); + + // Compute (k * standard deviation) in the neighborhood of each pixel + // and store in Mat stddev. Also threshold the values in the src matrix to compute dst matrix. + Mat_ stddev(size); + int i, j, threshold; + uchar imaxval = saturate_cast(maxValue); + for(i = 0; i < size.height; ++i) + { + for(j = 0; j < size.width; ++j) + { + stddev.at(i, j) = delta * cvRound( sqrt(sqmean.at(i, j) - + mean.at(i, j)*mean.at(i, j)) ); + threshold = cvRound(mean.at(i, j) + stddev.at(i, j)); + if(src.at(i, j) > threshold) + dst.at(i, j) = (type == THRESH_BINARY) ? imaxval : 0; + else + dst.at(i, j) = (type == THRESH_BINARY) ? 0 : imaxval; + } + } + +} + +} // namespace ximgproc +} //namespace cv From e226d7853a98862d14b45ea4dbd163b1b880b310 Mon Sep 17 00:00:00 2001 From: Samyak Datta Date: Sun, 26 Jul 2015 18:56:32 +0530 Subject: [PATCH 2/2] Converted double to float and removed new module. All Niblack related code now resides inside ximgproc and not as a separate new module. --- modules/ximgproc/include/opencv2/ximgproc.hpp | 12 ++- .../include/opencv2/ximgproc/niblack.hpp | 88 ------------------- .../ximgproc/samples/niblack_thresholding.cpp | 4 +- modules/ximgproc/src/niblack_thresholding.cpp | 10 +-- 4 files changed, 16 insertions(+), 98 deletions(-) delete mode 100644 modules/ximgproc/include/opencv2/ximgproc/niblack.hpp diff --git a/modules/ximgproc/include/opencv2/ximgproc.hpp b/modules/ximgproc/include/opencv2/ximgproc.hpp index d801ee114..8c265a7a8 100644 --- a/modules/ximgproc/include/opencv2/ximgproc.hpp +++ b/modules/ximgproc/include/opencv2/ximgproc.hpp @@ -41,7 +41,6 @@ #include "ximgproc/disparity_filter.hpp" #include "ximgproc/structured_edge_detection.hpp" #include "ximgproc/seeds.hpp" -#include "ximgproc/niblack.hpp" /** @defgroup ximgproc Extended Image Processing @{ @@ -53,9 +52,16 @@ which somehow takes into account pixel affinities in natural images. @defgroup ximgproc_filters Filters @defgroup ximgproc_superpixel Superpixels - - @defgroup ximgproc_niblack Niblack Thresholding @} */ +namespace cv { +namespace ximgproc { + CV_EXPORTS_W + void niBlackThreshold( InputArray _src, OutputArray _dst, double maxValue, + int type, int blockSize, double delta ); + +} // namespace ximgproc +} //namespace cv + #endif diff --git a/modules/ximgproc/include/opencv2/ximgproc/niblack.hpp b/modules/ximgproc/include/opencv2/ximgproc/niblack.hpp deleted file mode 100644 index b093b4934..000000000 --- a/modules/ximgproc/include/opencv2/ximgproc/niblack.hpp +++ /dev/null @@ -1,88 +0,0 @@ -/*M/////////////////////////////////////////////////////////////////////////////////////// -// -// IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING. -// -// By downloading, copying, installing or using the software you agree to this license. -// If you do not agree to this license, do not download, install, -// copy or use the software. -// -// -// License Agreement -// For Open Source Computer Vision Library -// -// Copyright (C) 2014, Beat Kueng (beat-kueng@gmx.net), Lukas Vogel, Morten Lysgaard -// Third party copyrights are property of their respective owners. -// -// Redistribution and use in source and binary forms, with or without modification, -// are permitted provided that the following conditions are met: -// -// * Redistribution's of source code must retain the above copyright notice, -// this list of conditions and the following disclaimer. -// -// * Redistribution's in binary form must reproduce the above copyright notice, -// this list of conditions and the following disclaimer in the documentation -// and/or other materials provided with the distribution. -// -// * The name of the copyright holders may not be used to endorse or promote products -// derived from this software without specific prior written permission. -// -// This software is provided by the copyright holders and contributors "as is" and -// any express or implied warranties, including, but not limited to, the implied -// warranties of merchantability and fitness for a particular purpose are disclaimed. -// In no event shall the Intel Corporation or contributors be liable for any direct, -// indirect, incidental, special, exemplary, or consequential damages -// (including, but not limited to, procurement of substitute goods or services; -// loss of use, data, or profits; or business interruption) however caused -// and on any theory of liability, whether in contract, strict liability, -// or tort (including negligence or otherwise) arising in any way out of -// the use of this software, even if advised of the possibility of such damage. -// -//M*/ - -#ifndef __OPENCV_NIBLACK_HPP__ -#define __OPENCV_NIBLACK_HPP__ -#ifdef __cplusplus - -#include - -namespace cv -{ - namespace ximgproc - { - //! @addtogroup ximgproc_niblack - //! @{ - - /** @brief Apply Niblack thresholding to input image. - - The function transforms a grayscale image to a binary image according to the formulae: -- **THRESH_BINARY** - \f[dst(x,y) = \fork{\texttt{maxValue}}{if \(src(x,y) > T(x,y)\)}{0}{otherwise}\f] -- **THRESH_BINARY_INV** - \f[dst(x,y) = \fork{0}{if \(src(x,y) > T(x,y)\)}{\texttt{maxValue}}{otherwise}\f] - where \f$T(x,y)\f$ is a threshold calculated individually for each pixel. - - The threshold value \f$T(x, y)\f$ is the mean minus \f$ delta \f$ times standard deviation - of \f$\texttt{blockSize} \times\texttt{blockSize}\f$ neighborhood of \f$(x, y)\f$. - - @param _src Source 8-bit single-channel image. - @param _dst Destination image of the same size and the same type as src. - @param maxValue Non-zero value assigned to the pixels for which the condition is satisfied - @param type Thresholding type that must be either THRESH_BINARY or THRESH_BINARY_INV, - see cv::ThresholdTypes. - @param blockSize Size of a pixel neighborhood that is used to calculate a threshold value for the - pixel: 3, 5, 7, and so on. - @param delta Constant multiplied with the standard deviation and subtracted from the mean. - Normally, it is taken to be a real number between 0 and 1. - - @sa threshold, adaptiveThreshold - */ - CV_EXPORTS_W - void niBlackThreshold( InputArray _src, OutputArray _dst, double maxValue, - int type, int blockSize, double delta ); - - //! @} - } -} - -#endif -#endif diff --git a/modules/ximgproc/samples/niblack_thresholding.cpp b/modules/ximgproc/samples/niblack_thresholding.cpp index 67f09b7e3..fed7ca456 100644 --- a/modules/ximgproc/samples/niblack_thresholding.cpp +++ b/modules/ximgproc/samples/niblack_thresholding.cpp @@ -10,7 +10,7 @@ #include "opencv2/core.hpp" #include "opencv2/imgproc.hpp" -#include "opencv2/ximgproc.hpp" +#include "opencv2/ximgproc.hpp" using namespace std; using namespace cv; @@ -53,6 +53,6 @@ void on_trackbar(int, void*) { k_actual = (double)k_from_slider/k_max_value; niBlackThreshold(src, dst, 255, THRESH_BINARY, 3, k_actual); - + imshow("Destination", dst); } diff --git a/modules/ximgproc/src/niblack_thresholding.cpp b/modules/ximgproc/src/niblack_thresholding.cpp index 58b618e57..7167e6d94 100644 --- a/modules/ximgproc/src/niblack_thresholding.cpp +++ b/modules/ximgproc/src/niblack_thresholding.cpp @@ -65,7 +65,7 @@ void niBlackThreshold( InputArray _src, OutputArray _dst, double maxValue, // Calculate and store the mean and mean of squares in the neighborhood // of each pixel and store them in Mat mean and sqmean. - Mat_ mean(size), sqmean(size); + Mat_ mean(size), sqmean(size); if( src.data != dst.data ) mean = dst; @@ -77,16 +77,16 @@ void niBlackThreshold( InputArray _src, OutputArray _dst, double maxValue, // Compute (k * standard deviation) in the neighborhood of each pixel // and store in Mat stddev. Also threshold the values in the src matrix to compute dst matrix. - Mat_ stddev(size); + Mat_ stddev(size); int i, j, threshold; uchar imaxval = saturate_cast(maxValue); for(i = 0; i < size.height; ++i) { for(j = 0; j < size.width; ++j) { - stddev.at(i, j) = delta * cvRound( sqrt(sqmean.at(i, j) - - mean.at(i, j)*mean.at(i, j)) ); - threshold = cvRound(mean.at(i, j) + stddev.at(i, j)); + stddev.at(i, j) = saturate_cast(delta) * cvRound( sqrt(sqmean.at(i, j) - + mean.at(i, j)*mean.at(i, j)) ); + threshold = cvRound(mean.at(i, j) + stddev.at(i, j)); if(src.at(i, j) > threshold) dst.at(i, j) = (type == THRESH_BINARY) ? imaxval : 0; else