From ee21f7fb36205cfc893005142a1d208e247f81cf Mon Sep 17 00:00:00 2001 From: Cristy Date: Sat, 27 Feb 2016 15:56:49 -0500 Subject: [PATCH] Support 'threshold x softness' parameter for wavelet denoise --- MagickCore/fx.c | 20 ++++++-------------- MagickWand/mogrify.c | 4 ++++ MagickWand/operation.c | 4 ++++ PerlMagick/Magick.xs | 10 ++++++++-- PerlMagick/quantum/quantum.xs.in | 10 ++++++++-- 5 files changed, 30 insertions(+), 18 deletions(-) diff --git a/MagickCore/fx.c b/MagickCore/fx.c index f477e24c7..a87c1de8e 100644 --- a/MagickCore/fx.c +++ b/MagickCore/fx.c @@ -5814,6 +5814,10 @@ MagickExport Image *WaveletDenoiseImage(const Image *image, size_t channel; + static const double + noise_levels[]= { + 0.8002, 0.2735, 0.1202, 0.0585, 0.0291, 0.0152, 0.0080, 0.0044 }; + /* Initialize noise image attributes. */ @@ -5970,7 +5974,6 @@ MagickExport Image *WaveletDenoiseImage(const Image *image, double sample_squared; - wavelet_pixels[high_pass+i]-=wavelet_pixels[low_pass+i]; if ((wavelet_pixels[high_pass+i] > magnitude) && (wavelet_pixels[high_pass+i] < -magnitude)) continue; @@ -6010,21 +6013,10 @@ MagickExport Image *WaveletDenoiseImage(const Image *image, To threshold, each coefficient is compared to a threshold value and attenuated / shrunk by some factor. */ + magnitude=threshold*noise_levels[level]; for (i=0; i < (ssize_t) number_pixels; ++i) { - if (wavelet_pixels[low_pass+i] > 0.8) - magnitude=threshold*standard_deviation[4]; - else - if (wavelet_pixels[low_pass+i] > 0.6) - magnitude=threshold*standard_deviation[3]; - else - if (wavelet_pixels[low_pass+i] > 0.4) - magnitude=threshold*standard_deviation[2]; - else - if (wavelet_pixels[low_pass+i] > 0.2) - magnitude=threshold*standard_deviation[1]; - else - magnitude=threshold*standard_deviation[0]; + wavelet_pixels[high_pass+i]-=wavelet_pixels[low_pass+i]; if (wavelet_pixels[high_pass+i] < -magnitude) wavelet_pixels[high_pass+i]+=magnitude-softness*magnitude; else diff --git a/MagickWand/mogrify.c b/MagickWand/mogrify.c index 91a8f24b7..f31146bfc 100644 --- a/MagickWand/mogrify.c +++ b/MagickWand/mogrify.c @@ -3298,6 +3298,10 @@ WandExport MagickBooleanType MogrifyImage(ImageInfo *image_info,const int argc, */ (void) SyncImageSettings(mogrify_info,*image,exception); flags=ParseGeometry(argv[i+1],&geometry_info); + if ((flags & PercentValue) != 0) + geometry_info.rho=(double) QuantumRange*geometry_info.rho/100.0; + if ((flags & SigmaValue) == 0) + geometry_info.sigma=0.0; mogrify_image=WaveletDenoiseImage(*image,geometry_info.rho, geometry_info.sigma,exception); break; diff --git a/MagickWand/operation.c b/MagickWand/operation.c index cb01736ca..ce3b8fff4 100644 --- a/MagickWand/operation.c +++ b/MagickWand/operation.c @@ -3544,6 +3544,10 @@ static MagickBooleanType CLISimpleOperatorImage(MagickCLI *cli_wand, flags=ParseGeometry(arg1,&geometry_info); if ((flags & RhoValue) == 0) CLIWandExceptArgBreak(OptionError,"InvalidArgument",option,arg1); + if ((flags & PercentValue) != 0) + geometry_info.rho=(double) QuantumRange*geometry_info.rho/100.0; + if ((flags & SigmaValue) == 0) + geometry_info.sigma=0.0; new_image=WaveletDenoiseImage(_image,geometry_info.rho, geometry_info.sigma,_exception); break; diff --git a/PerlMagick/Magick.xs b/PerlMagick/Magick.xs index 13f34534e..0b56ee619 100644 --- a/PerlMagick/Magick.xs +++ b/PerlMagick/Magick.xs @@ -11329,8 +11329,14 @@ Mogrify(ref,...) case 145: /* WaveletDenoise */ { if (attribute_flag[0] != 0) - flags=ParseGeometry(argument_list[0].string_reference, - &geometry_info); + { + flags=ParseGeometry(argument_list[0].string_reference, + &geometry_info); + if ((flags & PercentValue) != 0) + geometry_info.rho=QuantumRange*geometry_info.rho/100.0; + if ((flags & SigmaValue) == 0) + geometry_info.sigma=0.0; + } if (attribute_flag[1] != 0) geometry_info.rho=argument_list[1].real_reference; if (attribute_flag[2] != 0) diff --git a/PerlMagick/quantum/quantum.xs.in b/PerlMagick/quantum/quantum.xs.in index 8e02c98e5..1dceac6a7 100644 --- a/PerlMagick/quantum/quantum.xs.in +++ b/PerlMagick/quantum/quantum.xs.in @@ -11329,8 +11329,14 @@ Mogrify(ref,...) case 145: /* WaveletDenoise */ { if (attribute_flag[0] != 0) - flags=ParseGeometry(argument_list[0].string_reference, - &geometry_info); + { + flags=ParseGeometry(argument_list[0].string_reference, + &geometry_info); + if ((flags & PercentValue) != 0) + geometry_info.rho=QuantumRange*geometry_info.rho/100.0; + if ((flags & SigmaValue) == 0) + geometry_info.sigma=0.0; + } if (attribute_flag[1] != 0) geometry_info.rho=argument_list[1].real_reference; if (attribute_flag[2] != 0) -- 2.49.0