Issue 2850: normalized RGB-pipeline curve gammas to sRGB, make curve algorithms operate on linear image data
This commit is contained in:
@@ -340,6 +340,11 @@ void CurveFactory::curveBW (
|
|||||||
LUTu & histogrambw, LUTu & outBeforeCCurveHistogrambw,//for Luminance
|
LUTu & histogrambw, LUTu & outBeforeCCurveHistogrambw,//for Luminance
|
||||||
ToneCurve & customToneCurvebw1, ToneCurve & customToneCurvebw2, int skip)
|
ToneCurve & customToneCurvebw1, ToneCurve & customToneCurvebw2, int skip)
|
||||||
{
|
{
|
||||||
|
const float gamma_ = Color::sRGBGamma;
|
||||||
|
const float start = expf(gamma_*logf( -0.055 / ((1.0/gamma_-1.0)*1.055 )));
|
||||||
|
const float slope = 1.055 * powf (start, 1.0/gamma_-1) - 0.055/start;
|
||||||
|
const float mul = 1.055;
|
||||||
|
const float add = 0.055;
|
||||||
|
|
||||||
outBeforeCCurveHistogrambw.clear();
|
outBeforeCCurveHistogrambw.clear();
|
||||||
bool histNeeded = false;
|
bool histNeeded = false;
|
||||||
@@ -355,7 +360,7 @@ void CurveFactory::curveBW (
|
|||||||
}
|
}
|
||||||
if (tcurve) {
|
if (tcurve) {
|
||||||
if (!tcurve->isIdentity())
|
if (!tcurve->isIdentity())
|
||||||
customToneCurvebw2.Set(tcurve);
|
customToneCurvebw2.Set(tcurve, gamma_, start, slope, mul, add);
|
||||||
delete tcurve;
|
delete tcurve;
|
||||||
tcurve = NULL;
|
tcurve = NULL;
|
||||||
}
|
}
|
||||||
@@ -370,7 +375,7 @@ void CurveFactory::curveBW (
|
|||||||
}
|
}
|
||||||
if (tcurve) {
|
if (tcurve) {
|
||||||
if (!tcurve->isIdentity())
|
if (!tcurve->isIdentity())
|
||||||
customToneCurvebw1.Set(tcurve);
|
customToneCurvebw1.Set(tcurve, gamma_, start, slope, mul, add);
|
||||||
delete tcurve;
|
delete tcurve;
|
||||||
tcurve = NULL;
|
tcurve = NULL;
|
||||||
}
|
}
|
||||||
@@ -617,7 +622,7 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
|
||||||
SSEFUNCTION void CurveFactory::complexCurve (double ecomp, double black, double hlcompr, double hlcomprthresh,
|
SSEFUNCTION void CurveFactory::complexCurve (double ecomp, double black, double hlcompr, double hlcomprthresh,
|
||||||
double shcompr, double br, double contr, double gamma_, bool igamma_,
|
double shcompr, double br, double contr,
|
||||||
procparams::ToneCurveParams::eTCModeId curveMode, const std::vector<double>& curvePoints,
|
procparams::ToneCurveParams::eTCModeId curveMode, const std::vector<double>& curvePoints,
|
||||||
procparams::ToneCurveParams::eTCModeId curveMode2, const std::vector<double>& curvePoints2,
|
procparams::ToneCurveParams::eTCModeId curveMode2, const std::vector<double>& curvePoints2,
|
||||||
LUTu & histogram, LUTu & histogramCropped,
|
LUTu & histogram, LUTu & histogramCropped,
|
||||||
@@ -627,31 +632,16 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
ToneCurve & customToneCurve2,
|
ToneCurve & customToneCurve2,
|
||||||
int skip) {
|
int skip) {
|
||||||
|
|
||||||
|
// the curve shapes are defined in sRGB gamma, but the output curves will operate on linear floating point data,
|
||||||
//double def_mul = pow (2.0, defmul);
|
// hence we do both forward and inverse gamma conversions here.
|
||||||
|
const float gamma_ = Color::sRGBGamma;
|
||||||
/*printf ("def_mul= %f ecomp= %f black= %f hlcompr= %f shcompr= %f br= %f contr= %f defmul= %f
|
const float start = expf(gamma_*logf( -0.055 / ((1.0/gamma_-1.0)*1.055 )));
|
||||||
gamma= %f, skip= %d \n",def_mul,ecomp,black,hlcompr,shcompr,br,contr,defmul,gamma_,skip);*/
|
const float slope = 1.055 * powf (start, 1.0/gamma_-1) - 0.055/start;
|
||||||
|
const float mul = 1.055;
|
||||||
// compute parameters of the gamma curve
|
const float add = 0.055;
|
||||||
/*double start = exp(gamma_*log( -0.099 / ((1.0/gamma_-1.0)*1.099 )));
|
|
||||||
double slope = 1.099 * pow (start, 1.0/gamma_-1) - 0.099/start;
|
|
||||||
double mul = 1.099;
|
|
||||||
double add = 0.099;
|
|
||||||
// gamma BT709*/
|
|
||||||
|
|
||||||
//normalize gamma to sRGB
|
|
||||||
double start = exp(gamma_*log( -0.055 / ((1.0/gamma_-1.0)*1.055 )));
|
|
||||||
double slope = 1.055 * pow (start, 1.0/gamma_-1) - 0.055/start;
|
|
||||||
double mul = 1.055;
|
|
||||||
double add = 0.055;
|
|
||||||
|
|
||||||
// a: slope of the curve, black: starting point at the x axis
|
// a: slope of the curve, black: starting point at the x axis
|
||||||
double a = pow (2.0, ecomp);
|
const float a = powf (2.0, ecomp);
|
||||||
|
|
||||||
|
|
||||||
// check if inverse gamma is needed at the end
|
|
||||||
bool needigamma = igamma_ && gamma_>1.;
|
|
||||||
|
|
||||||
// clear array that stores histogram valid before applying the custom curve
|
// clear array that stores histogram valid before applying the custom curve
|
||||||
outBeforeCCurveHistogram.clear();
|
outBeforeCCurveHistogram.clear();
|
||||||
@@ -727,9 +717,8 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
float val2 = simplebasecurve (val, black, 0.015*shcompr);
|
float val2 = simplebasecurve (val, black, 0.015*shcompr);
|
||||||
shCurve[0] = CLIPD(val2)/val;
|
shCurve[0] = CLIPD(val2)/val;
|
||||||
val = 0.0;
|
val = 0.0;
|
||||||
// gamma correction
|
// gamma correction
|
||||||
if (gamma_>1.)
|
val = gamma (val, gamma_, start, slope, mul, add);
|
||||||
val = gamma (val, gamma_, start, slope, mul, add);
|
|
||||||
|
|
||||||
// apply brightness curve
|
// apply brightness curve
|
||||||
if (brightcurve)
|
if (brightcurve)
|
||||||
@@ -747,8 +736,7 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
shCurve[i] = CLIPD(val2)/val;
|
shCurve[i] = CLIPD(val2)/val;
|
||||||
|
|
||||||
// gamma correction
|
// gamma correction
|
||||||
if (gamma_>1.)
|
val = gamma (val, gamma_, start, slope, mul, add);
|
||||||
val = gamma (val, gamma_, start, slope, mul, add);
|
|
||||||
|
|
||||||
// apply brightness curve
|
// apply brightness curve
|
||||||
if (brightcurve)
|
if (brightcurve)
|
||||||
@@ -825,7 +813,7 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
}
|
}
|
||||||
if (tcurve) {
|
if (tcurve) {
|
||||||
if (!tcurve->isIdentity())
|
if (!tcurve->isIdentity())
|
||||||
customToneCurve2.Set(tcurve);
|
customToneCurve2.Set(tcurve, gamma_, start, slope, mul, add);
|
||||||
delete tcurve;
|
delete tcurve;
|
||||||
tcurve = NULL;
|
tcurve = NULL;
|
||||||
}
|
}
|
||||||
@@ -844,7 +832,7 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
}
|
}
|
||||||
if (tcurve) {
|
if (tcurve) {
|
||||||
if (!tcurve->isIdentity())
|
if (!tcurve->isIdentity())
|
||||||
customToneCurve1.Set(tcurve);
|
customToneCurve1.Set(tcurve, gamma_, start, slope, mul, add);
|
||||||
delete tcurve;
|
delete tcurve;
|
||||||
tcurve = NULL;
|
tcurve = NULL;
|
||||||
}
|
}
|
||||||
@@ -904,11 +892,7 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
int hi = (int)(255.0*(hval));
|
int hi = (int)(255.0*(hval));
|
||||||
outBeforeCCurveHistogram[hi] += histogram/*Cropped*/[i] ;
|
outBeforeCCurveHistogram[hi] += histogram/*Cropped*/[i] ;
|
||||||
}
|
}
|
||||||
|
val = igamma (val, gamma_, start, slope, mul, add);
|
||||||
// if inverse gamma is needed, do it (standard sRGB inverse gamma is applied)
|
|
||||||
if (needigamma)
|
|
||||||
val = igamma (val, gamma_, start, slope, mul, add);
|
|
||||||
|
|
||||||
outCurve[i] = (65535.f * val);
|
outCurve[i] = (65535.f * val);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1137,7 +1121,13 @@ void CurveFactory::curveToningLL ( bool & llctoningutili,const std::vector<doubl
|
|||||||
outCurve(65536, 0);
|
outCurve(65536, 0);
|
||||||
for (int i=0; i<65536; i++) {
|
for (int i=0; i<65536; i++) {
|
||||||
// apply custom/parametric/NURBS curve, if any
|
// apply custom/parametric/NURBS curve, if any
|
||||||
float val = tcurve->getVal ((float)i/65536.0f);
|
|
||||||
|
// RGB curves are defined with sRGB gamma, but operate on linear data
|
||||||
|
float val = float(i)/65535.f;
|
||||||
|
val = CurveFactory::gamma2 (val);
|
||||||
|
val = tcurve->getVal(val);
|
||||||
|
val = CurveFactory::igamma2 (val);
|
||||||
|
//float val = tcurve->getVal ((float)i/65536.0f);
|
||||||
outCurve[i] = (65536.0f * val);
|
outCurve[i] = (65536.0f * val);
|
||||||
}
|
}
|
||||||
delete tcurve;
|
delete tcurve;
|
||||||
@@ -1165,9 +1155,20 @@ void ToneCurve::Reset() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Fill a LUT with X/Y, ranged 0xffff
|
// Fill a LUT with X/Y, ranged 0xffff
|
||||||
void ToneCurve::Set(Curve *pCurve) {
|
void ToneCurve::Set(Curve *pCurve, float gamma, float start, float slope, float mul, float add) {
|
||||||
lutToneCurve(65536);
|
lutToneCurve(65536);
|
||||||
for (int i=0; i<65536; i++) lutToneCurve[i] = pCurve->getVal(double(i)/65535.) * 65535.;
|
if (gamma <= 0.0 || gamma == 1.) {
|
||||||
|
for (int i=0; i<65536; i++) lutToneCurve[i] = (float)pCurve->getVal(float(i)/65535.f) * 65535.f;
|
||||||
|
} else {
|
||||||
|
// apply gamma, that is 'pCurve' is defined with the given gamma and here we convert it to a curve in linear space
|
||||||
|
for (int i=0; i<65536; i++) {
|
||||||
|
float val = float(i)/65535.f;
|
||||||
|
val = CurveFactory::gamma (val, gamma, start, slope, mul, add);
|
||||||
|
val = pCurve->getVal(val);
|
||||||
|
val = CurveFactory::igamma (val, gamma, start, slope, mul, add);
|
||||||
|
lutToneCurve[i] = val * 65535.f;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void OpacityCurve::Reset() {
|
void OpacityCurve::Reset() {
|
||||||
|
|||||||
@@ -181,6 +181,12 @@ class CurveFactory {
|
|||||||
static inline double igamma2 (double x) {
|
static inline double igamma2 (double x) {
|
||||||
return x <= 0.03928 ? x/12.92 : exp(log((x+0.055)/1.055)*sRGBGammaCurve);
|
return x <= 0.03928 ? x/12.92 : exp(log((x+0.055)/1.055)*sRGBGammaCurve);
|
||||||
}
|
}
|
||||||
|
static inline float gamma2 (float x) {
|
||||||
|
return x <= 0.00304 ? x*12.92 : 1.055*expf(logf(x)/sRGBGammaCurve)-0.055;
|
||||||
|
}
|
||||||
|
static inline float igamma2 (float x) {
|
||||||
|
return x <= 0.03928 ? x/12.92 : expf(logf((x+0.055)/1.055)*sRGBGammaCurve);
|
||||||
|
}
|
||||||
// gamma function with adjustable parameters
|
// gamma function with adjustable parameters
|
||||||
static inline double gamma (double x, double gamma, double start, double slope, double mul, double add){
|
static inline double gamma (double x, double gamma, double start, double slope, double mul, double add){
|
||||||
return (x <= start ? x*slope : exp(log(x)/gamma)*mul-add);
|
return (x <= start ? x*slope : exp(log(x)/gamma)*mul-add);
|
||||||
@@ -188,6 +194,12 @@ class CurveFactory {
|
|||||||
static inline double igamma (double x, double gamma, double start, double slope, double mul, double add){
|
static inline double igamma (double x, double gamma, double start, double slope, double mul, double add){
|
||||||
return (x <= start*slope ? x/slope : exp(log((x+add)/mul)*gamma) );
|
return (x <= start*slope ? x/slope : exp(log((x+add)/mul)*gamma) );
|
||||||
}
|
}
|
||||||
|
static inline float gamma (float x, float gamma, float start, float slope, float mul, float add){
|
||||||
|
return (x <= start ? x*slope : expf(logf(x)/gamma)*mul-add);
|
||||||
|
}
|
||||||
|
static inline float igamma (float x, float gamma, float start, float slope, float mul, float add){
|
||||||
|
return (x <= start*slope ? x/slope : expf(logf((x+add)/mul)*gamma) );
|
||||||
|
}
|
||||||
|
|
||||||
static inline float hlcurve (const float exp_scale, const float comp, const float hlrange, float level)
|
static inline float hlcurve (const float exp_scale, const float comp, const float hlrange, float level)
|
||||||
{
|
{
|
||||||
@@ -208,7 +220,7 @@ class CurveFactory {
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
static void complexCurve (double ecomp, double black, double hlcompr, double hlcomprthresh, double shcompr, double br, double contr,
|
static void complexCurve (double ecomp, double black, double hlcompr, double hlcomprthresh, double shcompr, double br, double contr,
|
||||||
double gamma_, bool igamma_, procparams::ToneCurveParams::eTCModeId curveMode, const std::vector<double>& curvePoints, procparams::ToneCurveParams::eTCModeId curveMode2, const std::vector<double>& curvePoints2,
|
procparams::ToneCurveParams::eTCModeId curveMode, const std::vector<double>& curvePoints, procparams::ToneCurveParams::eTCModeId curveMode2, const std::vector<double>& curvePoints2,
|
||||||
|
|
||||||
LUTu & histogram, LUTu & histogramCropped,
|
LUTu & histogram, LUTu & histogramCropped,
|
||||||
LUTf & hlCurve, LUTf & shCurve,LUTf & outCurve, LUTu & outBeforeCCurveHistogram, ToneCurve & outToneCurve, ToneCurve & outToneCurve2,
|
LUTf & hlCurve, LUTf & shCurve,LUTf & outCurve, LUTu & outBeforeCCurveHistogram, ToneCurve & outToneCurve, ToneCurve & outToneCurve2,
|
||||||
@@ -348,7 +360,7 @@ class ToneCurve {
|
|||||||
virtual ~ToneCurve() {};
|
virtual ~ToneCurve() {};
|
||||||
|
|
||||||
void Reset();
|
void Reset();
|
||||||
void Set(Curve *pCurve);
|
void Set(Curve *pCurve, float gamma=0, float start=0, float slope=0, float mul=0, float add=0);
|
||||||
operator bool (void) const { return lutToneCurve; }
|
operator bool (void) const { return lutToneCurve; }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -86,8 +86,6 @@ class ImageSource : public InitialImage {
|
|||||||
|
|
||||||
virtual double getDefGain () { return 1.0; }
|
virtual double getDefGain () { return 1.0; }
|
||||||
|
|
||||||
virtual double getGamma () { return 0.0; }
|
|
||||||
|
|
||||||
virtual void getFullSize (int& w, int& h, int tr = TR_NONE) {}
|
virtual void getFullSize (int& w, int& h, int tr = TR_NONE) {}
|
||||||
virtual void getSize (int tran, PreviewProps pp, int& w, int& h) {}
|
virtual void getSize (int tran, PreviewProps pp, int& w, int& h) {}
|
||||||
virtual int getRotateDegree() const { return 0; }
|
virtual int getRotateDegree() const { return 0; }
|
||||||
|
|||||||
@@ -354,12 +354,10 @@ void ImProcCoordinator::updatePreviewImage (int todo, Crop* cropCall) {
|
|||||||
// if (hListener) oprevi->calcCroppedHistogram(params, scale, histCropped);
|
// if (hListener) oprevi->calcCroppedHistogram(params, scale, histCropped);
|
||||||
|
|
||||||
//complexCurve also calculated pre-curves histogram depending on crop
|
//complexCurve also calculated pre-curves histogram depending on crop
|
||||||
ipf.g = imgsrc->getGamma();
|
|
||||||
ipf.iGamma = true;
|
|
||||||
CurveFactory::complexCurve (params.toneCurve.expcomp, params.toneCurve.black/65535.0,
|
CurveFactory::complexCurve (params.toneCurve.expcomp, params.toneCurve.black/65535.0,
|
||||||
params.toneCurve.hlcompr, params.toneCurve.hlcomprthresh,
|
params.toneCurve.hlcompr, params.toneCurve.hlcomprthresh,
|
||||||
params.toneCurve.shcompr, params.toneCurve.brightness, params.toneCurve.contrast,
|
params.toneCurve.shcompr, params.toneCurve.brightness, params.toneCurve.contrast,
|
||||||
ipf.g, !ipf.iGamma, params.toneCurve.curveMode, params.toneCurve.curve, params.toneCurve.curveMode2, params.toneCurve.curve2,
|
params.toneCurve.curveMode, params.toneCurve.curve, params.toneCurve.curveMode2, params.toneCurve.curve2,
|
||||||
vhist16, histCropped, hltonecurve, shtonecurve, tonecurve, histToneCurve, customToneCurve1, customToneCurve2, scale==1 ? 1 : 1);
|
vhist16, histCropped, hltonecurve, shtonecurve, tonecurve, histToneCurve, customToneCurve1, customToneCurve2, scale==1 ? 1 : 1);
|
||||||
|
|
||||||
CurveFactory::RGBCurve (params.rgbCurves.rcurve, rCurve, scale==1 ? 1 : 1);
|
CurveFactory::RGBCurve (params.rgbCurves.rcurve, rCurve, scale==1 ? 1 : 1);
|
||||||
|
|||||||
@@ -2432,7 +2432,7 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, EditBuffer *e
|
|||||||
SHMap* shmap, int sat, LUTf & rCurve, LUTf & gCurve, LUTf & bCurve, float satLimit ,float satLimitOpacity, const ColorGradientCurve & ctColorCurve, const OpacityCurve & ctOpacityCurve, bool opautili, LUTf & clToningcurve,LUTf & cl2Toningcurve,
|
SHMap* shmap, int sat, LUTf & rCurve, LUTf & gCurve, LUTf & bCurve, float satLimit ,float satLimitOpacity, const ColorGradientCurve & ctColorCurve, const OpacityCurve & ctOpacityCurve, bool opautili, LUTf & clToningcurve,LUTf & cl2Toningcurve,
|
||||||
const ToneCurve & customToneCurve1, const ToneCurve & customToneCurve2, const ToneCurve & customToneCurvebw1,const ToneCurve & customToneCurvebw2,double &rrm, double &ggm, double &bbm, float &autor, float &autog, float &autob, double expcomp, int hlcompr, int hlcomprthresh, DCPProfile *dcpProf) {
|
const ToneCurve & customToneCurve1, const ToneCurve & customToneCurve2, const ToneCurve & customToneCurvebw1,const ToneCurve & customToneCurvebw2,double &rrm, double &ggm, double &bbm, float &autor, float &autog, float &autob, double expcomp, int hlcompr, int hlcomprthresh, DCPProfile *dcpProf) {
|
||||||
|
|
||||||
LUTf iGammaLUTf;
|
LUTf fGammaLUTf;
|
||||||
Imagefloat *tmpImage=NULL;
|
Imagefloat *tmpImage=NULL;
|
||||||
|
|
||||||
// NOTE: We're getting all 3 pointers here, but this function may not need them all, so one could optimize this
|
// NOTE: We're getting all 3 pointers here, but this function may not need them all, so one could optimize this
|
||||||
@@ -2688,20 +2688,11 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, EditBuffer *e
|
|||||||
}
|
}
|
||||||
bool hasgammabw = gammabwr!=1.f || gammabwg!=1.f || gammabwb!=1.f;
|
bool hasgammabw = gammabwr!=1.f || gammabwg!=1.f || gammabwb!=1.f;
|
||||||
|
|
||||||
//normalize gamma to sRGB
|
fGammaLUTf(65535);
|
||||||
double start = exp(g*log( -0.055 / ((1.0/g-1.0)*1.055 )));
|
|
||||||
double slope = 1.055 * pow (start, 1.0/g-1) - 0.055/start;
|
|
||||||
double mul = 1.055;
|
|
||||||
double add = 0.055;
|
|
||||||
|
|
||||||
if (iGamma && g > 1.) {
|
|
||||||
iGammaLUTf(65535);
|
|
||||||
#pragma omp parallel for
|
#pragma omp parallel for
|
||||||
for (int i=0; i<65536; i++) {
|
for (int i=0; i<65536; i++) {
|
||||||
iGammaLUTf[i] = float(CurveFactory::igamma (double(i)/65535., g, start, slope, mul, add)*65535.);
|
fGammaLUTf[i] = CurveFactory::gamma2 (float(i)/65535.f) * 65535.f;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (hasColorToning || blackwhite)
|
if (hasColorToning || blackwhite)
|
||||||
tmpImage = new Imagefloat(working->width,working->height);
|
tmpImage = new Imagefloat(working->width,working->height);
|
||||||
|
|
||||||
@@ -2887,9 +2878,9 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, EditBuffer *e
|
|||||||
if (editID == EUID_ToneCurve1) { // filling the pipette buffer
|
if (editID == EUID_ToneCurve1) { // filling the pipette buffer
|
||||||
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
||||||
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
||||||
editIFloatTmpR[ti*TS+tj] = CLIP(rtemp[ti*TS+tj]/65535.f);
|
editIFloatTmpR[ti*TS+tj] = CLIP(fGammaLUTf[rtemp[ti*TS+tj]]/65535.f);
|
||||||
editIFloatTmpG[ti*TS+tj] = CLIP(gtemp[ti*TS+tj]/65535.f);
|
editIFloatTmpG[ti*TS+tj] = CLIP(fGammaLUTf[gtemp[ti*TS+tj]]/65535.f);
|
||||||
editIFloatTmpB[ti*TS+tj] = CLIP(btemp[ti*TS+tj]/65535.f);
|
editIFloatTmpB[ti*TS+tj] = CLIP(fGammaLUTf[btemp[ti*TS+tj]]/65535.f);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2949,9 +2940,9 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, EditBuffer *e
|
|||||||
if (editID == EUID_ToneCurve2) { // filling the pipette buffer
|
if (editID == EUID_ToneCurve2) { // filling the pipette buffer
|
||||||
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
||||||
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
||||||
editIFloatTmpR[ti*TS+tj] = CLIP(rtemp[ti*TS+tj]/65535.f);
|
editIFloatTmpR[ti*TS+tj] = CLIP(fGammaLUTf[rtemp[ti*TS+tj]]/65535.f);
|
||||||
editIFloatTmpG[ti*TS+tj] = CLIP(gtemp[ti*TS+tj]/65535.f);
|
editIFloatTmpG[ti*TS+tj] = CLIP(fGammaLUTf[gtemp[ti*TS+tj]]/65535.f);
|
||||||
editIFloatTmpB[ti*TS+tj] = CLIP(btemp[ti*TS+tj]/65535.f);
|
editIFloatTmpB[ti*TS+tj] = CLIP(fGammaLUTf[btemp[ti*TS+tj]]/65535.f);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2999,35 +2990,24 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, EditBuffer *e
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (iGammaLUTf) {
|
|
||||||
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
|
||||||
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
|
||||||
// apply inverse gamma
|
|
||||||
rtemp[ti*TS+tj] = iGammaLUTf[ rtemp[ti*TS+tj] ];
|
|
||||||
gtemp[ti*TS+tj] = iGammaLUTf[ gtemp[ti*TS+tj] ];
|
|
||||||
btemp[ti*TS+tj] = iGammaLUTf[ btemp[ti*TS+tj] ];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (editID == EUID_RGB_R) {
|
if (editID == EUID_RGB_R) {
|
||||||
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
||||||
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
||||||
editWhateverTmp[ti*TS+tj] = rtemp[ti*TS+tj]/65536.f;
|
editWhateverTmp[ti*TS+tj] = fGammaLUTf[rtemp[ti*TS+tj]]/65536.f;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (editID == EUID_RGB_G) {
|
else if (editID == EUID_RGB_G) {
|
||||||
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
||||||
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
||||||
editWhateverTmp[ti*TS+tj] = gtemp[ti*TS+tj]/65536.f;
|
editWhateverTmp[ti*TS+tj] = fGammaLUTf[gtemp[ti*TS+tj]]/65536.f;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (editID == EUID_RGB_B) {
|
else if (editID == EUID_RGB_B) {
|
||||||
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
||||||
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
||||||
editWhateverTmp[ti*TS+tj] = btemp[ti*TS+tj]/65536.f;
|
editWhateverTmp[ti*TS+tj] = fGammaLUTf[btemp[ti*TS+tj]]/65536.f;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -3379,9 +3359,9 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, EditBuffer *e
|
|||||||
if (editID == EUID_BlackWhiteBeforeCurve) {
|
if (editID == EUID_BlackWhiteBeforeCurve) {
|
||||||
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
for (int i=istart,ti=0; i<tH; i++,ti++) {
|
||||||
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
for (int j=jstart,tj=0; j<tW; j++,tj++) {
|
||||||
editIFloatTmpR[ti*TS+tj] = CLIP(rtemp[ti*TS+tj]/65535.f);
|
editIFloatTmpR[ti*TS+tj] = CLIP(fGammaLUTf[rtemp[ti*TS+tj]]/65535.f);
|
||||||
editIFloatTmpG[ti*TS+tj] = CLIP(gtemp[ti*TS+tj]/65535.f);
|
editIFloatTmpG[ti*TS+tj] = CLIP(fGammaLUTf[gtemp[ti*TS+tj]]/65535.f);
|
||||||
editIFloatTmpB[ti*TS+tj] = CLIP(btemp[ti*TS+tj]/65535.f);
|
editIFloatTmpB[ti*TS+tj] = CLIP(fGammaLUTf[btemp[ti*TS+tj]]/65535.f);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -3748,7 +3728,7 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, EditBuffer *e
|
|||||||
#endif
|
#endif
|
||||||
for (int i=0; i<tH; i++) {
|
for (int i=0; i<tH; i++) {
|
||||||
for (int j=0; j<tW; j++) {
|
for (int j=0; j<tW; j++) {
|
||||||
editWhatever->v(i,j) = CLIP(tmpImage->r(i,j)/65535.f); // assuming that r=g=b
|
editWhatever->v(i,j) = CLIP(fGammaLUTf[tmpImage->r(i,j)]/65535.f); // assuming that r=g=b
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -5732,7 +5712,7 @@ fclose(f);*/
|
|||||||
|
|
||||||
double gavg = 0.;
|
double gavg = 0.;
|
||||||
for (int i=0; i<65536>>histcompr; i++)
|
for (int i=0; i<65536>>histcompr; i++)
|
||||||
gavg += histogram[i] * CurveFactory::gamma2((int)(corr*(i<<histcompr)<65535 ? corr*(i<<histcompr) : 65535)) / sum;
|
gavg += histogram[i] * CurveFactory::gamma2((float)(corr*(i<<histcompr)<65535 ? corr*(i<<histcompr) : 65535)) / sum;
|
||||||
if (black < gavg) {
|
if (black < gavg) {
|
||||||
int maxwhiteclip = (gavg - black) * 4 / 3 + black; // dont let whiteclip be such large that the histogram average goes above 3/4
|
int maxwhiteclip = (gavg - black) * 4 / 3 + black; // dont let whiteclip be such large that the histogram average goes above 3/4
|
||||||
if (whiteclipg < maxwhiteclip)
|
if (whiteclipg < maxwhiteclip)
|
||||||
|
|||||||
@@ -185,8 +185,6 @@ class ImProcFunctions {
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
bool iGamma; // true if inverse gamma has to be applied in rgbProc
|
|
||||||
double g;
|
|
||||||
static LUTf cachef;
|
static LUTf cachef;
|
||||||
double lumimul[3];
|
double lumimul[3];
|
||||||
// float chau;
|
// float chau;
|
||||||
@@ -211,7 +209,7 @@ class ImProcFunctions {
|
|||||||
static void cleanupCache ();
|
static void cleanupCache ();
|
||||||
|
|
||||||
ImProcFunctions (const ProcParams* iparams, bool imultiThread=true)
|
ImProcFunctions (const ProcParams* iparams, bool imultiThread=true)
|
||||||
: monitorTransform(NULL), params(iparams), scale(1), multiThread(imultiThread), iGamma(true), g(0.0) {}
|
: monitorTransform(NULL), params(iparams), scale(1), multiThread(imultiThread) {}
|
||||||
~ImProcFunctions ();
|
~ImProcFunctions ();
|
||||||
|
|
||||||
void setScale (double iscale);
|
void setScale (double iscale);
|
||||||
|
|||||||
@@ -162,8 +162,6 @@ class RawImageSource : public ImageSource {
|
|||||||
|
|
||||||
double getDefGain () { return defGain; }
|
double getDefGain () { return defGain; }
|
||||||
|
|
||||||
double getGamma () { return Color::sRGBGamma; }
|
|
||||||
|
|
||||||
void getFullSize (int& w, int& h, int tr = TR_NONE);
|
void getFullSize (int& w, int& h, int tr = TR_NONE);
|
||||||
void getSize (int tran, PreviewProps pp, int& w, int& h);
|
void getSize (int tran, PreviewProps pp, int& w, int& h);
|
||||||
int getRotateDegree() const { return ri->get_rotateDegree(); }
|
int getRotateDegree() const { return ri->get_rotateDegree(); }
|
||||||
|
|||||||
@@ -910,10 +910,8 @@ IImage8* Thumbnail::processImage (const procparams::ProcParams& params, int rhei
|
|||||||
ToneCurve customToneCurvebw1;
|
ToneCurve customToneCurvebw1;
|
||||||
ToneCurve customToneCurvebw2;
|
ToneCurve customToneCurvebw2;
|
||||||
|
|
||||||
ipf.g = gamma;
|
|
||||||
ipf.iGamma = true;
|
|
||||||
CurveFactory::complexCurve (expcomp, black/65535.0, hlcompr, hlcomprthresh,
|
CurveFactory::complexCurve (expcomp, black/65535.0, hlcompr, hlcomprthresh,
|
||||||
params.toneCurve.shcompr, bright, contr, ipf.g, !ipf.iGamma,
|
params.toneCurve.shcompr, bright, contr,
|
||||||
params.toneCurve.curveMode, params.toneCurve.curve,
|
params.toneCurve.curveMode, params.toneCurve.curve,
|
||||||
params.toneCurve.curveMode2, params.toneCurve.curve2,
|
params.toneCurve.curveMode2, params.toneCurve.curve2,
|
||||||
hist16, dummy, curve1, curve2, curve, dummy, customToneCurve1, customToneCurve2, 16);
|
hist16, dummy, curve1, curve2, curve, dummy, customToneCurve1, customToneCurve2, 16);
|
||||||
|
|||||||
@@ -606,9 +606,7 @@ IImage16* processImage (ProcessingJob* pjob, int& errorCode, ProgressListener* p
|
|||||||
ToneCurve customToneCurvebw2;
|
ToneCurve customToneCurvebw2;
|
||||||
//if(params.blackwhite.enabled) params.toneCurve.hrenabled=false;
|
//if(params.blackwhite.enabled) params.toneCurve.hrenabled=false;
|
||||||
|
|
||||||
ipf.g = imgsrc->getGamma();
|
CurveFactory::complexCurve (expcomp, black/65535.0, hlcompr, hlcomprthresh, params.toneCurve.shcompr, bright, contr,
|
||||||
ipf.iGamma = true;
|
|
||||||
CurveFactory::complexCurve (expcomp, black/65535.0, hlcompr, hlcomprthresh, params.toneCurve.shcompr, bright, contr, ipf.g, !ipf.iGamma,
|
|
||||||
params.toneCurve.curveMode, params.toneCurve.curve, params.toneCurve.curveMode2, params.toneCurve.curve2,
|
params.toneCurve.curveMode, params.toneCurve.curve, params.toneCurve.curveMode2, params.toneCurve.curve2,
|
||||||
hist16, dummy, curve1, curve2, curve, dummy, customToneCurve1, customToneCurve2 );
|
hist16, dummy, curve1, curve2, curve, dummy, customToneCurve1, customToneCurve2 );
|
||||||
|
|
||||||
|
|||||||
@@ -53,7 +53,6 @@ class StdImageSource : public ImageSource {
|
|||||||
void getAutoExpHistogram (LUTu &histogram, int& histcompr);
|
void getAutoExpHistogram (LUTu &histogram, int& histcompr);
|
||||||
|
|
||||||
double getDefGain () { return 0.0; }
|
double getDefGain () { return 0.0; }
|
||||||
double getGamma () { return 0.0; }
|
|
||||||
|
|
||||||
void getFullSize (int& w, int& h, int tr = TR_NONE);
|
void getFullSize (int& w, int& h, int tr = TR_NONE);
|
||||||
void getSize (int tran, PreviewProps pp, int& w, int& h);
|
void getSize (int tran, PreviewProps pp, int& w, int& h);
|
||||||
|
|||||||
Reference in New Issue
Block a user