Added normType parameter to fastNlMeansDenoisingMulti

This commit is contained in:
Erik Karlsson 2015-03-24 02:01:31 +01:00
parent 70a64ebe72
commit 01d3df0d00
2 changed files with 107 additions and 52 deletions

View File

@ -142,7 +142,8 @@ CV_EXPORTS_W void fastNlMeansDenoising( InputArray src, OutputArray dst, float h
<http://www.ipol.im/pub/algo/bcm_non_local_means_denoising/> with several computational <http://www.ipol.im/pub/algo/bcm_non_local_means_denoising/> with several computational
optimizations. Noise expected to be a gaussian white noise optimizations. Noise expected to be a gaussian white noise
@param src Input 8-bit 1-channel, 2-channel, 3-channel or 4-channel image. @param src Input 8-bit or 16-bit (only with NORM_L1) 1-channel,
2-channel, 3-channel or 4-channel image.
@param dst Output image with the same size and type as src . @param dst Output image with the same size and type as src .
@param templateWindowSize Size in pixels of the template patch that is used to compute weights. @param templateWindowSize Size in pixels of the template patch that is used to compute weights.
Should be odd. Recommended value 7 pixels Should be odd. Recommended value 7 pixels
@ -153,7 +154,7 @@ denoising time. Recommended value 21 pixels
parameter applied to all channels or one per channel in dst. Big h value parameter applied to all channels or one per channel in dst. Big h value
perfectly removes noise but also removes image details, smaller h perfectly removes noise but also removes image details, smaller h
value preserves details but also preserves some noise value preserves details but also preserves some noise
@param normType Type of norm used for weight calcluation. Can be either NORM_L2 or NORM_L1 @param normType Type of norm used for weight calculation. Can be either NORM_L2 or NORM_L1
This function expected to be applied to grayscale images. For colored images look at This function expected to be applied to grayscale images. For colored images look at
fastNlMeansDenoisingColored. Advanced usage of this functions can be manual denoising of colored fastNlMeansDenoisingColored. Advanced usage of this functions can be manual denoising of colored
@ -220,9 +221,9 @@ captured in small period of time. For example video. This version of the functio
images or for manual manipulation with colorspaces. For more details see images or for manual manipulation with colorspaces. For more details see
<http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.131.6394> <http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.131.6394>
@param srcImgs Input 8-bit 1-channel, 2-channel, 3-channel or @param srcImgs Input 8-bit or 16-bit (only with NORM_L1) 1-channel,
4-channel images sequence. All images should have the same type and 2-channel, 3-channel or 4-channel images sequence. All images should
size. have the same type and size.
@param imgToDenoiseIndex Target image to denoise index in srcImgs sequence @param imgToDenoiseIndex Target image to denoise index in srcImgs sequence
@param temporalWindowSize Number of surrounding images to use for target image denoising. Should @param temporalWindowSize Number of surrounding images to use for target image denoising. Should
be odd. Images from imgToDenoiseIndex - temporalWindowSize / 2 to be odd. Images from imgToDenoiseIndex - temporalWindowSize / 2 to
@ -238,10 +239,13 @@ denoising time. Recommended value 21 pixels
parameter applied to all channels or one per channel in dst. Big h value parameter applied to all channels or one per channel in dst. Big h value
perfectly removes noise but also removes image details, smaller h perfectly removes noise but also removes image details, smaller h
value preserves details but also preserves some noise value preserves details but also preserves some noise
@param normType Type of norm used for weight calculation. Can be either NORM_L2 or NORM_L1
*/ */
CV_EXPORTS_W void fastNlMeansDenoisingMulti( InputArrayOfArrays srcImgs, OutputArray dst, CV_EXPORTS_W void fastNlMeansDenoisingMulti( InputArrayOfArrays srcImgs, OutputArray dst,
int imgToDenoiseIndex, int temporalWindowSize, int imgToDenoiseIndex, int temporalWindowSize,
const std::vector<float>& h , int templateWindowSize = 7, int searchWindowSize = 21); const std::vector<float>& h,
int templateWindowSize = 7, int searchWindowSize = 21,
int normType = NORM_L2);
/** @brief Modification of fastNlMeansDenoisingMulti function for colored images sequences /** @brief Modification of fastNlMeansDenoisingMulti function for colored images sequences

View File

@ -230,6 +230,64 @@ static void fastNlMeansDenoisingMultiCheckPreconditions(
} }
} }
template<typename ST, typename IT, typename UIT, typename D>
static void fastNlMeansDenoisingMulti_( const std::vector<Mat>& srcImgs, Mat& dst,
int imgToDenoiseIndex, int temporalWindowSize,
const std::vector<float>& h,
int templateWindowSize, int searchWindowSize)
{
int hn = (int)h.size();
switch (srcImgs[0].type())
{
case CV_8U:
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<uchar, IT, UIT, D, int>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
break;
case CV_8UC2:
if (hn == 1)
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec<ST, 2>, IT, UIT, D, int>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
else
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec<ST, 2>, IT, UIT, D, Vec2i>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
break;
case CV_8UC3:
if (hn == 1)
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec<ST, 3>, IT, UIT, D, int>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
else
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec<ST, 3>, IT, UIT, D, Vec3i>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
break;
case CV_8UC4:
if (hn == 1)
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec<ST, 4>, IT, UIT, D, int>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
else
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec<ST, 4>, IT, UIT, D, Vec4i>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
break;
default:
CV_Error(Error::StsBadArg,
"Unsupported image format! Only CV_8U, CV_8UC2, CV_8UC3 and CV_8UC4 are supported");
}
}
void cv::fastNlMeansDenoisingMulti( InputArrayOfArrays _srcImgs, OutputArray _dst, void cv::fastNlMeansDenoisingMulti( InputArrayOfArrays _srcImgs, OutputArray _dst,
int imgToDenoiseIndex, int temporalWindowSize, int imgToDenoiseIndex, int temporalWindowSize,
float h, int templateWindowSize, int searchWindowSize) float h, int templateWindowSize, int searchWindowSize)
@ -241,7 +299,7 @@ void cv::fastNlMeansDenoisingMulti( InputArrayOfArrays _srcImgs, OutputArray _ds
void cv::fastNlMeansDenoisingMulti( InputArrayOfArrays _srcImgs, OutputArray _dst, void cv::fastNlMeansDenoisingMulti( InputArrayOfArrays _srcImgs, OutputArray _dst,
int imgToDenoiseIndex, int temporalWindowSize, int imgToDenoiseIndex, int temporalWindowSize,
const std::vector<float>& h, const std::vector<float>& h,
int templateWindowSize, int searchWindowSize) int templateWindowSize, int searchWindowSize, int normType)
{ {
std::vector<Mat> srcImgs; std::vector<Mat> srcImgs;
_srcImgs.getMatVector(srcImgs); _srcImgs.getMatVector(srcImgs);
@ -251,58 +309,51 @@ void cv::fastNlMeansDenoisingMulti( InputArrayOfArrays _srcImgs, OutputArray _ds
temporalWindowSize, templateWindowSize, searchWindowSize); temporalWindowSize, templateWindowSize, searchWindowSize);
int hn = (int)h.size(); int hn = (int)h.size();
CV_Assert(hn == 1 || hn == CV_MAT_CN(srcImgs[0].type())); int type = srcImgs[0].type(), depth = CV_MAT_DEPTH(type), cn = CV_MAT_CN(type);
CV_Assert(hn == 1 || hn == cn);
_dst.create(srcImgs[0].size(), srcImgs[0].type()); _dst.create(srcImgs[0].size(), srcImgs[0].type());
Mat dst = _dst.getMat(); Mat dst = _dst.getMat();
switch (srcImgs[0].type()) switch (normType) {
{ case NORM_L2:
switch (depth) {
case CV_8U: case CV_8U:
parallel_for_(cv::Range(0, srcImgs[0].rows), fastNlMeansDenoisingMulti_<uchar, int, unsigned,
FastNlMeansMultiDenoisingInvoker<uchar, int, unsigned, DistSquared, int>( DistSquared>(srcImgs, dst,
srcImgs, imgToDenoiseIndex, temporalWindowSize, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0])); h,
break; templateWindowSize, searchWindowSize);
case CV_8UC2:
if (hn == 1)
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec2b, int, unsigned, DistSquared, int>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
else
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec2b, int, unsigned, DistSquared, Vec2i>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
break;
case CV_8UC3:
if (hn == 1)
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec3b, int, unsigned, DistSquared, int>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
else
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec3b, int, unsigned, DistSquared, Vec3i>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
break;
case CV_8UC4:
if (hn == 1)
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec4b, int, unsigned, DistSquared, int>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
else
parallel_for_(cv::Range(0, srcImgs[0].rows),
FastNlMeansMultiDenoisingInvoker<Vec4b, int, unsigned, DistSquared, Vec4i>(
srcImgs, imgToDenoiseIndex, temporalWindowSize,
dst, templateWindowSize, searchWindowSize, &h[0]));
break; break;
default: default:
CV_Error(Error::StsBadArg, CV_Error(Error::StsBadArg,
"Unsupported image format! Only CV_8U, CV_8UC2, CV_8UC3 and CV_8UC4 are supported"); "Unsupported depth! Only CV_8U is supported for NORM_L2");
}
break;
case NORM_L1:
switch (depth) {
case CV_8U:
fastNlMeansDenoisingMulti_<uchar, int, unsigned,
DistAbs>(srcImgs, dst,
imgToDenoiseIndex, temporalWindowSize,
h,
templateWindowSize, searchWindowSize);
break;
case CV_16U:
fastNlMeansDenoisingMulti_<ushort, int64, uint64,
DistAbs>(srcImgs, dst,
imgToDenoiseIndex, temporalWindowSize,
h,
templateWindowSize, searchWindowSize);
break;
default:
CV_Error(Error::StsBadArg,
"Unsupported depth! Only CV_8U and CV_16U are supported for NORM_L1");
}
break;
default:
CV_Error(Error::StsBadArg,
"Unsupported norm type! Only NORM_L2 and NORM_L1 are supported");
} }
} }