From d5c60475e577c725cbd31b777334fc3d35e3a91e Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Fri, 17 Jan 2020 14:16:54 +0100 Subject: [PATCH 1/5] review mlsharpen --- rtengine/CMakeLists.txt | 1 + rtengine/ipsharpen.cc | 237 +------------------------------------ rtengine/ipsharpenedges.cc | 223 ++++++++++++++++++++++++++++++++++ 3 files changed, 225 insertions(+), 236 deletions(-) create mode 100644 rtengine/ipsharpenedges.cc diff --git a/rtengine/CMakeLists.txt b/rtengine/CMakeLists.txt index 6bce68d1a..baca55c0a 100644 --- a/rtengine/CMakeLists.txt +++ b/rtengine/CMakeLists.txt @@ -94,6 +94,7 @@ set(RTENGINESOURCEFILES ipretinex.cc ipshadowshighlights.cc ipsharpen.cc + ipsharpenedges.cc ipsoftlight.cc iptransform.cc ipvibrance.cc diff --git a/rtengine/ipsharpen.cc b/rtengine/ipsharpen.cc index 7198b76c5..78892a024 100644 --- a/rtengine/ipsharpen.cc +++ b/rtengine/ipsharpen.cc @@ -30,7 +30,7 @@ #include "settings.h" #include "sleef.h" -//#define BENCHMARK +#define BENCHMARK #include "StopWatch.h" using namespace std; @@ -385,241 +385,6 @@ BENCHFUN } -// To the extent possible under law, Manuel Llorens -// has waived all copyright and related or neighboring rights to this work. -// This work is published from: Spain. - -// Thanks to Manuel for this excellent job (Jacques Desmis JDC or frej83) -void ImProcFunctions::MLsharpen (LabImage* lab) -{ - // JD: this algorithm maximize clarity of images; it does not play on accutance. It can remove (partially) the effects of the AA filter) - // I think we can use this algorithm alone in most cases, or first to clarify image and if you want a very little USM (unsharp mask sharpening) after... - if (!params->sharpenEdge.enabled) { - return; - } - - MyTime t1e, t2e; - t1e.set(); - - int offset, c, i, j, p, width2; - int width = lab->W, height = lab->H; - float *L, lumH, lumV, lumD1, lumD2, v, contrast, s; - float difL, difR, difT, difB, difLT, difRB, difLB, difRT, wH, wV, wD1, wD2, chmax[3]; - float f1, f2, f3, f4; - float templab; - int iii, kkk; - width2 = 2 * width; - const float epsil = 0.01f; //prevent divide by zero - const float eps2 = 0.001f; //prevent divide by zero - float amount; - amount = params->sharpenEdge.amount / 100.0f; - - if (amount < 0.00001f) { - return; - } - - if (settings->verbose) { - printf ("SharpenEdge amount %f\n", amount); - } - - L = new float[width * height]; - - chmax[0] = 8.0f; - chmax[1] = 3.0f; - chmax[2] = 3.0f; - - int channels; - - if (params->sharpenEdge.threechannels) { - channels = 0; - } else { - channels = 2; - } - - if (settings->verbose) { - printf ("SharpenEdge channels %d\n", channels); - } - - int passes = params->sharpenEdge.passes; - - if (settings->verbose) { - printf ("SharpenEdge passes %d\n", passes); - } - - for (p = 0; p < passes; p++) - for (c = 0; c <= channels; c++) { // c=0 Luminance only - -#ifdef _OPENMP - #pragma omp parallel for private(offset) shared(L) -#endif - - for (offset = 0; offset < width * height; offset++) { - int ii = offset / width; - int kk = offset - ii * width; - - if (c == 0) { - L[offset] = lab->L[ii][kk] / 327.68f; // adjust to RT and to 0..100 - } else if (c == 1) { - L[offset] = lab->a[ii][kk] / 327.68f; - } else { /*if (c==2) */ - L[offset] = lab->b[ii][kk] / 327.68f; - } - } - -#ifdef _OPENMP - #pragma omp parallel for private(j,i,iii,kkk, templab,offset,wH,wV,wD1,wD2,s,lumH,lumV,lumD1,lumD2,v,contrast,f1,f2,f3,f4,difT,difB,difL,difR,difLT,difLB,difRT,difRB) shared(lab,L,amount) -#endif - - for(j = 2; j < height - 2; j++) - for(i = 2, offset = j * width + i; i < width - 2; i++, offset++) { - // weight functions - wH = eps2 + fabs(L[offset + 1] - L[offset - 1]); - wV = eps2 + fabs(L[offset + width] - L[offset - width]); - - s = 1.0f + fabs(wH - wV) / 2.0f; - wD1 = eps2 + fabs(L[offset + width + 1] - L[offset - width - 1]) / s; - wD2 = eps2 + fabs(L[offset + width - 1] - L[offset - width + 1]) / s; - s = wD1; - wD1 /= wD2; - wD2 /= s; - - // initial values - int ii = offset / width; - int kk = offset - ii * width; - - if (c == 0) { - lumH = lumV = lumD1 = lumD2 = v = lab->L[ii][kk] / 327.68f; - } else if (c == 1) { - lumH = lumV = lumD1 = lumD2 = v = lab->a[ii][kk] / 327.68f; - } else { /* if (c==2) */ - lumH = lumV = lumD1 = lumD2 = v = lab->b[ii][kk] / 327.68f; - } - - - // contrast detection - contrast = sqrt(fabs(L[offset + 1] - L[offset - 1]) * fabs(L[offset + 1] - L[offset - 1]) + fabs(L[offset + width] - L[offset - width]) * fabs(L[offset + width] - L[offset - width])) / chmax[c]; - - if (contrast > 1.0f) { - contrast = 1.0f; - } - - // new possible values - if (((L[offset] < L[offset - 1]) && (L[offset] > L[offset + 1])) || ((L[offset] > L[offset - 1]) && (L[offset] < L[offset + 1]))) { - f1 = fabs(L[offset - 2] - L[offset - 1]); - f2 = fabs(L[offset - 1] - L[offset]); - f3 = fabs(L[offset - 1] - L[offset - width]) * fabs(L[offset - 1] - L[offset + width]); - f4 = sqrt(fabs(L[offset - 1] - L[offset - width2]) * fabs(L[offset - 1] - L[offset + width2])); - difL = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + 2] - L[offset + 1]); - f2 = fabs(L[offset + 1] - L[offset]); - f3 = fabs(L[offset + 1] - L[offset - width]) * fabs(L[offset + 1] - L[offset + width]); - f4 = sqrt(fabs(L[offset + 1] - L[offset - width2]) * fabs(L[offset + 1] - L[offset + width2])); - difR = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difR > epsil) && (difL > epsil)) { - lumH = (L[offset - 1] * difR + L[offset + 1] * difL) / (difL + difR); - lumH = v * (1.f - contrast) + lumH * contrast; - } - } - - if (((L[offset] < L[offset - width]) && (L[offset] > L[offset + width])) || ((L[offset] > L[offset - width]) && (L[offset] < L[offset + width]))) { - f1 = fabs(L[offset - width2] - L[offset - width]); - f2 = fabs(L[offset - width] - L[offset]); - f3 = fabs(L[offset - width] - L[offset - 1]) * fabs(L[offset - width] - L[offset + 1]); - f4 = sqrt(fabs(L[offset - width] - L[offset - 2]) * fabs(L[offset - width] - L[offset + 2])); - difT = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + width2] - L[offset + width]); - f2 = fabs(L[offset + width] - L[offset]); - f3 = fabs(L[offset + width] - L[offset - 1]) * fabs(L[offset + width] - L[offset + 1]); - f4 = sqrt(fabs(L[offset + width] - L[offset - 2]) * fabs(L[offset + width] - L[offset + 2])); - difB = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difB > epsil) && (difT > epsil)) { - lumV = (L[offset - width] * difB + L[offset + width] * difT) / (difT + difB); - lumV = v * (1.f - contrast) + lumV * contrast; - } - } - - if (((L[offset] < L[offset - 1 - width]) && (L[offset] > L[offset + 1 + width])) || ((L[offset] > L[offset - 1 - width]) && (L[offset] < L[offset + 1 + width]))) { - f1 = fabs(L[offset - 2 - width2] - L[offset - 1 - width]); - f2 = fabs(L[offset - 1 - width] - L[offset]); - f3 = fabs(L[offset - 1 - width] - L[offset - width + 1]) * fabs(L[offset - 1 - width] - L[offset + width - 1]); - f4 = sqrt(fabs(L[offset - 1 - width] - L[offset - width2 + 2]) * fabs(L[offset - 1 - width] - L[offset + width2 - 2])); - difLT = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + 2 + width2] - L[offset + 1 + width]); - f2 = fabs(L[offset + 1 + width] - L[offset]); - f3 = fabs(L[offset + 1 + width] - L[offset - width + 1]) * fabs(L[offset + 1 + width] - L[offset + width - 1]); - f4 = sqrt(fabs(L[offset + 1 + width] - L[offset - width2 + 2]) * fabs(L[offset + 1 + width] - L[offset + width2 - 2])); - difRB = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difLT > epsil) && (difRB > epsil)) { - lumD1 = (L[offset - 1 - width] * difRB + L[offset + 1 + width] * difLT) / (difLT + difRB); - lumD1 = v * (1.f - contrast) + lumD1 * contrast; - } - } - - if (((L[offset] < L[offset + 1 - width]) && (L[offset] > L[offset - 1 + width])) || ((L[offset] > L[offset + 1 - width]) && (L[offset] < L[offset - 1 + width]))) { - f1 = fabs(L[offset - 2 + width2] - L[offset - 1 + width]); - f2 = fabs(L[offset - 1 + width] - L[offset]); - f3 = fabs(L[offset - 1 + width] - L[offset - width - 1]) * fabs(L[offset - 1 + width] - L[offset + width + 1]); - f4 = sqrt(fabs(L[offset - 1 + width] - L[offset - width2 - 2]) * fabs(L[offset - 1 + width] - L[offset + width2 + 2])); - difLB = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + 2 - width2] - L[offset + 1 - width]); - f2 = fabs(L[offset + 1 - width] - L[offset]) * fabs(L[offset + 1 - width] - L[offset]); - f3 = fabs(L[offset + 1 - width] - L[offset + width + 1]) * fabs(L[offset + 1 - width] - L[offset - width - 1]); - f4 = sqrt(fabs(L[offset + 1 - width] - L[offset + width2 + 2]) * fabs(L[offset + 1 - width] - L[offset - width2 - 2])); - difRT = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difLB > epsil) && (difRT > epsil)) { - lumD2 = (L[offset + 1 - width] * difLB + L[offset - 1 + width] * difRT) / (difLB + difRT); - lumD2 = v * (1.f - contrast) + lumD2 * contrast; - } - } - - s = amount; - - // avoid sharpening diagonals too much - if (((fabs(wH / wV) < 0.45f) && (fabs(wH / wV) > 0.05f)) || ((fabs(wV / wH) < 0.45f) && (fabs(wV / wH) > 0.05f))) { - s = amount / 3.0f; - } - - // final mix - if ((wH != 0.0f) && (wV != 0.0f) && (wD1 != 0.0f) && (wD2 != 0.0f)) { - iii = offset / width; - kkk = offset - iii * width; - float provL = lab->L[iii][kkk] / 327.68f; - - if(c == 0) { - if(provL < 92.f) { - templab = v * (1.f - s) + (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2) * s; - } else { - templab = provL; - } - } else { - templab = v * (1.f - s) + (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2) * s; - } - - if (c == 0) { - lab->L[iii][kkk] = fabs(327.68f * templab); // fabs because lab->L always >0 - } else if (c == 1) { - lab->a[iii][kkk] = 327.68f * templab ; - } else if (c == 2) { - lab->b[iii][kkk] = 327.68f * templab ; - } - } - - } - } - - delete [] L; - - t2e.set(); - - if (settings->verbose) { - printf("SharpenEdge gradient %d usec\n", t2e.etime(t1e)); - } -} - // To the extent possible under law, Manuel Llorens // has waived all copyright and related or neighboring rights to this work. // This code is licensed under CC0 v1.0, see license information at diff --git a/rtengine/ipsharpenedges.cc b/rtengine/ipsharpenedges.cc new file mode 100644 index 000000000..4d310abb2 --- /dev/null +++ b/rtengine/ipsharpenedges.cc @@ -0,0 +1,223 @@ +/* + * This file is part of RawTherapee. + * + * Copyright (c) 2004-2020 Gabor Horvath + * + * RawTherapee is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * RawTherapee is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with RawTherapee. If not, see . +*/ + +#include +#include "improcfun.h" +#include "labimage.h" +#include "procparams.h" +#include "rt_math.h" + +#define BENCHMARK +#include "StopWatch.h" + +using namespace std; +namespace { +#ifdef __SSE2__ +bool inintervall(float a, float b, float c) +{ + return a < std::max(b, c) && a > std::min(b, c); +} + +float selectweight(float a, float b, float low, float high) +{ + const float minVal = std::min(a,b); + const float maxVal = std::max(a,b); + const float res = (minVal < 0.45f * maxVal) ? low : high; + return (minVal > 0.05f * maxVal) ? res : high; +} + +#else +bool inintervall(float a, float b, float c) +{ + return (a < b && a > c) || (a < c && a > b); +} + +float selectweight(float a, float b, float low, float high) +{ + if ((a < 0.45f * b && a > 0.05f * b) || (b < 0.45f * a && b > 0.05f * a)) { + return low; + } else { + return high; + } +} + +#endif +} +namespace rtengine +{ + +// To the extent possible under law, Manuel Llorens +// has waived all copyright and related or neighboring rights to this work. +// This work is published from: Spain. + +// Thanks to Manuel for this excellent job (Jacques Desmis JDC or frej83) +void ImProcFunctions::MLsharpen (LabImage* lab) +{ + // JD: this algorithm maximize clarity of images; it does not play on accutance. It can remove (partially) the effects of the AA filter) + // I think we can use this algorithm alone in most cases, or first to clarify image and if you want a very little USM (unsharp mask sharpening) after... + if (!params->sharpenEdge.enabled || params->sharpenEdge.amount == 0) { + return; + } + +BENCHFUN + + const int width = lab->W, height = lab->H; + constexpr float chmax[3] = {1.f / 8.f, 1.f / 3.f, 1.f / 3.f}; + const int width2 = 2 * width; + constexpr float eps2 = 0.001f; //prevent divide by zero + const float amount = params->sharpenEdge.amount / 100.0f; + const float amountby3 = params->sharpenEdge.amount / 300.0f; + + std::unique_ptr L(new float[width * height]); + + const int channels = params->sharpenEdge.threechannels ? 1 : 3; + const int passes = params->sharpenEdge.passes; + + for (int c = 0; c < channels; ++c) { // c=0 Luminance only + float** channel = c == 0 ? lab->L : c == 1 ? lab->a : lab->b; + for (int p = 0; p < passes; ++p) { +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int i = 0; i < height; ++i) { + for (int j = 0; j < width; ++j) { + L[i * width + j] = channel[i][j] / 327.68f; + } + } + +#ifdef _OPENMP + #pragma omp parallel for schedule(dynamic,16) +#endif + + for (int j = 2; j < height - 2; j++) { + for (int i = 2, offset = j * width + i; i < width - 2; i++, offset++) { + // weight functions + const float wH = eps2 + fabs(L[offset + 1] - L[offset - 1]); + const float wV = eps2 + fabs(L[offset + width] - L[offset - width]); + + float s = 2.f / (2.f + fabs(wH - wV)); + float wD1 = eps2 + fabs(L[offset + width + 1] - L[offset - width - 1]) * s; + float wD2 = eps2 + fabs(L[offset + width - 1] - L[offset - width + 1]) * s; + s = wD1; + wD1 /= wD2; + wD2 /= s; + + const float v = L[offset]; + float lumH, lumV, lumD1, lumD2; + lumH = lumV = lumD1 = lumD2 = v; + + // contrast detection + const float contrast = std::min(std::sqrt(SQR(L[offset + 1] - L[offset - 1]) + SQR(L[offset + width] - L[offset - width])) * chmax[c], 1.f); + + // new possible values + if (inintervall(L[offset], L[offset - 1], L[offset + 1])) { + float f1 = fabs(L[offset - 2] - L[offset - 1]); + float f2 = L[offset - 1] - L[offset]; + float f3 = (L[offset - 1] - L[offset - width]) * (L[offset - 1] - L[offset + width]); + float f4 = std::sqrt(fabs(L[offset - 1] - L[offset - width2]) * fabs(L[offset - 1] - L[offset + width2])); + const float difL = f1 * SQR(f2) * SQR(f3) * f4; + if (difL > 0.f) { + f1 = fabs(L[offset + 2] - L[offset + 1]); + f2 = L[offset + 1] - L[offset]; + f3 = (L[offset + 1] - L[offset - width]) * (L[offset + 1] - L[offset + width]); + f4 = std::sqrt(fabs(L[offset + 1] - L[offset - width2]) * fabs(L[offset + 1] - L[offset + width2])); + const float difR = f1 * SQR(f2) * SQR(f3) * f4; + if (difR > 0.f) { + lumH = (L[offset - 1] * difR + L[offset + 1] * difL) / (difL + difR); + lumH = intp(contrast, lumH, v); + } + } + } + + if (inintervall(L[offset], L[offset - width], L[offset + width])) { + float f1 = fabs(L[offset - width2] - L[offset - width]); + float f2 = L[offset - width] - L[offset]; + float f3 = (L[offset - width] - L[offset - 1]) * (L[offset - width] - L[offset + 1]); + float f4 = std::sqrt(fabs(L[offset - width] - L[offset - 2]) * fabs(L[offset - width] - L[offset + 2])); + const float difT = f1 * SQR(f2) * SQR(f3) * f4; + if (difT > 0.f) { + f1 = fabs(L[offset + width2] - L[offset + width]); + f2 = L[offset + width] - L[offset]; + f3 = (L[offset + width] - L[offset - 1]) * (L[offset + width] - L[offset + 1]); + f4 = std::sqrt(fabs(L[offset + width] - L[offset - 2]) * fabs(L[offset + width] - L[offset + 2])); + const float difB = f1 * SQR(f2) * SQR(f3) * f4; + if (difB > 0.f) { + lumV = (L[offset - width] * difB + L[offset + width] * difT) / (difT + difB); + lumV = intp(contrast, lumV, v); + } + } + } + + if (inintervall(L[offset], L[offset - 1 - width], L[offset + 1 + width])) { + float f1 = fabs(L[offset - 2 - width2] - L[offset - 1 - width]); + float f2 = L[offset - 1 - width] - L[offset]; + float f3 = (L[offset - 1 - width] - L[offset - width + 1]) * (L[offset - 1 - width] - L[offset + width - 1]); + float f4 = std::sqrt(fabs(L[offset - 1 - width] - L[offset - width2 + 2]) * fabs(L[offset - 1 - width] - L[offset + width2 - 2])); + const float difLT = f1 * SQR(f2) * SQR(f3) * f4; + if (difLT > 0.f) { + f1 = fabs(L[offset + 2 + width2] - L[offset + 1 + width]); + f2 = L[offset + 1 + width] - L[offset]; + f3 = (L[offset + 1 + width] - L[offset - width + 1]) * (L[offset + 1 + width] - L[offset + width - 1]); + f4 = std::sqrt(fabs(L[offset + 1 + width] - L[offset - width2 + 2]) * fabs(L[offset + 1 + width] - L[offset + width2 - 2])); + const float difRB = f1 * SQR(f2) * SQR(f3) * f4; + if (difRB > 0.f) { + lumD1 = (L[offset - 1 - width] * difRB + L[offset + 1 + width] * difLT) / (difLT + difRB); + lumD1 = intp(contrast, lumD1, v); + } + } + } + + if (inintervall(L[offset], L[offset + 1 - width], L[offset] > L[offset - 1 + width])) { + float f1 = fabs(L[offset - 2 + width2] - L[offset - 1 + width]); + float f2 = L[offset - 1 + width] - L[offset]; + float f3 = (L[offset - 1 + width] - L[offset - width - 1]) * (L[offset - 1 + width] - L[offset + width + 1]); + float f4 = std::sqrt(fabs(L[offset - 1 + width] - L[offset - width2 - 2]) * fabs(L[offset - 1 + width] - L[offset + width2 + 2])); + const float difLB = f1 * SQR(f2) * SQR(f3) * f4; + if (difLB > 0.f) { + f1 = fabs(L[offset + 2 - width2] - L[offset + 1 - width]); + f2 = L[offset + 1 - width] - L[offset]; + f3 = (L[offset + 1 - width] - L[offset + width + 1]) * (L[offset + 1 - width] - L[offset - width - 1]); + f4 = std::sqrt(fabs(L[offset + 1 - width] - L[offset + width2 + 2]) * fabs(L[offset + 1 - width] - L[offset - width2 - 2])); + const float difRT = f1 * SQR(f2) * SQR(f3) * f4; + if (difRT > 0.f) { + lumD2 = (L[offset + 1 - width] * difLB + L[offset - 1 + width] * difRT) / (difLB + difRT); + lumD2 = intp(contrast, lumD2, v); + } + } + } + + // final mix + // avoid sharpening diagonals too much + const float weight = selectweight(wH, wV, amountby3, amount); + + if (c == 0) { + if (v < 92.f) { + channel[j][i] = fabs(327.68f * intp(weight, (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2), v)); // fabs because lab->L always > 0 + } + } else { + channel[j][i] = 327.68f * intp(weight, (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2), v); + } + } + } + } + } +} + +} \ No newline at end of file From c304d3270214cccc1c445b8a1aaeef1e58c7377d Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Fri, 17 Jan 2020 14:23:06 +0100 Subject: [PATCH 2/5] mlsharpen review: minor changes --- rtengine/ipsharpen.cc | 2 +- rtengine/ipsharpenedges.cc | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/rtengine/ipsharpen.cc b/rtengine/ipsharpen.cc index 78892a024..959030dc6 100644 --- a/rtengine/ipsharpen.cc +++ b/rtengine/ipsharpen.cc @@ -30,7 +30,7 @@ #include "settings.h" #include "sleef.h" -#define BENCHMARK +//#define BENCHMARK #include "StopWatch.h" using namespace std; diff --git a/rtengine/ipsharpenedges.cc b/rtengine/ipsharpenedges.cc index 4d310abb2..c42472598 100644 --- a/rtengine/ipsharpenedges.cc +++ b/rtengine/ipsharpenedges.cc @@ -220,4 +220,4 @@ BENCHFUN } } -} \ No newline at end of file +} From 507af11adf521a05cac111625282b906a1bc1e0f Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Fri, 17 Jan 2020 16:25:20 +0100 Subject: [PATCH 3/5] mlsharpen: bugfix and speedup --- rtengine/ipsharpenedges.cc | 56 +++++++++++++++++++------------------- 1 file changed, 28 insertions(+), 28 deletions(-) diff --git a/rtengine/ipsharpenedges.cc b/rtengine/ipsharpenedges.cc index c42472598..73295e4fa 100644 --- a/rtengine/ipsharpenedges.cc +++ b/rtengine/ipsharpenedges.cc @@ -127,18 +127,18 @@ BENCHFUN const float contrast = std::min(std::sqrt(SQR(L[offset + 1] - L[offset - 1]) + SQR(L[offset + width] - L[offset - width])) * chmax[c], 1.f); // new possible values - if (inintervall(L[offset], L[offset - 1], L[offset + 1])) { + if (inintervall(v, L[offset - 1], L[offset + 1])) { float f1 = fabs(L[offset - 2] - L[offset - 1]); - float f2 = L[offset - 1] - L[offset]; + float f2 = L[offset - 1] - v; float f3 = (L[offset - 1] - L[offset - width]) * (L[offset - 1] - L[offset + width]); - float f4 = std::sqrt(fabs(L[offset - 1] - L[offset - width2]) * fabs(L[offset - 1] - L[offset + width2])); - const float difL = f1 * SQR(f2) * SQR(f3) * f4; + float f4 = std::sqrt(fabs((L[offset - 1] - L[offset - width2]) * (L[offset - 1] - L[offset + width2]))); + const float difL = f1 * SQR(f2 * f3) * f4; if (difL > 0.f) { f1 = fabs(L[offset + 2] - L[offset + 1]); - f2 = L[offset + 1] - L[offset]; + f2 = L[offset + 1] - v; f3 = (L[offset + 1] - L[offset - width]) * (L[offset + 1] - L[offset + width]); - f4 = std::sqrt(fabs(L[offset + 1] - L[offset - width2]) * fabs(L[offset + 1] - L[offset + width2])); - const float difR = f1 * SQR(f2) * SQR(f3) * f4; + f4 = std::sqrt(fabs((L[offset + 1] - L[offset - width2]) * (L[offset + 1] - L[offset + width2]))); + const float difR = f1 * SQR(f2 * f3) * f4; if (difR > 0.f) { lumH = (L[offset - 1] * difR + L[offset + 1] * difL) / (difL + difR); lumH = intp(contrast, lumH, v); @@ -146,18 +146,18 @@ BENCHFUN } } - if (inintervall(L[offset], L[offset - width], L[offset + width])) { + if (inintervall(v, L[offset - width], L[offset + width])) { float f1 = fabs(L[offset - width2] - L[offset - width]); - float f2 = L[offset - width] - L[offset]; + float f2 = L[offset - width] - v; float f3 = (L[offset - width] - L[offset - 1]) * (L[offset - width] - L[offset + 1]); - float f4 = std::sqrt(fabs(L[offset - width] - L[offset - 2]) * fabs(L[offset - width] - L[offset + 2])); - const float difT = f1 * SQR(f2) * SQR(f3) * f4; + float f4 = std::sqrt(fabs((L[offset - width] - L[offset - 2]) * (L[offset - width] - L[offset + 2]))); + const float difT = f1 * SQR(f2 * f3) * f4; if (difT > 0.f) { f1 = fabs(L[offset + width2] - L[offset + width]); - f2 = L[offset + width] - L[offset]; + f2 = L[offset + width] - v; f3 = (L[offset + width] - L[offset - 1]) * (L[offset + width] - L[offset + 1]); - f4 = std::sqrt(fabs(L[offset + width] - L[offset - 2]) * fabs(L[offset + width] - L[offset + 2])); - const float difB = f1 * SQR(f2) * SQR(f3) * f4; + f4 = std::sqrt(fabs((L[offset + width] - L[offset - 2]) * (L[offset + width] - L[offset + 2]))); + const float difB = f1 * SQR(f2 * f3) * f4; if (difB > 0.f) { lumV = (L[offset - width] * difB + L[offset + width] * difT) / (difT + difB); lumV = intp(contrast, lumV, v); @@ -165,18 +165,18 @@ BENCHFUN } } - if (inintervall(L[offset], L[offset - 1 - width], L[offset + 1 + width])) { + if (inintervall(v, L[offset - 1 - width], L[offset + 1 + width])) { float f1 = fabs(L[offset - 2 - width2] - L[offset - 1 - width]); - float f2 = L[offset - 1 - width] - L[offset]; + float f2 = L[offset - 1 - width] - v; float f3 = (L[offset - 1 - width] - L[offset - width + 1]) * (L[offset - 1 - width] - L[offset + width - 1]); - float f4 = std::sqrt(fabs(L[offset - 1 - width] - L[offset - width2 + 2]) * fabs(L[offset - 1 - width] - L[offset + width2 - 2])); - const float difLT = f1 * SQR(f2) * SQR(f3) * f4; + float f4 = std::sqrt(fabs((L[offset - 1 - width] - L[offset - width2 + 2]) * (L[offset - 1 - width] - L[offset + width2 - 2]))); + const float difLT = f1 * SQR(f2 * f3) * f4; if (difLT > 0.f) { f1 = fabs(L[offset + 2 + width2] - L[offset + 1 + width]); - f2 = L[offset + 1 + width] - L[offset]; + f2 = L[offset + 1 + width] - v; f3 = (L[offset + 1 + width] - L[offset - width + 1]) * (L[offset + 1 + width] - L[offset + width - 1]); - f4 = std::sqrt(fabs(L[offset + 1 + width] - L[offset - width2 + 2]) * fabs(L[offset + 1 + width] - L[offset + width2 - 2])); - const float difRB = f1 * SQR(f2) * SQR(f3) * f4; + f4 = std::sqrt(fabs((L[offset + 1 + width] - L[offset - width2 + 2]) * (L[offset + 1 + width] - L[offset + width2 - 2]))); + const float difRB = f1 * SQR(f2 * f3) * f4; if (difRB > 0.f) { lumD1 = (L[offset - 1 - width] * difRB + L[offset + 1 + width] * difLT) / (difLT + difRB); lumD1 = intp(contrast, lumD1, v); @@ -184,18 +184,18 @@ BENCHFUN } } - if (inintervall(L[offset], L[offset + 1 - width], L[offset] > L[offset - 1 + width])) { + if (inintervall(v, L[offset + 1 - width], L[offset - 1 + width])) { float f1 = fabs(L[offset - 2 + width2] - L[offset - 1 + width]); - float f2 = L[offset - 1 + width] - L[offset]; + float f2 = L[offset - 1 + width] - v; float f3 = (L[offset - 1 + width] - L[offset - width - 1]) * (L[offset - 1 + width] - L[offset + width + 1]); - float f4 = std::sqrt(fabs(L[offset - 1 + width] - L[offset - width2 - 2]) * fabs(L[offset - 1 + width] - L[offset + width2 + 2])); - const float difLB = f1 * SQR(f2) * SQR(f3) * f4; + float f4 = std::sqrt(fabs((L[offset - 1 + width] - L[offset - width2 - 2]) * (L[offset - 1 + width] - L[offset + width2 + 2]))); + const float difLB = f1 * SQR(f2 * f3) * f4; if (difLB > 0.f) { f1 = fabs(L[offset + 2 - width2] - L[offset + 1 - width]); - f2 = L[offset + 1 - width] - L[offset]; + f2 = L[offset + 1 - width] - v; f3 = (L[offset + 1 - width] - L[offset + width + 1]) * (L[offset + 1 - width] - L[offset - width - 1]); - f4 = std::sqrt(fabs(L[offset + 1 - width] - L[offset + width2 + 2]) * fabs(L[offset + 1 - width] - L[offset - width2 - 2])); - const float difRT = f1 * SQR(f2) * SQR(f3) * f4; + f4 = std::sqrt(fabs((L[offset + 1 - width] - L[offset + width2 + 2]) * (L[offset + 1 - width] - L[offset - width2 - 2]))); + const float difRT = f1 * SQR(f2 * f3) * f4; if (difRT > 0.f) { lumD2 = (L[offset + 1 - width] * difLB + L[offset - 1 + width] * difRT) / (difLB + difRT); lumD2 = intp(contrast, lumD2, v); From acdb3c32ddbcc7c78075a9e75e2e8803e88e0694 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Sun, 9 Feb 2020 12:02:57 +0100 Subject: [PATCH 4/5] MLsharpen: cleanup --- rtengine/ipsharpenedges.cc | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/rtengine/ipsharpenedges.cc b/rtengine/ipsharpenedges.cc index 73295e4fa..8dd12c836 100644 --- a/rtengine/ipsharpenedges.cc +++ b/rtengine/ipsharpenedges.cc @@ -23,13 +23,9 @@ #include "procparams.h" #include "rt_math.h" -#define BENCHMARK -#include "StopWatch.h" - -using namespace std; namespace { #ifdef __SSE2__ -bool inintervall(float a, float b, float c) +bool inintervalLoRo(float a, float b, float c) { return a < std::max(b, c) && a > std::min(b, c); } @@ -43,7 +39,7 @@ float selectweight(float a, float b, float low, float high) } #else -bool inintervall(float a, float b, float c) +bool inintervalLoRo(float a, float b, float c) { return (a < b && a > c) || (a < c && a > b); } @@ -75,8 +71,6 @@ void ImProcFunctions::MLsharpen (LabImage* lab) return; } -BENCHFUN - const int width = lab->W, height = lab->H; constexpr float chmax[3] = {1.f / 8.f, 1.f / 3.f, 1.f / 3.f}; const int width2 = 2 * width; @@ -127,7 +121,7 @@ BENCHFUN const float contrast = std::min(std::sqrt(SQR(L[offset + 1] - L[offset - 1]) + SQR(L[offset + width] - L[offset - width])) * chmax[c], 1.f); // new possible values - if (inintervall(v, L[offset - 1], L[offset + 1])) { + if (inintervalLoRo(v, L[offset - 1], L[offset + 1])) { float f1 = fabs(L[offset - 2] - L[offset - 1]); float f2 = L[offset - 1] - v; float f3 = (L[offset - 1] - L[offset - width]) * (L[offset - 1] - L[offset + width]); @@ -146,7 +140,7 @@ BENCHFUN } } - if (inintervall(v, L[offset - width], L[offset + width])) { + if (inintervalLoRo(v, L[offset - width], L[offset + width])) { float f1 = fabs(L[offset - width2] - L[offset - width]); float f2 = L[offset - width] - v; float f3 = (L[offset - width] - L[offset - 1]) * (L[offset - width] - L[offset + 1]); @@ -165,7 +159,7 @@ BENCHFUN } } - if (inintervall(v, L[offset - 1 - width], L[offset + 1 + width])) { + if (inintervalLoRo(v, L[offset - 1 - width], L[offset + 1 + width])) { float f1 = fabs(L[offset - 2 - width2] - L[offset - 1 - width]); float f2 = L[offset - 1 - width] - v; float f3 = (L[offset - 1 - width] - L[offset - width + 1]) * (L[offset - 1 - width] - L[offset + width - 1]); @@ -184,7 +178,7 @@ BENCHFUN } } - if (inintervall(v, L[offset + 1 - width], L[offset - 1 + width])) { + if (inintervalLoRo(v, L[offset + 1 - width], L[offset - 1 + width])) { float f1 = fabs(L[offset - 2 + width2] - L[offset - 1 + width]); float f2 = L[offset - 1 + width] - v; float f3 = (L[offset - 1 + width] - L[offset - width - 1]) * (L[offset - 1 + width] - L[offset + width + 1]); From d9a62aa27af2d3fa930d370c7ed524451cac81d4 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Sun, 9 Feb 2020 14:14:46 +0100 Subject: [PATCH 5/5] Fix LGTM alerts --- rtengine/ipsharpenedges.cc | 48 +++++++++++++++++++------------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/rtengine/ipsharpenedges.cc b/rtengine/ipsharpenedges.cc index 8dd12c836..6a44ee40a 100644 --- a/rtengine/ipsharpenedges.cc +++ b/rtengine/ipsharpenedges.cc @@ -75,8 +75,8 @@ void ImProcFunctions::MLsharpen (LabImage* lab) constexpr float chmax[3] = {1.f / 8.f, 1.f / 3.f, 1.f / 3.f}; const int width2 = 2 * width; constexpr float eps2 = 0.001f; //prevent divide by zero - const float amount = params->sharpenEdge.amount / 100.0f; - const float amountby3 = params->sharpenEdge.amount / 300.0f; + const float amount = params->sharpenEdge.amount / 100.0; + const float amountby3 = params->sharpenEdge.amount / 300.0; std::unique_ptr L(new float[width * height]); @@ -103,12 +103,12 @@ void ImProcFunctions::MLsharpen (LabImage* lab) for (int j = 2; j < height - 2; j++) { for (int i = 2, offset = j * width + i; i < width - 2; i++, offset++) { // weight functions - const float wH = eps2 + fabs(L[offset + 1] - L[offset - 1]); - const float wV = eps2 + fabs(L[offset + width] - L[offset - width]); + const float wH = eps2 + std::fabs(L[offset + 1] - L[offset - 1]); + const float wV = eps2 + std::fabs(L[offset + width] - L[offset - width]); - float s = 2.f / (2.f + fabs(wH - wV)); - float wD1 = eps2 + fabs(L[offset + width + 1] - L[offset - width - 1]) * s; - float wD2 = eps2 + fabs(L[offset + width - 1] - L[offset - width + 1]) * s; + float s = 2.f / (2.f + std::fabs(wH - wV)); + float wD1 = eps2 + std::fabs(L[offset + width + 1] - L[offset - width - 1]) * s; + float wD2 = eps2 + std::fabs(L[offset + width - 1] - L[offset - width + 1]) * s; s = wD1; wD1 /= wD2; wD2 /= s; @@ -122,16 +122,16 @@ void ImProcFunctions::MLsharpen (LabImage* lab) // new possible values if (inintervalLoRo(v, L[offset - 1], L[offset + 1])) { - float f1 = fabs(L[offset - 2] - L[offset - 1]); + float f1 = std::fabs(L[offset - 2] - L[offset - 1]); float f2 = L[offset - 1] - v; float f3 = (L[offset - 1] - L[offset - width]) * (L[offset - 1] - L[offset + width]); - float f4 = std::sqrt(fabs((L[offset - 1] - L[offset - width2]) * (L[offset - 1] - L[offset + width2]))); + float f4 = std::sqrt(std::fabs((L[offset - 1] - L[offset - width2]) * (L[offset - 1] - L[offset + width2]))); const float difL = f1 * SQR(f2 * f3) * f4; if (difL > 0.f) { - f1 = fabs(L[offset + 2] - L[offset + 1]); + f1 = std::fabs(L[offset + 2] - L[offset + 1]); f2 = L[offset + 1] - v; f3 = (L[offset + 1] - L[offset - width]) * (L[offset + 1] - L[offset + width]); - f4 = std::sqrt(fabs((L[offset + 1] - L[offset - width2]) * (L[offset + 1] - L[offset + width2]))); + f4 = std::sqrt(std::fabs((L[offset + 1] - L[offset - width2]) * (L[offset + 1] - L[offset + width2]))); const float difR = f1 * SQR(f2 * f3) * f4; if (difR > 0.f) { lumH = (L[offset - 1] * difR + L[offset + 1] * difL) / (difL + difR); @@ -141,16 +141,16 @@ void ImProcFunctions::MLsharpen (LabImage* lab) } if (inintervalLoRo(v, L[offset - width], L[offset + width])) { - float f1 = fabs(L[offset - width2] - L[offset - width]); + float f1 = std::fabs(L[offset - width2] - L[offset - width]); float f2 = L[offset - width] - v; float f3 = (L[offset - width] - L[offset - 1]) * (L[offset - width] - L[offset + 1]); - float f4 = std::sqrt(fabs((L[offset - width] - L[offset - 2]) * (L[offset - width] - L[offset + 2]))); + float f4 = std::sqrt(std::fabs((L[offset - width] - L[offset - 2]) * (L[offset - width] - L[offset + 2]))); const float difT = f1 * SQR(f2 * f3) * f4; if (difT > 0.f) { - f1 = fabs(L[offset + width2] - L[offset + width]); + f1 = std::fabs(L[offset + width2] - L[offset + width]); f2 = L[offset + width] - v; f3 = (L[offset + width] - L[offset - 1]) * (L[offset + width] - L[offset + 1]); - f4 = std::sqrt(fabs((L[offset + width] - L[offset - 2]) * (L[offset + width] - L[offset + 2]))); + f4 = std::sqrt(std::fabs((L[offset + width] - L[offset - 2]) * (L[offset + width] - L[offset + 2]))); const float difB = f1 * SQR(f2 * f3) * f4; if (difB > 0.f) { lumV = (L[offset - width] * difB + L[offset + width] * difT) / (difT + difB); @@ -160,16 +160,16 @@ void ImProcFunctions::MLsharpen (LabImage* lab) } if (inintervalLoRo(v, L[offset - 1 - width], L[offset + 1 + width])) { - float f1 = fabs(L[offset - 2 - width2] - L[offset - 1 - width]); + float f1 = std::fabs(L[offset - 2 - width2] - L[offset - 1 - width]); float f2 = L[offset - 1 - width] - v; float f3 = (L[offset - 1 - width] - L[offset - width + 1]) * (L[offset - 1 - width] - L[offset + width - 1]); - float f4 = std::sqrt(fabs((L[offset - 1 - width] - L[offset - width2 + 2]) * (L[offset - 1 - width] - L[offset + width2 - 2]))); + float f4 = std::sqrt(std::fabs((L[offset - 1 - width] - L[offset - width2 + 2]) * (L[offset - 1 - width] - L[offset + width2 - 2]))); const float difLT = f1 * SQR(f2 * f3) * f4; if (difLT > 0.f) { - f1 = fabs(L[offset + 2 + width2] - L[offset + 1 + width]); + f1 = std::fabs(L[offset + 2 + width2] - L[offset + 1 + width]); f2 = L[offset + 1 + width] - v; f3 = (L[offset + 1 + width] - L[offset - width + 1]) * (L[offset + 1 + width] - L[offset + width - 1]); - f4 = std::sqrt(fabs((L[offset + 1 + width] - L[offset - width2 + 2]) * (L[offset + 1 + width] - L[offset + width2 - 2]))); + f4 = std::sqrt(std::fabs((L[offset + 1 + width] - L[offset - width2 + 2]) * (L[offset + 1 + width] - L[offset + width2 - 2]))); const float difRB = f1 * SQR(f2 * f3) * f4; if (difRB > 0.f) { lumD1 = (L[offset - 1 - width] * difRB + L[offset + 1 + width] * difLT) / (difLT + difRB); @@ -179,16 +179,16 @@ void ImProcFunctions::MLsharpen (LabImage* lab) } if (inintervalLoRo(v, L[offset + 1 - width], L[offset - 1 + width])) { - float f1 = fabs(L[offset - 2 + width2] - L[offset - 1 + width]); + float f1 = std::fabs(L[offset - 2 + width2] - L[offset - 1 + width]); float f2 = L[offset - 1 + width] - v; float f3 = (L[offset - 1 + width] - L[offset - width - 1]) * (L[offset - 1 + width] - L[offset + width + 1]); - float f4 = std::sqrt(fabs((L[offset - 1 + width] - L[offset - width2 - 2]) * (L[offset - 1 + width] - L[offset + width2 + 2]))); + float f4 = std::sqrt(std::fabs((L[offset - 1 + width] - L[offset - width2 - 2]) * (L[offset - 1 + width] - L[offset + width2 + 2]))); const float difLB = f1 * SQR(f2 * f3) * f4; if (difLB > 0.f) { - f1 = fabs(L[offset + 2 - width2] - L[offset + 1 - width]); + f1 = std::fabs(L[offset + 2 - width2] - L[offset + 1 - width]); f2 = L[offset + 1 - width] - v; f3 = (L[offset + 1 - width] - L[offset + width + 1]) * (L[offset + 1 - width] - L[offset - width - 1]); - f4 = std::sqrt(fabs((L[offset + 1 - width] - L[offset + width2 + 2]) * (L[offset + 1 - width] - L[offset - width2 - 2]))); + f4 = std::sqrt(std::fabs((L[offset + 1 - width] - L[offset + width2 + 2]) * (L[offset + 1 - width] - L[offset - width2 - 2]))); const float difRT = f1 * SQR(f2 * f3) * f4; if (difRT > 0.f) { lumD2 = (L[offset + 1 - width] * difLB + L[offset - 1 + width] * difRT) / (difLB + difRT); @@ -203,7 +203,7 @@ void ImProcFunctions::MLsharpen (LabImage* lab) if (c == 0) { if (v < 92.f) { - channel[j][i] = fabs(327.68f * intp(weight, (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2), v)); // fabs because lab->L always > 0 + channel[j][i] = std::fabs(327.68f * intp(weight, (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2), v)); // fabs because lab->L always > 0 } } else { channel[j][i] = 327.68f * intp(weight, (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2), v);