From 7d691c46c4e76f5faceb5e3cbdefbe06988cf785 Mon Sep 17 00:00:00 2001 From: Desmis Date: Thu, 16 May 2019 08:18:24 +0200 Subject: [PATCH] Improve mask Retinex normal --- rtengine/improcfun.h | 4 ++-- rtengine/iplocallab.cc | 48 +++++++++++++++++++++++++++++++----------- rtengine/ipretinex.cc | 43 ++++++++++++++++++++++++++++++++----- 3 files changed, 76 insertions(+), 19 deletions(-) diff --git a/rtengine/improcfun.h b/rtengine/improcfun.h index 62d1b7948..1ed3e4ed0 100644 --- a/rtengine/improcfun.h +++ b/rtengine/improcfun.h @@ -298,7 +298,7 @@ public: void idirpyr(LabImage* data_coarse, LabImage* data_fine, int level, LUTf &rangefn_L, LUTf & nrwt_l, LUTf & nrwt_ab, int pitch, int scale, const int luma, const int chroma/*, LUTf & Lcurve, LUTf & abcurve*/); //locallab - void MSRLocal(int sp, int lum, LabImage * bufreti, LabImage * bufmask, float** luminance, float** templ, const float* const *originalLuminance, const int width, const int height, const procparams::LocallabParams &loc, const int skip, const LocretigainCurve &locRETgainCcurve, const int chrome, const int scall, const float krad, float &minCD, float &maxCD, float &mini, float &maxi, float &Tmean, float &Tsigma, float &Tmin, float &Tmax, + void MSRLocal(int sp, int lum, LabImage * bufreti, LabImage * bufmask, LabImage * buforig, LabImage * buforigmas, float** luminance, float** templ, const float* const *originalLuminance, const int width, const int height, const procparams::LocallabParams &loc, const int skip, const LocretigainCurve &locRETgainCcurve, const int chrome, const int scall, const float krad, float &minCD, float &maxCD, float &mini, float &maxi, float &Tmean, float &Tsigma, float &Tmin, float &Tmax, const LocCCmaskretiCurve & locccmasretiCurve, bool &lcmasretiutili, const LocLLmaskretiCurve & locllmasretiCurve, bool &llmasretiutili, const LocHHmaskretiCurve & lochhmasretiCurve, bool & lhmasretiutili, int llretiMask, LabImage * transformed, bool retiMasktmap, bool retiMask); void calc_ref(int sp, LabImage* original, LabImage* transformed, int cx, int cy, int oW, int oH, int sk, double &huerefblur, double &chromarefblur, double &lumarefblur, double &hueref, double &chromaref, double &lumaref, double &sobelref, float &avg); void copy_ref(LabImage* spotbuffer, LabImage* original, LabImage* transformed, int cx, int cy, int sk, const struct local_params & lp, double &huerefspot, double &chromarefspot, double &lumarefspot); @@ -316,7 +316,7 @@ public: static void strcurv_data(std::string retistr, int *s_datc, int &siz); void blendstruc(int bfw, int bfh, LabImage* bufcolorig, float radius, float stru, array2D & blend2, int sk, bool multiThread); - void transit_shapedetect_retinex(int senstype, LabImage * bufexporig, LabImage * bufmask, float **buflight, float **bufchro, const float hueref, const float chromaref, const float lumaref, const struct local_params & lp, LabImage * original, LabImage * transformed, int cx, int cy, int sk); + void transit_shapedetect_retinex(int senstype, LabImage * bufexporig, LabImage * bufmask, LabImage * buforigmas, float **buflight, float **bufchro, const float hueref, const float chromaref, const float lumaref, const struct local_params & lp, LabImage * original, LabImage * transformed, int cx, int cy, int sk); void transit_shapedetect(int senstype, const LabImage *bufexporig, LabImage * originalmask, float **buflight, float **bufchro, float **buf_a_cat, float ** buf_b_cat, float ** bufhh, bool HHutili, const float hueref, const float chromaref, const float lumaref, float sobelref, float meansobel, float ** blend2, const struct local_params & lp, LabImage * original, LabImage * transformed, int cx, int cy, int sk); void exlabLocal(const local_params& lp, int bfh, int bfw, LabImage* bufexporig, LabImage* lab, LUTf & hltonecurve, LUTf & shtonecurve, LUTf & tonecurve); void Exclude_Local(float **deltaso, float hueref, float chromaref, float lumaref, float sobelref, float meansobel, const struct local_params & lp, const LabImage * original, LabImage * transformed, const LabImage * rsv, const LabImage * reserv, int cx, int cy, int sk); diff --git a/rtengine/iplocallab.cc b/rtengine/iplocallab.cc index fe680f401..56ce68455 100644 --- a/rtengine/iplocallab.cc +++ b/rtengine/iplocallab.cc @@ -458,8 +458,8 @@ static void calcLocalParams(int sp, int oW, int oH, const LocallabParams& locall lp.enaExpMask = locallab.spots.at(sp).enaExpMask && llExpMask == 0 && llColorMask == 0 && llSHMask == 0 && llcbMask == 0 && llretiMask == 0;// Exposure mask is deactivated if Color & Light mask is visible lp.enaSHMask = locallab.spots.at(sp).enaSHMask && llSHMask == 0 && llColorMask == 0 && llExpMask == 0 && llcbMask == 0 && llretiMask == 0; lp.enacbMask = locallab.spots.at(sp).enacbMask && llcbMask == 0 && llColorMask == 0 && llExpMask == 0 && llSHMask == 0 && llretiMask == 0; - lp.enaretiMask = locallab.spots.at(sp).enaretiMask;// && llretiMask == 0 ;// && llColorMask == 0 && llExpMask == 0 && llSHMask == 0 && llcbMask == 0; - if(lp.enaretiMask) printf("lp.enaretiMasktrue\n"); else printf("lp.enaretiMaskfalse\n"); + lp.enaretiMask = locallab.spots.at(sp).enaretiMask && llretiMask == 0 && llColorMask == 0 && llExpMask == 0 && llSHMask == 0 && llcbMask == 0; + // if(lp.enaretiMask) printf("lp.enaretiMasktrue\n"); else printf("lp.enaretiMaskfalse\n"); if (locallab.spots.at(sp).blurMethod == "norm") { @@ -2296,7 +2296,7 @@ void ImProcFunctions::Exclude_Local(float **deltaso, float hueref, float chromar } } -void ImProcFunctions::transit_shapedetect_retinex(int senstype, LabImage * bufexporig, LabImage * bufmask, float **buflight, float **bufchro, const float hueref, const float chromaref, const float lumaref, const struct local_params & lp, LabImage * original, LabImage * transformed, int cx, int cy, int sk) +void ImProcFunctions::transit_shapedetect_retinex(int senstype, LabImage * bufexporig, LabImage * bufmask, LabImage * buforigmas, float **buflight, float **bufchro, const float hueref, const float chromaref, const float lumaref, const struct local_params & lp, LabImage * original, LabImage * transformed, int cx, int cy, int sk) { BENCHFUN { @@ -2316,9 +2316,12 @@ void ImProcFunctions::transit_shapedetect_retinex(int senstype, LabImage * bufex float kab = 1.f; balancedeltaE(kL, kab); bool showmas = false ; - if(lp.showmaskretimet == 3) showmas = true; + if(lp.showmaskretimet == 3) { + showmas = true; + } std::unique_ptr origblur(new LabImage(GW, GH)); const float radius = 3.f / sk; + const bool usemaskreti = (lp.showmaskretimet == 2 || lp.enaretiMask || lp.showmaskretimet == 4) && senstype == 4 && !lp.enaretiMasktmap; #ifdef _OPENMP #pragma omp parallel @@ -2327,7 +2330,6 @@ void ImProcFunctions::transit_shapedetect_retinex(int senstype, LabImage * bufex gaussianBlur(original->L, origblur->L, GW, GH, radius); gaussianBlur(original->a, origblur->a, GW, GH, radius); gaussianBlur(original->b, origblur->b, GW, GH, radius); - } @@ -2374,9 +2376,12 @@ void ImProcFunctions::transit_shapedetect_retinex(int senstype, LabImage * bufex } float rL = origblur->L[y][x] / 327.68f; - - const float dE = sqrt(kab * SQR(refa - origblur->a[y][x] / 327.68f) + kab * SQR(refb - origblur->b[y][x] / 327.68f) + kL * SQR(lumaref - rL)); - + float dE; + if(!usemaskreti) { + dE = sqrt(kab * SQR(refa - origblur->a[y][x] / 327.68f) + kab * SQR(refb - origblur->b[y][x] / 327.68f) + kL * SQR(lumaref - rL)); + } else { + dE = sqrt(kab * SQR(refa - buforigmas->a[loy - begy][lox - begx] / 327.68f) + kab * SQR(refb - buforigmas->b[loy - begy][lox - begx] / 327.68f) + kL * SQR(lumaref - buforigmas->L[loy - begy][lox - begx] / 327.68f)); + } float cli = buflight[loy - begy][lox - begx]; //float clc = bufchro[loy - begy][lox - begx]; float clc = previewreti ? settings->previewselection * 100.f : bufchro[loy - begy][lox - begx]; @@ -5747,6 +5752,8 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o LabImage *bufreti = nullptr; LabImage *bufmask = nullptr; + LabImage *buforig = nullptr; + LabImage *buforigmas = nullptr; int bfh = int (lp.ly + lp.lyT) + del; //bfw bfh real size of square zone int bfw = int (lp.lx + lp.lxL) + del; array2D buflight(bfw, bfh); @@ -5762,6 +5769,10 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o Wd = bfw; bufreti = new LabImage(bfw, bfh); bufmask = new LabImage(bfw, bfh); + if(!lp.enaretiMasktmap && lp.enaretiMask) { + buforig = new LabImage(bfw, bfh); + buforigmas = new LabImage(bfw, bfh); + } #ifdef _OPENMP #pragma omp parallel for @@ -5797,6 +5808,11 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o bufmask->L[loy - begy][lox - begx] = original->L[y][x]; bufmask->a[loy - begy][lox - begx] = original->a[y][x]; bufmask->b[loy - begy][lox - begx] = original->b[y][x]; + if(!lp.enaretiMasktmap && lp.enaretiMask) { + buforig->L[loy - begy][lox - begx] = original->L[y][x]; + buforig->a[loy - begy][lox - begx] = original->a[y][x]; + buforig->b[loy - begy][lox - begx] = original->b[y][x]; + } } } @@ -5901,7 +5917,7 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o } float minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax; - ImProcFunctions::MSRLocal(sp, 1, bufreti, bufmask, orig, tmpl->L, orig1, Wd, Hd, params->locallab, sk, locRETgainCcurve, 0, 4, 0.8f, minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax, + ImProcFunctions::MSRLocal(sp, 1, bufreti, bufmask, buforig, buforigmas, orig, tmpl->L, orig1, Wd, Hd, params->locallab, sk, locRETgainCcurve, 0, 4, 0.8f, minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax, locccmasretiCurve, lcmasretiutili, locllmasretiCurve, llmasretiutili, lochhmasretiCurve, lhmasretiutili, llretiMask, transformed, lp.enaretiMasktmap, lp.enaretiMask); #ifdef _OPENMP #pragma omp parallel for @@ -5939,7 +5955,7 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o // softprocess(bufreti, buflight, lp.softradiusret, Hd, Wd, sk, multiThread); } - transit_shapedetect_retinex(4, bufreti, bufmask, buflight, bufchro, hueref, chromaref, lumaref, lp, original, transformed, cx, cy, sk); + transit_shapedetect_retinex(4, bufreti, bufmask, buforigmas, buflight, bufchro, hueref, chromaref, lumaref, lp, original, transformed, cx, cy, sk); } else { InverseReti_Local(lp, hueref, chromaref, lumaref, original, transformed, tmpl, cx, cy, 0, sk); @@ -5973,7 +5989,7 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o } } - ImProcFunctions::MSRLocal(sp, 0, bufreti, bufmask, orig, tmpl->L, orig1, Wd, Hd, params->locallab, sk, locRETgainCcurve, 1, 4, 0.8f, minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax, + ImProcFunctions::MSRLocal(sp, 0, bufreti, bufmask, buforig, buforigmas, orig, tmpl->L, orig1, Wd, Hd, params->locallab, sk, locRETgainCcurve, 1, 4, 0.8f, minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax, locccmasretiCurve, lcmasretiutili, locllmasretiCurve, llmasretiutili, lochhmasretiCurve, lhmasretiutili, llretiMask, transformed, lp.enaretiMasktmap, lp.enaretiMask); if (!lp.invret && call <= 3) { @@ -6033,7 +6049,7 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o if (!lp.invret) { - transit_shapedetect_retinex(5, tmpl, bufmask, buflight, bufchro, hueref, chromaref, lumaref, lp, original, transformed, cx, cy, sk); + transit_shapedetect_retinex(5, tmpl, bufmask, buforigmas, buflight, bufchro, hueref, chromaref, lumaref, lp, original, transformed, cx, cy, sk); } else { InverseReti_Local(lp, hueref, chromaref, lumaref, original, transformed, tmpl, cx, cy, 1, sk); } @@ -6046,6 +6062,14 @@ void ImProcFunctions::Lab_Local(int call, int sp, float** shbuffer, LabImage * o if (bufmask) { delete bufmask; } + if(!lp.enaretiMasktmap && lp.enaretiMask) { + if (buforig) { + delete buforig; + } + if (buforigmas) { + delete buforigmas; + } + } if (bufreti) { delete bufreti; } diff --git a/rtengine/ipretinex.cc b/rtengine/ipretinex.cc index 88c3902ea..1f284840c 100644 --- a/rtengine/ipretinex.cc +++ b/rtengine/ipretinex.cc @@ -843,7 +843,7 @@ void RawImageSource::MSR(float** luminance, float** originalLuminance, float **e } } -void ImProcFunctions::MSRLocal(int sp, int lum, LabImage * bufreti, LabImage * bufmask, float** luminance, float** templ, const float* const *originalLuminance, const int width, const int height, const LocallabParams &loc, const int skip, const LocretigainCurve &locRETgainCcurve, const int chrome, const int scall, const float krad, float &minCD, float &maxCD, float &mini, float &maxi, float &Tmean, float &Tsigma, float &Tmin, float &Tmax, +void ImProcFunctions::MSRLocal(int sp, int lum, LabImage * bufreti, LabImage * bufmask, LabImage * buforig, LabImage * buforigmas, float** luminance, float** templ, const float* const *originalLuminance, const int width, const int height, const LocallabParams &loc, const int skip, const LocretigainCurve &locRETgainCcurve, const int chrome, const int scall, const float krad, float &minCD, float &maxCD, float &mini, float &maxi, float &Tmean, float &Tsigma, float &Tmin, float &Tmax, const LocCCmaskretiCurve & locccmasretiCurve, bool &lcmasretiutili, const LocLLmaskretiCurve & locllmasretiCurve, bool &llmasretiutili, const LocHHmaskretiCurve & lochhmasretiCurve, bool & lhmasretiutili, int llretiMask, LabImage * transformed, bool retiMasktmap, bool retiMask) { BENCHFUN @@ -1050,9 +1050,9 @@ void ImProcFunctions::MSRLocal(int sp, int lum, LabImage * bufreti, LabImage * b gaussianBlur(bufmaskblurreti->b, bufmaskorigreti->b, W_L, H_L, 1.f + (0.5f * loc.spots.at(sp).radmaskreti) / skip); } + float modr = 0.01f * (float) loc.spots.at(sp).blendmaskreti; if(llretiMask != 3 && retiMask) { - float modr = 0.01f * (float) loc.spots.at(sp).blendmaskreti; #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif @@ -1073,8 +1073,41 @@ void ImProcFunctions::MSRLocal(int sp, int lum, LabImage * bufreti, LabImage * b bufreti->b[y][x] = CLIPC(bufreti->b[y][x]); } } - } - + } + if(!retiMasktmap && retiMask) {//new original blur mask for deltaE +#ifdef _OPENMP + #pragma omp parallel for schedule(dynamic,16) +#endif + for (int y = 0; y < H_L; y++) { + for (int x = 0; x < W_L; x++) { + + buforig->L[y][x] += (modr * bufmaskorigreti->L[y][x]); + buforig->a[y][x] *= (1.f + modr * bufmaskorigreti->a[y][x]); + buforig->b[y][x] *= (1.f + modr * bufmaskorigreti->b[y][x]); + + buforig->L[y][x] = CLIP(buforig->L[y][x]); + buforig->a[y][x] = CLIPC(buforig->a[y][x]); + buforig->b[y][x] = CLIPC(buforig->b[y][x]); + + buforig->L[y][x] = CLIP(buforig->L[y][x] - bufmaskorigreti->L[y][x]); + buforig->a[y][x] = CLIPC(buforig->a[y][x] * (1.f - bufmaskorigreti->a[y][x])); + buforig->b[y][x] = CLIPC(buforig->b[y][x] * (1.f - bufmaskorigreti->b[y][x])); + } + } + + float radius = 3.f / skip; + +#ifdef _OPENMP + #pragma omp parallel if (multiThread) +#endif + { + gaussianBlur(buforig->L, buforigmas->L, W_L, H_L, radius); + gaussianBlur(buforig->a, buforigmas->a, W_L, H_L, radius); + gaussianBlur(buforig->b, buforigmas->b, W_L, H_L, radius); + } + + } + if(llretiMask == 3){ #ifdef _OPENMP @@ -1110,7 +1143,7 @@ void ImProcFunctions::MSRLocal(int sp, int lum, LabImage * bufreti, LabImage * b for (; j < W_L - 3; j += 4) { _mm_storeu_ps(&luminance[i][j], LVFU(luminance[i][j]) + pondv * (vclampf(LVFU(src[i][j]) / LVFU(out[i][j]), limMinv, limMaxv) )); } - } else {//always Lab mode due to Wavelet + } else { for (; j < W_L - 3; j += 4) { _mm_storeu_ps(&luminance[i][j], LVFU(luminance[i][j]) + pondv * xlogf(vclampf(LVFU(src[i][j]) / LVFU(out[i][j]), limMinv, limMaxv) )); }