mirror of
https://github.com/opencv/opencv.git
synced 2025-06-08 01:53:19 +08:00
moved gpu nlm to photo module
This commit is contained in:
parent
fc3730fcc2
commit
e72ba73e70
@ -6,4 +6,4 @@ set(the_description "GPU-accelerated Image Processing")
|
|||||||
|
|
||||||
ocv_warnings_disable(CMAKE_CXX_FLAGS -Wundef -Wmissing-declarations -Wshadow -Wunused-parameter)
|
ocv_warnings_disable(CMAKE_CXX_FLAGS -Wundef -Wmissing-declarations -Wshadow -Wunused-parameter)
|
||||||
|
|
||||||
ocv_define_module(gpuimgproc opencv_imgproc opencv_gpuarithm opencv_gpufilters OPTIONAL opencv_photo)
|
ocv_define_module(gpuimgproc opencv_imgproc opencv_gpuarithm opencv_gpufilters)
|
||||||
|
@ -397,105 +397,7 @@ Performs bilateral filtering of passed image
|
|||||||
|
|
||||||
.. seealso::
|
.. seealso::
|
||||||
|
|
||||||
:ocv:func:`bilateralFilter`,
|
:ocv:func:`bilateralFilter`
|
||||||
|
|
||||||
|
|
||||||
gpu::nonLocalMeans
|
|
||||||
-------------------
|
|
||||||
Performs pure non local means denoising without any simplification, and thus it is not fast.
|
|
||||||
|
|
||||||
.. ocv:function:: void gpu::nonLocalMeans(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, int borderMode = BORDER_DEFAULT, Stream& s = Stream::Null())
|
|
||||||
|
|
||||||
:param src: Source image. Supports only CV_8UC1, CV_8UC2 and CV_8UC3.
|
|
||||||
|
|
||||||
:param dst: Destination image.
|
|
||||||
|
|
||||||
:param h: Filter sigma regulating filter strength for color.
|
|
||||||
|
|
||||||
:param search_window: Size of search window.
|
|
||||||
|
|
||||||
:param block_size: Size of block used for computing weights.
|
|
||||||
|
|
||||||
:param borderMode: Border type. See :ocv:func:`borderInterpolate` for details. ``BORDER_REFLECT101`` , ``BORDER_REPLICATE`` , ``BORDER_CONSTANT`` , ``BORDER_REFLECT`` and ``BORDER_WRAP`` are supported for now.
|
|
||||||
|
|
||||||
:param stream: Stream for the asynchronous version.
|
|
||||||
|
|
||||||
.. seealso::
|
|
||||||
|
|
||||||
:ocv:func:`fastNlMeansDenoising`
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
gpu::FastNonLocalMeansDenoising
|
|
||||||
-------------------------------
|
|
||||||
.. ocv:class:: gpu::FastNonLocalMeansDenoising
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
class FastNonLocalMeansDenoising
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
//! Simple method, recommended for grayscale images (though it supports multichannel images)
|
|
||||||
void simpleMethod(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
|
||||||
//! Processes luminance and color components separatelly
|
|
||||||
void labMethod(const GpuMat& src, GpuMat& dst, float h_luminance, float h_color, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
|
||||||
};
|
|
||||||
|
|
||||||
The class implements fast approximate Non Local Means Denoising algorithm.
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
gpu::FastNonLocalMeansDenoising::simpleMethod()
|
|
||||||
-----------------------------------------------
|
|
||||||
Perform image denoising using Non-local Means Denoising algorithm http://www.ipol.im/pub/algo/bcm_non_local_means_denoising with several computational optimizations. Noise expected to be a gaussian white noise
|
|
||||||
|
|
||||||
.. ocv:function:: void gpu::FastNonLocalMeansDenoising::simpleMethod(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
|
||||||
|
|
||||||
:param src: Input 8-bit 1-channel, 2-channel or 3-channel image.
|
|
||||||
|
|
||||||
:param dst: Output image with the same size and type as ``src`` .
|
|
||||||
|
|
||||||
:param h: Parameter regulating filter strength. Big h value perfectly removes noise but also removes image details, smaller h value preserves details but also preserves some noise
|
|
||||||
|
|
||||||
:param search_window: Size in pixels of the window that is used to compute weighted average for given pixel. Should be odd. Affect performance linearly: greater search_window - greater denoising time. Recommended value 21 pixels
|
|
||||||
|
|
||||||
:param block_size: Size in pixels of the template patch that is used to compute weights. Should be odd. Recommended value 7 pixels
|
|
||||||
|
|
||||||
:param stream: Stream for the asynchronous invocations.
|
|
||||||
|
|
||||||
This function expected to be applied to grayscale images. For colored images look at ``FastNonLocalMeansDenoising::labMethod``.
|
|
||||||
|
|
||||||
.. seealso::
|
|
||||||
|
|
||||||
:ocv:func:`fastNlMeansDenoising`
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
gpu::FastNonLocalMeansDenoising::labMethod()
|
|
||||||
--------------------------------------------
|
|
||||||
Modification of ``FastNonLocalMeansDenoising::simpleMethod`` for color images
|
|
||||||
|
|
||||||
.. ocv:function:: void gpu::FastNonLocalMeansDenoising::labMethod(const GpuMat& src, GpuMat& dst, float h_luminance, float h_color, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
|
||||||
|
|
||||||
:param src: Input 8-bit 3-channel image.
|
|
||||||
|
|
||||||
:param dst: Output image with the same size and type as ``src`` .
|
|
||||||
|
|
||||||
:param h_luminance: Parameter regulating filter strength. Big h value perfectly removes noise but also removes image details, smaller h value preserves details but also preserves some noise
|
|
||||||
|
|
||||||
:param float: The same as h but for color components. For most images value equals 10 will be enought to remove colored noise and do not distort colors
|
|
||||||
|
|
||||||
:param search_window: Size in pixels of the window that is used to compute weighted average for given pixel. Should be odd. Affect performance linearly: greater search_window - greater denoising time. Recommended value 21 pixels
|
|
||||||
|
|
||||||
:param block_size: Size in pixels of the template patch that is used to compute weights. Should be odd. Recommended value 7 pixels
|
|
||||||
|
|
||||||
:param stream: Stream for the asynchronous invocations.
|
|
||||||
|
|
||||||
The function converts image to CIELAB colorspace and then separately denoise L and AB components with given h parameters using ``FastNonLocalMeansDenoising::simpleMethod`` function.
|
|
||||||
|
|
||||||
.. seealso::
|
|
||||||
|
|
||||||
:ocv:func:`fastNlMeansDenoisingColored`
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -143,25 +143,6 @@ CV_EXPORTS void blendLinear(const GpuMat& img1, const GpuMat& img2, const GpuMat
|
|||||||
CV_EXPORTS void bilateralFilter(const GpuMat& src, GpuMat& dst, int kernel_size, float sigma_color, float sigma_spatial,
|
CV_EXPORTS void bilateralFilter(const GpuMat& src, GpuMat& dst, int kernel_size, float sigma_color, float sigma_spatial,
|
||||||
int borderMode = BORDER_DEFAULT, Stream& stream = Stream::Null());
|
int borderMode = BORDER_DEFAULT, Stream& stream = Stream::Null());
|
||||||
|
|
||||||
//! Brute force non-local means algorith (slow but universal)
|
|
||||||
CV_EXPORTS void nonLocalMeans(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, int borderMode = BORDER_DEFAULT, Stream& s = Stream::Null());
|
|
||||||
|
|
||||||
//! Fast (but approximate)version of non-local means algorith similar to CPU function (running sums technique)
|
|
||||||
class CV_EXPORTS FastNonLocalMeansDenoising
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
//! Simple method, recommended for grayscale images (though it supports multichannel images)
|
|
||||||
void simpleMethod(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, Stream& s = Stream::Null());
|
|
||||||
|
|
||||||
//! Processes luminance and color components separatelly
|
|
||||||
void labMethod(const GpuMat& src, GpuMat& dst, float h_luminance, float h_color, int search_window = 21, int block_size = 7, Stream& s = Stream::Null());
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
GpuMat buffer, extended_src_buffer;
|
|
||||||
GpuMat lab, l, ab;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct CV_EXPORTS CannyBuf
|
struct CV_EXPORTS CannyBuf
|
||||||
{
|
{
|
||||||
void create(const Size& image_size, int apperture_size = 3);
|
void create(const Size& image_size, int apperture_size = 3);
|
||||||
|
@ -1046,3 +1046,49 @@ PERF_TEST_P(Method_Sz, GeneralizedHough,
|
|||||||
CPU_SANITY_CHECK(positions);
|
CPU_SANITY_CHECK(positions);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////
|
||||||
|
// BilateralFilter
|
||||||
|
|
||||||
|
DEF_PARAM_TEST(Sz_Depth_Cn_KernelSz, cv::Size, MatDepth, MatCn, int);
|
||||||
|
|
||||||
|
PERF_TEST_P(Sz_Depth_Cn_KernelSz, BilateralFilter,
|
||||||
|
Combine(GPU_TYPICAL_MAT_SIZES,
|
||||||
|
Values(CV_8U, CV_32F),
|
||||||
|
GPU_CHANNELS_1_3,
|
||||||
|
Values(3, 5, 9)))
|
||||||
|
{
|
||||||
|
declare.time(60.0);
|
||||||
|
|
||||||
|
const cv::Size size = GET_PARAM(0);
|
||||||
|
const int depth = GET_PARAM(1);
|
||||||
|
const int channels = GET_PARAM(2);
|
||||||
|
const int kernel_size = GET_PARAM(3);
|
||||||
|
|
||||||
|
const float sigma_color = 7;
|
||||||
|
const float sigma_spatial = 5;
|
||||||
|
const int borderMode = cv::BORDER_REFLECT101;
|
||||||
|
|
||||||
|
const int type = CV_MAKE_TYPE(depth, channels);
|
||||||
|
|
||||||
|
cv::Mat src(size, type);
|
||||||
|
declare.in(src, WARMUP_RNG);
|
||||||
|
|
||||||
|
if (PERF_RUN_GPU())
|
||||||
|
{
|
||||||
|
const cv::gpu::GpuMat d_src(src);
|
||||||
|
cv::gpu::GpuMat dst;
|
||||||
|
|
||||||
|
TEST_CYCLE() cv::gpu::bilateralFilter(d_src, dst, kernel_size, sigma_color, sigma_spatial, borderMode);
|
||||||
|
|
||||||
|
GPU_SANITY_CHECK(dst);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
cv::Mat dst;
|
||||||
|
|
||||||
|
TEST_CYCLE() cv::bilateralFilter(src, dst, kernel_size, sigma_color, sigma_spatial, borderMode);
|
||||||
|
|
||||||
|
CPU_SANITY_CHECK(dst);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -57,8 +57,6 @@
|
|||||||
#include "opencv2/gpuimgproc.hpp"
|
#include "opencv2/gpuimgproc.hpp"
|
||||||
#include "opencv2/imgproc.hpp"
|
#include "opencv2/imgproc.hpp"
|
||||||
|
|
||||||
#include "opencv2/photo.hpp"
|
|
||||||
|
|
||||||
#ifdef GTEST_CREATE_SHARED_LIBRARY
|
#ifdef GTEST_CREATE_SHARED_LIBRARY
|
||||||
#error no modules except ts should have GTEST_CREATE_SHARED_LIBRARY defined
|
#error no modules except ts should have GTEST_CREATE_SHARED_LIBRARY defined
|
||||||
#endif
|
#endif
|
||||||
|
99
modules/gpuimgproc/src/bilateral_filter.cpp
Normal file
99
modules/gpuimgproc/src/bilateral_filter.cpp
Normal file
@ -0,0 +1,99 @@
|
|||||||
|
/*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) 2000-2008, Intel Corporation, all rights reserved.
|
||||||
|
// Copyright (C) 2009, Willow Garage Inc., all rights reserved.
|
||||||
|
// 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"
|
||||||
|
|
||||||
|
using namespace cv;
|
||||||
|
using namespace cv::gpu;
|
||||||
|
|
||||||
|
#if !defined (HAVE_CUDA) || defined (CUDA_DISABLER)
|
||||||
|
|
||||||
|
void cv::gpu::bilateralFilter(const GpuMat&, GpuMat&, int, float, float, int, Stream&) { throw_no_cuda(); }
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
namespace cv { namespace gpu { namespace cudev
|
||||||
|
{
|
||||||
|
namespace imgproc
|
||||||
|
{
|
||||||
|
template<typename T>
|
||||||
|
void bilateral_filter_gpu(const PtrStepSzb& src, PtrStepSzb dst, int kernel_size, float sigma_spatial, float sigma_color, int borderMode, cudaStream_t stream);
|
||||||
|
}
|
||||||
|
}}}
|
||||||
|
|
||||||
|
void cv::gpu::bilateralFilter(const GpuMat& src, GpuMat& dst, int kernel_size, float sigma_color, float sigma_spatial, int borderMode, Stream& s)
|
||||||
|
{
|
||||||
|
using cv::gpu::cudev::imgproc::bilateral_filter_gpu;
|
||||||
|
|
||||||
|
typedef void (*func_t)(const PtrStepSzb& src, PtrStepSzb dst, int kernel_size, float sigma_spatial, float sigma_color, int borderMode, cudaStream_t s);
|
||||||
|
|
||||||
|
static const func_t funcs[6][4] =
|
||||||
|
{
|
||||||
|
{bilateral_filter_gpu<uchar> , 0 /*bilateral_filter_gpu<uchar2>*/ , bilateral_filter_gpu<uchar3> , bilateral_filter_gpu<uchar4> },
|
||||||
|
{0 /*bilateral_filter_gpu<schar>*/, 0 /*bilateral_filter_gpu<schar2>*/ , 0 /*bilateral_filter_gpu<schar3>*/, 0 /*bilateral_filter_gpu<schar4>*/},
|
||||||
|
{bilateral_filter_gpu<ushort> , 0 /*bilateral_filter_gpu<ushort2>*/, bilateral_filter_gpu<ushort3> , bilateral_filter_gpu<ushort4> },
|
||||||
|
{bilateral_filter_gpu<short> , 0 /*bilateral_filter_gpu<short2>*/ , bilateral_filter_gpu<short3> , bilateral_filter_gpu<short4> },
|
||||||
|
{0 /*bilateral_filter_gpu<int>*/ , 0 /*bilateral_filter_gpu<int2>*/ , 0 /*bilateral_filter_gpu<int3>*/ , 0 /*bilateral_filter_gpu<int4>*/ },
|
||||||
|
{bilateral_filter_gpu<float> , 0 /*bilateral_filter_gpu<float2>*/ , bilateral_filter_gpu<float3> , bilateral_filter_gpu<float4> }
|
||||||
|
};
|
||||||
|
|
||||||
|
sigma_color = (sigma_color <= 0 ) ? 1 : sigma_color;
|
||||||
|
sigma_spatial = (sigma_spatial <= 0 ) ? 1 : sigma_spatial;
|
||||||
|
|
||||||
|
|
||||||
|
int radius = (kernel_size <= 0) ? cvRound(sigma_spatial*1.5) : kernel_size/2;
|
||||||
|
kernel_size = std::max(radius, 1)*2 + 1;
|
||||||
|
|
||||||
|
CV_Assert(src.depth() <= CV_32F && src.channels() <= 4);
|
||||||
|
const func_t func = funcs[src.depth()][src.channels() - 1];
|
||||||
|
CV_Assert(func != 0);
|
||||||
|
|
||||||
|
CV_Assert(borderMode == BORDER_REFLECT101 || borderMode == BORDER_REPLICATE || borderMode == BORDER_CONSTANT || borderMode == BORDER_REFLECT || borderMode == BORDER_WRAP);
|
||||||
|
|
||||||
|
int gpuBorderType;
|
||||||
|
CV_Assert(tryConvertToGpuBorderType(borderMode, gpuBorderType));
|
||||||
|
|
||||||
|
dst.create(src.size(), src.type());
|
||||||
|
func(src, dst, kernel_size, sigma_spatial, sigma_color, gpuBorderType, StreamAccessor::getStream(s));
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
@ -881,7 +881,7 @@ GPU_TEST_P(BilateralFilter, Accuracy)
|
|||||||
EXPECT_MAT_NEAR(dst_gold, dst, src.depth() == CV_32F ? 1e-3 : 1.0);
|
EXPECT_MAT_NEAR(dst_gold, dst, src.depth() == CV_32F ? 1e-3 : 1.0);
|
||||||
}
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(GPU_Denoising, BilateralFilter, testing::Combine(
|
INSTANTIATE_TEST_CASE_P(GPU_ImgProc, BilateralFilter, testing::Combine(
|
||||||
ALL_DEVICES,
|
ALL_DEVICES,
|
||||||
testing::Values(cv::Size(128, 128), cv::Size(113, 113), cv::Size(639, 481)),
|
testing::Values(cv::Size(128, 128), cv::Size(113, 113), cv::Size(639, 481)),
|
||||||
testing::Values(MatType(CV_8UC1), MatType(CV_8UC3), MatType(CV_32FC1), MatType(CV_32FC3))
|
testing::Values(MatType(CV_8UC1), MatType(CV_8UC3), MatType(CV_32FC1), MatType(CV_32FC3))
|
||||||
|
@ -1,2 +1,2 @@
|
|||||||
set(the_description "Computational Photography")
|
set(the_description "Computational Photography")
|
||||||
ocv_define_module(photo opencv_imgproc)
|
ocv_define_module(photo opencv_imgproc OPTIONAL opencv_gpuimgproc)
|
||||||
|
@ -89,3 +89,102 @@ Modification of ``fastNlMeansDenoisingMulti`` function for colored images sequen
|
|||||||
|
|
||||||
The function converts images to CIELAB colorspace and then separately denoise L and AB components with given h parameters using ``fastNlMeansDenoisingMulti`` function.
|
The function converts images to CIELAB colorspace and then separately denoise L and AB components with given h parameters using ``fastNlMeansDenoisingMulti`` function.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
gpu::nonLocalMeans
|
||||||
|
-------------------
|
||||||
|
Performs pure non local means denoising without any simplification, and thus it is not fast.
|
||||||
|
|
||||||
|
.. ocv:function:: void gpu::nonLocalMeans(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, int borderMode = BORDER_DEFAULT, Stream& s = Stream::Null())
|
||||||
|
|
||||||
|
:param src: Source image. Supports only CV_8UC1, CV_8UC2 and CV_8UC3.
|
||||||
|
|
||||||
|
:param dst: Destination image.
|
||||||
|
|
||||||
|
:param h: Filter sigma regulating filter strength for color.
|
||||||
|
|
||||||
|
:param search_window: Size of search window.
|
||||||
|
|
||||||
|
:param block_size: Size of block used for computing weights.
|
||||||
|
|
||||||
|
:param borderMode: Border type. See :ocv:func:`borderInterpolate` for details. ``BORDER_REFLECT101`` , ``BORDER_REPLICATE`` , ``BORDER_CONSTANT`` , ``BORDER_REFLECT`` and ``BORDER_WRAP`` are supported for now.
|
||||||
|
|
||||||
|
:param stream: Stream for the asynchronous version.
|
||||||
|
|
||||||
|
.. seealso::
|
||||||
|
|
||||||
|
:ocv:func:`fastNlMeansDenoising`
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
gpu::FastNonLocalMeansDenoising
|
||||||
|
-------------------------------
|
||||||
|
.. ocv:class:: gpu::FastNonLocalMeansDenoising
|
||||||
|
|
||||||
|
::
|
||||||
|
|
||||||
|
class FastNonLocalMeansDenoising
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
//! Simple method, recommended for grayscale images (though it supports multichannel images)
|
||||||
|
void simpleMethod(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
||||||
|
//! Processes luminance and color components separatelly
|
||||||
|
void labMethod(const GpuMat& src, GpuMat& dst, float h_luminance, float h_color, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
||||||
|
};
|
||||||
|
|
||||||
|
The class implements fast approximate Non Local Means Denoising algorithm.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
gpu::FastNonLocalMeansDenoising::simpleMethod()
|
||||||
|
-----------------------------------------------
|
||||||
|
Perform image denoising using Non-local Means Denoising algorithm http://www.ipol.im/pub/algo/bcm_non_local_means_denoising with several computational optimizations. Noise expected to be a gaussian white noise
|
||||||
|
|
||||||
|
.. ocv:function:: void gpu::FastNonLocalMeansDenoising::simpleMethod(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
||||||
|
|
||||||
|
:param src: Input 8-bit 1-channel, 2-channel or 3-channel image.
|
||||||
|
|
||||||
|
:param dst: Output image with the same size and type as ``src`` .
|
||||||
|
|
||||||
|
:param h: Parameter regulating filter strength. Big h value perfectly removes noise but also removes image details, smaller h value preserves details but also preserves some noise
|
||||||
|
|
||||||
|
:param search_window: Size in pixels of the window that is used to compute weighted average for given pixel. Should be odd. Affect performance linearly: greater search_window - greater denoising time. Recommended value 21 pixels
|
||||||
|
|
||||||
|
:param block_size: Size in pixels of the template patch that is used to compute weights. Should be odd. Recommended value 7 pixels
|
||||||
|
|
||||||
|
:param stream: Stream for the asynchronous invocations.
|
||||||
|
|
||||||
|
This function expected to be applied to grayscale images. For colored images look at ``FastNonLocalMeansDenoising::labMethod``.
|
||||||
|
|
||||||
|
.. seealso::
|
||||||
|
|
||||||
|
:ocv:func:`fastNlMeansDenoising`
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
gpu::FastNonLocalMeansDenoising::labMethod()
|
||||||
|
--------------------------------------------
|
||||||
|
Modification of ``FastNonLocalMeansDenoising::simpleMethod`` for color images
|
||||||
|
|
||||||
|
.. ocv:function:: void gpu::FastNonLocalMeansDenoising::labMethod(const GpuMat& src, GpuMat& dst, float h_luminance, float h_color, int search_window = 21, int block_size = 7, Stream& s = Stream::Null())
|
||||||
|
|
||||||
|
:param src: Input 8-bit 3-channel image.
|
||||||
|
|
||||||
|
:param dst: Output image with the same size and type as ``src`` .
|
||||||
|
|
||||||
|
:param h_luminance: Parameter regulating filter strength. Big h value perfectly removes noise but also removes image details, smaller h value preserves details but also preserves some noise
|
||||||
|
|
||||||
|
:param float: The same as h but for color components. For most images value equals 10 will be enought to remove colored noise and do not distort colors
|
||||||
|
|
||||||
|
:param search_window: Size in pixels of the window that is used to compute weighted average for given pixel. Should be odd. Affect performance linearly: greater search_window - greater denoising time. Recommended value 21 pixels
|
||||||
|
|
||||||
|
:param block_size: Size in pixels of the template patch that is used to compute weights. Should be odd. Recommended value 7 pixels
|
||||||
|
|
||||||
|
:param stream: Stream for the asynchronous invocations.
|
||||||
|
|
||||||
|
The function converts image to CIELAB colorspace and then separately denoise L and AB components with given h parameters using ``FastNonLocalMeansDenoising::simpleMethod`` function.
|
||||||
|
|
||||||
|
.. seealso::
|
||||||
|
|
||||||
|
:ocv:func:`fastNlMeansDenoisingColored`
|
||||||
|
|
||||||
|
71
modules/photo/include/opencv2/photo/gpu.hpp
Normal file
71
modules/photo/include/opencv2/photo/gpu.hpp
Normal file
@ -0,0 +1,71 @@
|
|||||||
|
/*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) 2000-2008, Intel Corporation, all rights reserved.
|
||||||
|
// Copyright (C) 2008-2012, Willow Garage Inc., all rights reserved.
|
||||||
|
// 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_PHOTO_GPU_HPP__
|
||||||
|
#define __OPENCV_PHOTO_GPU_HPP__
|
||||||
|
|
||||||
|
#include "opencv2/core/gpumat.hpp"
|
||||||
|
|
||||||
|
namespace cv { namespace gpu {
|
||||||
|
|
||||||
|
//! Brute force non-local means algorith (slow but universal)
|
||||||
|
CV_EXPORTS void nonLocalMeans(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, int borderMode = BORDER_DEFAULT, Stream& s = Stream::Null());
|
||||||
|
|
||||||
|
//! Fast (but approximate)version of non-local means algorith similar to CPU function (running sums technique)
|
||||||
|
class CV_EXPORTS FastNonLocalMeansDenoising
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
//! Simple method, recommended for grayscale images (though it supports multichannel images)
|
||||||
|
void simpleMethod(const GpuMat& src, GpuMat& dst, float h, int search_window = 21, int block_size = 7, Stream& s = Stream::Null());
|
||||||
|
|
||||||
|
//! Processes luminance and color components separatelly
|
||||||
|
void labMethod(const GpuMat& src, GpuMat& dst, float h_luminance, float h_color, int search_window = 21, int block_size = 7, Stream& s = Stream::Null());
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
GpuMat buffer, extended_src_buffer;
|
||||||
|
GpuMat lab, l, ab;
|
||||||
|
};
|
||||||
|
|
||||||
|
}} // namespace cv { namespace gpu {
|
||||||
|
|
||||||
|
#endif /* __OPENCV_PHOTO_GPU_HPP__ */
|
@ -42,58 +42,15 @@
|
|||||||
|
|
||||||
#include "perf_precomp.hpp"
|
#include "perf_precomp.hpp"
|
||||||
|
|
||||||
|
#include "opencv2/photo/gpu.hpp"
|
||||||
|
#include "opencv2/ts/gpu_perf.hpp"
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
using namespace testing;
|
using namespace testing;
|
||||||
using namespace perf;
|
using namespace perf;
|
||||||
|
|
||||||
#define GPU_DENOISING_IMAGE_SIZES testing::Values(perf::szVGA, perf::sz720p)
|
#define GPU_DENOISING_IMAGE_SIZES testing::Values(perf::szVGA, perf::sz720p)
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////
|
|
||||||
// BilateralFilter
|
|
||||||
|
|
||||||
DEF_PARAM_TEST(Sz_Depth_Cn_KernelSz, cv::Size, MatDepth, MatCn, int);
|
|
||||||
|
|
||||||
PERF_TEST_P(Sz_Depth_Cn_KernelSz, Denoising_BilateralFilter,
|
|
||||||
Combine(GPU_DENOISING_IMAGE_SIZES,
|
|
||||||
Values(CV_8U, CV_32F),
|
|
||||||
GPU_CHANNELS_1_3,
|
|
||||||
Values(3, 5, 9)))
|
|
||||||
{
|
|
||||||
declare.time(60.0);
|
|
||||||
|
|
||||||
const cv::Size size = GET_PARAM(0);
|
|
||||||
const int depth = GET_PARAM(1);
|
|
||||||
const int channels = GET_PARAM(2);
|
|
||||||
const int kernel_size = GET_PARAM(3);
|
|
||||||
|
|
||||||
const float sigma_color = 7;
|
|
||||||
const float sigma_spatial = 5;
|
|
||||||
const int borderMode = cv::BORDER_REFLECT101;
|
|
||||||
|
|
||||||
const int type = CV_MAKE_TYPE(depth, channels);
|
|
||||||
|
|
||||||
cv::Mat src(size, type);
|
|
||||||
declare.in(src, WARMUP_RNG);
|
|
||||||
|
|
||||||
if (PERF_RUN_GPU())
|
|
||||||
{
|
|
||||||
const cv::gpu::GpuMat d_src(src);
|
|
||||||
cv::gpu::GpuMat dst;
|
|
||||||
|
|
||||||
TEST_CYCLE() cv::gpu::bilateralFilter(d_src, dst, kernel_size, sigma_color, sigma_spatial, borderMode);
|
|
||||||
|
|
||||||
GPU_SANITY_CHECK(dst);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cv::Mat dst;
|
|
||||||
|
|
||||||
TEST_CYCLE() cv::bilateralFilter(src, dst, kernel_size, sigma_color, sigma_spatial, borderMode);
|
|
||||||
|
|
||||||
CPU_SANITY_CHECK(dst);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////
|
||||||
// nonLocalMeans
|
// nonLocalMeans
|
||||||
|
|
@ -42,18 +42,20 @@
|
|||||||
|
|
||||||
#include "precomp.hpp"
|
#include "precomp.hpp"
|
||||||
|
|
||||||
|
#include "opencv2/photo/gpu.hpp"
|
||||||
|
#include "opencv2/core/gpu_private.hpp"
|
||||||
|
#include "opencv2/gpuarithm.hpp"
|
||||||
|
#include "opencv2/gpuimgproc.hpp"
|
||||||
|
|
||||||
using namespace cv;
|
using namespace cv;
|
||||||
using namespace cv::gpu;
|
using namespace cv::gpu;
|
||||||
|
|
||||||
#if !defined (HAVE_CUDA) || defined (CUDA_DISABLER)
|
#if !defined (HAVE_CUDA) || defined (CUDA_DISABLER)
|
||||||
|
|
||||||
void cv::gpu::bilateralFilter(const GpuMat&, GpuMat&, int, float, float, int, Stream&) { throw_no_cuda(); }
|
|
||||||
void cv::gpu::nonLocalMeans(const GpuMat&, GpuMat&, float, int, int, int, Stream&) { throw_no_cuda(); }
|
void cv::gpu::nonLocalMeans(const GpuMat&, GpuMat&, float, int, int, int, Stream&) { throw_no_cuda(); }
|
||||||
|
|
||||||
void cv::gpu::FastNonLocalMeansDenoising::simpleMethod(const GpuMat&, GpuMat&, float, int, int, Stream&) { throw_no_cuda(); }
|
void cv::gpu::FastNonLocalMeansDenoising::simpleMethod(const GpuMat&, GpuMat&, float, int, int, Stream&) { throw_no_cuda(); }
|
||||||
void cv::gpu::FastNonLocalMeansDenoising::labMethod( const GpuMat&, GpuMat&, float, float, int, int, Stream&) { throw_no_cuda(); }
|
void cv::gpu::FastNonLocalMeansDenoising::labMethod( const GpuMat&, GpuMat&, float, float, int, int, Stream&) { throw_no_cuda(); }
|
||||||
|
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////////
|
||||||
@ -63,50 +65,11 @@ namespace cv { namespace gpu { namespace cudev
|
|||||||
{
|
{
|
||||||
namespace imgproc
|
namespace imgproc
|
||||||
{
|
{
|
||||||
template<typename T>
|
|
||||||
void bilateral_filter_gpu(const PtrStepSzb& src, PtrStepSzb dst, int kernel_size, float sigma_spatial, float sigma_color, int borderMode, cudaStream_t stream);
|
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
void nlm_bruteforce_gpu(const PtrStepSzb& src, PtrStepSzb dst, int search_radius, int block_radius, float h, int borderMode, cudaStream_t stream);
|
void nlm_bruteforce_gpu(const PtrStepSzb& src, PtrStepSzb dst, int search_radius, int block_radius, float h, int borderMode, cudaStream_t stream);
|
||||||
}
|
}
|
||||||
}}}
|
}}}
|
||||||
|
|
||||||
void cv::gpu::bilateralFilter(const GpuMat& src, GpuMat& dst, int kernel_size, float sigma_color, float sigma_spatial, int borderMode, Stream& s)
|
|
||||||
{
|
|
||||||
using cv::gpu::cudev::imgproc::bilateral_filter_gpu;
|
|
||||||
|
|
||||||
typedef void (*func_t)(const PtrStepSzb& src, PtrStepSzb dst, int kernel_size, float sigma_spatial, float sigma_color, int borderMode, cudaStream_t s);
|
|
||||||
|
|
||||||
static const func_t funcs[6][4] =
|
|
||||||
{
|
|
||||||
{bilateral_filter_gpu<uchar> , 0 /*bilateral_filter_gpu<uchar2>*/ , bilateral_filter_gpu<uchar3> , bilateral_filter_gpu<uchar4> },
|
|
||||||
{0 /*bilateral_filter_gpu<schar>*/, 0 /*bilateral_filter_gpu<schar2>*/ , 0 /*bilateral_filter_gpu<schar3>*/, 0 /*bilateral_filter_gpu<schar4>*/},
|
|
||||||
{bilateral_filter_gpu<ushort> , 0 /*bilateral_filter_gpu<ushort2>*/, bilateral_filter_gpu<ushort3> , bilateral_filter_gpu<ushort4> },
|
|
||||||
{bilateral_filter_gpu<short> , 0 /*bilateral_filter_gpu<short2>*/ , bilateral_filter_gpu<short3> , bilateral_filter_gpu<short4> },
|
|
||||||
{0 /*bilateral_filter_gpu<int>*/ , 0 /*bilateral_filter_gpu<int2>*/ , 0 /*bilateral_filter_gpu<int3>*/ , 0 /*bilateral_filter_gpu<int4>*/ },
|
|
||||||
{bilateral_filter_gpu<float> , 0 /*bilateral_filter_gpu<float2>*/ , bilateral_filter_gpu<float3> , bilateral_filter_gpu<float4> }
|
|
||||||
};
|
|
||||||
|
|
||||||
sigma_color = (sigma_color <= 0 ) ? 1 : sigma_color;
|
|
||||||
sigma_spatial = (sigma_spatial <= 0 ) ? 1 : sigma_spatial;
|
|
||||||
|
|
||||||
|
|
||||||
int radius = (kernel_size <= 0) ? cvRound(sigma_spatial*1.5) : kernel_size/2;
|
|
||||||
kernel_size = std::max(radius, 1)*2 + 1;
|
|
||||||
|
|
||||||
CV_Assert(src.depth() <= CV_32F && src.channels() <= 4);
|
|
||||||
const func_t func = funcs[src.depth()][src.channels() - 1];
|
|
||||||
CV_Assert(func != 0);
|
|
||||||
|
|
||||||
CV_Assert(borderMode == BORDER_REFLECT101 || borderMode == BORDER_REPLICATE || borderMode == BORDER_CONSTANT || borderMode == BORDER_REFLECT || borderMode == BORDER_WRAP);
|
|
||||||
|
|
||||||
int gpuBorderType;
|
|
||||||
CV_Assert(tryConvertToGpuBorderType(borderMode, gpuBorderType));
|
|
||||||
|
|
||||||
dst.create(src.size(), src.type());
|
|
||||||
func(src, dst, kernel_size, sigma_spatial, sigma_color, gpuBorderType, StreamAccessor::getStream(s));
|
|
||||||
}
|
|
||||||
|
|
||||||
void cv::gpu::nonLocalMeans(const GpuMat& src, GpuMat& dst, float h, int search_window, int block_window, int borderMode, Stream& s)
|
void cv::gpu::nonLocalMeans(const GpuMat& src, GpuMat& dst, float h, int search_window, int block_window, int borderMode, Stream& s)
|
||||||
{
|
{
|
||||||
using cv::gpu::cudev::imgproc::nlm_bruteforce_gpu;
|
using cv::gpu::cudev::imgproc::nlm_bruteforce_gpu;
|
||||||
@ -129,11 +92,6 @@ void cv::gpu::nonLocalMeans(const GpuMat& src, GpuMat& dst, float h, int search_
|
|||||||
func(src, dst, search_window/2, block_window/2, h, gpuBorderType, StreamAccessor::getStream(s));
|
func(src, dst, search_window/2, block_window/2, h, gpuBorderType, StreamAccessor::getStream(s));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////////
|
|
||||||
//// Non Local Means Denosing (fast approxinate)
|
|
||||||
|
|
||||||
|
|
||||||
namespace cv { namespace gpu { namespace cudev
|
namespace cv { namespace gpu { namespace cudev
|
||||||
{
|
{
|
||||||
namespace imgproc
|
namespace imgproc
|
@ -42,26 +42,17 @@
|
|||||||
|
|
||||||
#include "test_precomp.hpp"
|
#include "test_precomp.hpp"
|
||||||
|
|
||||||
|
#include "opencv2/photo/gpu.hpp"
|
||||||
|
#include "opencv2/ts/gpu_test.hpp"
|
||||||
|
|
||||||
#ifdef HAVE_CUDA
|
#ifdef HAVE_CUDA
|
||||||
|
|
||||||
using namespace cvtest;
|
using namespace cvtest;
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////
|
||||||
// Brute Force Non local means
|
// Brute Force Non local means
|
||||||
|
|
||||||
struct BruteForceNonLocalMeans: testing::TestWithParam<cv::gpu::DeviceInfo>
|
TEST(BruteForceNonLocalMeans, Regression)
|
||||||
{
|
|
||||||
cv::gpu::DeviceInfo devInfo;
|
|
||||||
|
|
||||||
virtual void SetUp()
|
|
||||||
{
|
|
||||||
devInfo = GetParam();
|
|
||||||
cv::gpu::setDevice(devInfo.deviceID());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
GPU_TEST_P(BruteForceNonLocalMeans, Regression)
|
|
||||||
{
|
{
|
||||||
using cv::gpu::GpuMat;
|
using cv::gpu::GpuMat;
|
||||||
|
|
||||||
@ -88,23 +79,10 @@ GPU_TEST_P(BruteForceNonLocalMeans, Regression)
|
|||||||
EXPECT_MAT_NEAR(gray_gold, dgray, 1e-4);
|
EXPECT_MAT_NEAR(gray_gold, dgray, 1e-4);
|
||||||
}
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(GPU_Denoising, BruteForceNonLocalMeans, ALL_DEVICES);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////
|
||||||
// Fast Force Non local means
|
// Fast Force Non local means
|
||||||
|
|
||||||
struct FastNonLocalMeans: testing::TestWithParam<cv::gpu::DeviceInfo>
|
TEST(FastNonLocalMeans, Regression)
|
||||||
{
|
|
||||||
cv::gpu::DeviceInfo devInfo;
|
|
||||||
|
|
||||||
virtual void SetUp()
|
|
||||||
{
|
|
||||||
devInfo = GetParam();
|
|
||||||
cv::gpu::setDevice(devInfo.deviceID());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
GPU_TEST_P(FastNonLocalMeans, Regression)
|
|
||||||
{
|
{
|
||||||
using cv::gpu::GpuMat;
|
using cv::gpu::GpuMat;
|
||||||
|
|
||||||
@ -133,6 +111,4 @@ GPU_TEST_P(FastNonLocalMeans, Regression)
|
|||||||
EXPECT_MAT_NEAR(gray_gold, dgray, 1);
|
EXPECT_MAT_NEAR(gray_gold, dgray, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
INSTANTIATE_TEST_CASE_P(GPU_Denoising, FastNonLocalMeans, ALL_DEVICES);
|
|
||||||
|
|
||||||
#endif // HAVE_CUDA
|
#endif // HAVE_CUDA
|
Loading…
Reference in New Issue
Block a user