diff --git a/rtengine/improcfun.h b/rtengine/improcfun.h index ff5d380b1..55ef6f9dc 100644 --- a/rtengine/improcfun.h +++ b/rtengine/improcfun.h @@ -190,7 +190,7 @@ public: void chromiLuminanceCurve(PipetteBuffer *pipetteBuffer, int pW, LabImage* lold, LabImage* lnew, const LUTf& acurve, const LUTf& bcurve, const LUTf& satcurve, const LUTf& satclcurve, const LUTf& clcurve, LUTf &curve, bool utili, bool autili, bool butili, bool ccutili, bool cclutili, bool clcutili, LUTu &histCCurve, LUTu &histLurve); void vibrance(LabImage* lab, const procparams::VibranceParams &vibranceParams, bool highlight, const Glib::ustring &workingProfile); //Jacques' vibrance void softprocess(const LabImage* bufcolorig, array2D &buflight, /* float ** bufchro, float ** buf_a, float ** buf_b, */ float rad, int bfh, int bfw, double epsilmax, double epsilmin, float thres, int sk, bool multiThread); - void softproc(const LabImage* bufcolorig, const LabImage* bufcolfin, float rad, int bfh, int bfw, double epsilmax, double epsilmin, float thres, int sk, bool multiThread, int flag); + void softproc(const LabImage* bufcolorig, const LabImage* bufcolfin, float rad, int bfh, int bfw, float epsilmax, float epsilmin, float thres, int sk, bool multiThread, int flag); // void colorCurve (LabImage* lold, LabImage* lnew); void sharpening(LabImage* lab, const procparams::SharpeningParams &sharpenParam, bool showMask = false); void sharpeningcam(CieImage* ncie, float** buffer, bool showMask = false); diff --git a/rtengine/iplocallab.cc b/rtengine/iplocallab.cc index c575b803c..14c09f30d 100644 --- a/rtengine/iplocallab.cc +++ b/rtengine/iplocallab.cc @@ -2248,122 +2248,73 @@ void ImProcFunctions::ciecamloc_02float(int sp, LabImage* lab) } } -void ImProcFunctions::softproc(const LabImage* bufcolorig, const LabImage* bufcolfin, float rad, int bfh, int bfw, double epsilmax, double epsilmin, float thres, int sk, bool multiThread, int flag) +void ImProcFunctions::softproc(const LabImage* bufcolorig, const LabImage* bufcolfin, float rad, int bfh, int bfw, float epsilmax, float epsilmin, float thres, int sk, bool multiThread, int flag) { - if (flag == 0) { - if (rad > 0.f) { - array2D ble(bfw, bfh); - array2D guid(bfw, bfh); - Imagefloat *tmpImage = nullptr; - tmpImage = new Imagefloat(bfw, bfh); + if (rad > 0.f) { + array2D ble(bfw, bfh); + array2D guid(bfw, bfh); + if (flag == 0) { #ifdef _OPENMP - #pragma omp parallel for -#endif - - for (int ir = 0; ir < bfh; ir++) - for (int jr = 0; jr < bfw; jr++) { - - float X, Y, Z; - float L = bufcolorig->L[ir][jr]; - float a = bufcolorig->a[ir][jr]; - float b = bufcolorig->b[ir][jr]; - Color::Lab2XYZ(L, a, b, X, Y, Z); - - guid[ir][jr] = Y / 32768.f; - float La = bufcolfin->L[ir][jr]; - float aa = bufcolfin->a[ir][jr]; - float ba = bufcolfin->b[ir][jr]; - Color::Lab2XYZ(La, aa, ba, X, Y, Z); - tmpImage->r(ir, jr) = X; - tmpImage->g(ir, jr) = Y; - tmpImage->b(ir, jr) = Z; - - ble[ir][jr] = Y / 32768.f; - } - - double aepsil = (epsilmax - epsilmin) / 90.f; - double bepsil = epsilmax - 100.f * aepsil; - double epsil = aepsil * 0.1 * rad + bepsil; - - float blur = 10.f / sk * (thres + 0.8f * rad); - rtengine::guidedFilter(guid, ble, ble, blur, epsil, multiThread, 4); - - - -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for (int ir = 0; ir < bfh; ir++) - for (int jr = 0; jr < bfw; jr++) { - float X = tmpImage->r(ir, jr); - float Y = 32768.f * ble[ir][jr]; - float Z = tmpImage->b(ir, jr); - float L, a, b; - Color::XYZ2Lab(X, Y, Z, L, a, b); - bufcolfin->L[ir][jr] = L; - } - - delete tmpImage; - } - } else if (flag == 1) { - if (rad > 0.f) { - array2D ble(bfw, bfh); - array2D blechro(bfw, bfh); - array2D hue(bfw, bfh); - array2D guid(bfw, bfh); - -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for (int ir = 0; ir < bfh; ir++) - for (int jr = 0; jr < bfw; jr++) { -// hue[ir][jr] = xatan2f(bufcolfin->b[ir][jr], bufcolfin->a[ir][jr]); -// float chromah = std::sqrt(SQR(bufcolfin->b[ir][jr]) + SQR(bufcolfin->a[ir][jr])); - - ble[ir][jr] = (bufcolfin->L[ir][jr]) / 32768.f; -// blechro[ir][jr] = chromah / 32768.f; - guid[ir][jr] = bufcolorig->L[ir][jr] / 32768.f; - } - - double aepsil = (epsilmax - epsilmin) / 90.f; - double bepsil = epsilmax - 100.f * aepsil; - double epsil = aepsil * 0.1 * rad + bepsil; - - if (rad != 0.f) { - float blur = rad; - blur = blur < 0.f ? -1.f / blur : 1.f + blur; - // int r1 = max(int(4 / sk * blur + 0.5), 1); - int r2 = max(int(25 / sk * blur + 0.5), 1); - - if (rad < 0.f) { - epsil = 0.0001; - } - rtengine::guidedFilter(guid, ble, ble, r2, epsil, multiThread); - } - - - -#ifdef _OPENMP - #pragma omp parallel for + #pragma omp parallel for if(multiThread) #endif for (int ir = 0; ir < bfh; ir++) { for (int jr = 0; jr < bfw; jr++) { - // float2 sincosval = xsincosf(hue[ir][jr]); + guid[ir][jr] = Color::L2Y(bufcolorig->L[ir][jr]) / 32768.f; + ble[ir][jr] = Color::L2Y(bufcolfin->L[ir][jr]) / 32768.f; + } + } + const float aepsil = (epsilmax - epsilmin) / 90.f; + const float bepsil = epsilmax - 100.f * aepsil; + const float epsil = aepsil * 0.1f * rad + bepsil; + const float blur = 10.f / sk * (thres + 0.8f * rad); + + rtengine::guidedFilter(guid, ble, ble, blur, epsil, multiThread, 4); + +#ifdef _OPENMP + #pragma omp parallel for if(multiThread) +#endif + + for (int ir = 0; ir < bfh; ir++) { + for (int jr = 0; jr < bfw; jr++) { + bufcolfin->L[ir][jr] = Color::computeXYZ2LabY(32768.f * ble[ir][jr]); + } + } + } else if (flag == 1) { + +#ifdef _OPENMP + #pragma omp parallel for if(multiThread) +#endif + + for (int ir = 0; ir < bfh; ir++) + for (int jr = 0; jr < bfw; jr++) { + ble[ir][jr] = bufcolfin->L[ir][jr] / 32768.f; + guid[ir][jr] = bufcolorig->L[ir][jr] / 32768.f; + } + + const float aepsil = (epsilmax - epsilmin) / 90.f; + const float bepsil = epsilmax - 100.f * aepsil; + const float epsil = rad < 0.f ? 0.0001f : aepsil * 0.1f * rad + bepsil; + const float blur = rad < 0.f ? -1.f / rad : 1.f + rad; + const int r2 = std::max(int(25 / sk * blur + 0.5f), 1); + + rtengine::guidedFilter(guid, ble, ble, r2, epsil, multiThread); + +#ifdef _OPENMP + #pragma omp parallel for if(multiThread) +#endif + + for (int ir = 0; ir < bfh; ir++) { + for (int jr = 0; jr < bfw; jr++) { bufcolfin->L[ir][jr] = 32768.f * ble[ir][jr]; - // bufcolfin->a[ir][jr] = 32768.f * sincosval.y * blechro[ir][jr]; - // bufcolfin->b[ir][jr] = 32768.f * sincosval.x * blechro[ir][jr]; } } } } } - void ImProcFunctions::softprocess(const LabImage* bufcolorig, array2D &buflight, float rad, int bfh, int bfw, double epsilmax, double epsilmin, float thres, int sk, bool multiThread) { float minlig = buflight[0][0];