Raw white point correction for LUT based profiles (DCP only)

see issue 1466
This commit is contained in:
Oliver Duis
2012-07-07 23:08:04 +02:00
parent 00c280a80e
commit 5bd13c22a4
5 changed files with 25 additions and 15 deletions

View File

@@ -205,7 +205,7 @@ DCPLightType DCPProfile::GetLightType(short iLightSource) const {
return Daylight; return Daylight;
} }
void DCPProfile::Apply(Imagefloat *pImg, DCPLightType preferredProfile, Glib::ustring workingSpace) const { void DCPProfile::Apply(Imagefloat *pImg, DCPLightType preferredProfile, Glib::ustring workingSpace, float rawWhiteFac) const {
TMatrix mWork = iccStore->workingSpaceInverseMatrix (workingSpace); TMatrix mWork = iccStore->workingSpaceInverseMatrix (workingSpace);
double mXYZCAM[3][3]; double mXYZCAM[3][3];
@@ -258,10 +258,12 @@ void DCPProfile::Apply(Imagefloat *pImg, DCPLightType preferredProfile, Glib::us
int hueStep = iSatDivisions; int hueStep = iSatDivisions;
int valStep = iHueDivisions * hueStep; int valStep = iHueDivisions * hueStep;
bool useRawWhite=fabs(rawWhiteFac)>0.001;
// Convert to prophoto and apply LUT // Convert to prophoto and apply LUT
#pragma omp parallel for #pragma omp parallel for
for (int y=0; y<pImg->height; y++) { for (int y=0; y<pImg->height; y++) {
float newr, newg, newb, h,s,v; float newr, newg, newb, h,s,v,hs,ss,vs;
for (int x=0; x<pImg->width; x++) { for (int x=0; x<pImg->width; x++) {
newr = m2ProPhoto[0][0]*pImg->r[y][x] + m2ProPhoto[0][1]*pImg->g[y][x] + m2ProPhoto[0][2]*pImg->b[y][x]; newr = m2ProPhoto[0][0]*pImg->r[y][x] + m2ProPhoto[0][1]*pImg->g[y][x] + m2ProPhoto[0][2]*pImg->b[y][x];
newg = m2ProPhoto[1][0]*pImg->r[y][x] + m2ProPhoto[1][1]*pImg->g[y][x] + m2ProPhoto[1][2]*pImg->b[y][x]; newg = m2ProPhoto[1][0]*pImg->r[y][x] + m2ProPhoto[1][1]*pImg->g[y][x] + m2ProPhoto[1][2]*pImg->b[y][x];
@@ -272,13 +274,21 @@ void DCPProfile::Apply(Imagefloat *pImg, DCPLightType preferredProfile, Glib::us
ImProcFunctions::rgb2hsv(newr, newg, newb, h , s, v); ImProcFunctions::rgb2hsv(newr, newg, newb, h , s, v);
h*=6.f; // RT calculates in [0,1] h*=6.f; // RT calculates in [0,1]
if (useRawWhite) {
// Retro-calculate what the point was like before RAW white came in
ImProcFunctions::rgb2hsv(newr/rawWhiteFac, newg/rawWhiteFac, newb/rawWhiteFac, hs, ss, vs);
hs*=6.f; // RT calculates in [0,1]
} else {
hs=h; ss=s; vs=v;
}
// Apply the HueSatMap. Ported from Adobes reference implementation // Apply the HueSatMap. Ported from Adobes reference implementation
float hueShift, satScale, valScale; float hueShift, satScale, valScale;
if (iValDivisions < 2) // Optimize most common case of "2.5D" table. if (iValDivisions < 2) // Optimize most common case of "2.5D" table.
{ {
float hScaled = h * hScale; float hScaled = hs * hScale;
float sScaled = s * sScale; float sScaled = ss * sScale;
int hIndex0 = max((int)hScaled, 0); int hIndex0 = max((int)hScaled, 0);
int sIndex0 = max(min((int)sScaled,maxSatIndex0),0); int sIndex0 = max(min((int)sScaled,maxSatIndex0),0);
@@ -329,9 +339,9 @@ void DCPProfile::Apply(Imagefloat *pImg, DCPLightType preferredProfile, Glib::us
} else { } else {
float hScaled = h * hScale; float hScaled = hs * hScale;
float sScaled = s * sScale; float sScaled = ss * sScale;
float vScaled = v * vScale; float vScaled = vs * vScale;
int hIndex0 = (int) hScaled; int hIndex0 = (int) hScaled;
int sIndex0 = max(min((int)sScaled,maxSatIndex0),0); int sIndex0 = max(min((int)sScaled,maxSatIndex0),0);

View File

@@ -57,7 +57,7 @@ namespace rtengine {
DCPProfile(Glib::ustring fname); DCPProfile(Glib::ustring fname);
~DCPProfile(); ~DCPProfile();
void Apply(Imagefloat *pImg, DCPLightType preferredProfile, Glib::ustring workingSpace) const; void Apply(Imagefloat *pImg, DCPLightType preferredProfile, Glib::ustring workingSpace, float rawWhiteFac=1) const;
void Apply(Image16 *pImg, DCPLightType preferredProfile, Glib::ustring workingSpace) const; void Apply(Image16 *pImg, DCPLightType preferredProfile, Glib::ustring workingSpace) const;
}; };

View File

@@ -427,7 +427,7 @@ void RawImageSource::getImage (ColorTemp ctemp, int tran, Imagefloat* image, Pre
// Color correction (only when running on full resolution) // Color correction (only when running on full resolution)
if (ri->isBayer() && pp.skip==1) if (ri->isBayer() && pp.skip==1)
processFalseColorCorrection (image, raw.ccSteps); processFalseColorCorrection (image, raw.ccSteps);
colorSpaceConversion (image, cmp, embProfile, camProfile, xyz_cam, (static_cast<const ImageData*>(getMetaData()))->getCamera(), defGain); colorSpaceConversion (image, cmp, raw, embProfile, camProfile, xyz_cam, (static_cast<const ImageData*>(getMetaData()))->getCamera());
} }
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -1690,7 +1690,7 @@ void RawImageSource::getProfilePreprocParams(cmsHPROFILE in, float& gammaFac, fl
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
// Converts raw image including ICC input profile to working space - floating point version // Converts raw image including ICC input profile to working space - floating point version
void RawImageSource::colorSpaceConversion (Imagefloat* im, ColorManagementParams cmp, cmsHPROFILE embedded, cmsHPROFILE camprofile, double camMatrix[3][3], std::string camName, double& defgain) { void RawImageSource::colorSpaceConversion (Imagefloat* im, ColorManagementParams cmp, RAWParams raw, cmsHPROFILE embedded, cmsHPROFILE camprofile, double camMatrix[3][3], std::string camName) {
//MyTime t1, t2, t3; //MyTime t1, t2, t3;
//t1.set (); //t1.set ();
@@ -1700,7 +1700,7 @@ void RawImageSource::colorSpaceConversion (Imagefloat* im, ColorManagementParams
if (!findInputProfile(cmp.input, embedded, camName, &dcpProf, in)) return; if (!findInputProfile(cmp.input, embedded, camName, &dcpProf, in)) return;
if (dcpProf!=NULL) { if (dcpProf!=NULL) {
dcpProf->Apply(im, (DCPLightType)cmp.preferredProfile, cmp.working); dcpProf->Apply(im, (DCPLightType)cmp.preferredProfile, cmp.working, (float)raw.expos);
} else { } else {
// Calculate matrix for direct conversion raw>working space // Calculate matrix for direct conversion raw>working space
TMatrix work = iccStore->workingSpaceInverseMatrix (cmp.working); TMatrix work = iccStore->workingSpaceInverseMatrix (cmp.working);
@@ -1916,7 +1916,7 @@ void RawImageSource::colorSpaceConversion (Imagefloat* im, ColorManagementParams
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
// Converts raw image including ICC input profile to working space - 16bit int version // Converts raw image including ICC input profile to working space - 16bit int version
void RawImageSource::colorSpaceConversion16 (Image16* im, ColorManagementParams cmp, cmsHPROFILE embedded, cmsHPROFILE camprofile, double camMatrix[3][3], std::string camName, double& defgain) { void RawImageSource::colorSpaceConversion16 (Image16* im, ColorManagementParams cmp, cmsHPROFILE embedded, cmsHPROFILE camprofile, double camMatrix[3][3], std::string camName) {
cmsHPROFILE in; cmsHPROFILE in;
DCPProfile *dcpProf; DCPProfile *dcpProf;

View File

@@ -167,8 +167,8 @@ class RawImageSource : public ImageSource {
void getAutoExpHistogram (LUTu & histogram, int& histcompr); void getAutoExpHistogram (LUTu & histogram, int& histcompr);
void getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LUTu & histBlueRaw); void getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LUTu & histBlueRaw);
static void colorSpaceConversion16 (Image16* im, ColorManagementParams cmp, cmsHPROFILE embedded, cmsHPROFILE camprofile, double cam[3][3], std::string camName, double& defgain); static void colorSpaceConversion16 (Image16* im, ColorManagementParams cmp, cmsHPROFILE embedded, cmsHPROFILE camprofile, double cam[3][3], std::string camName);
static void colorSpaceConversion (Imagefloat* im, ColorManagementParams cmp, cmsHPROFILE embedded, cmsHPROFILE camprofile, double cam[3][3], std::string camName, double& defgain); static void colorSpaceConversion (Imagefloat* im, ColorManagementParams cmp, RAWParams raw, cmsHPROFILE embedded, cmsHPROFILE camprofile, double cam[3][3], std::string camName);
static void inverse33 (const double (*coeff)[3], double (*icoeff)[3]); static void inverse33 (const double (*coeff)[3], double (*icoeff)[3]);
void boxblur2(float** src, float** dst, int H, int W, int box ); void boxblur2(float** src, float** dst, int H, int W, int box );

View File

@@ -680,7 +680,7 @@ IImage8* Thumbnail::processImage (const procparams::ProcParams& params, int rhei
*/ */
// perform color space transformation // perform color space transformation
if (isRaw) if (isRaw)
RawImageSource::colorSpaceConversion16 (resImg, params.icm, embProfile, camProfile, cam2xyz, camName, logDefGain ); RawImageSource::colorSpaceConversion16 (resImg, params.icm, embProfile, camProfile, cam2xyz, camName );
else else
StdImageSource::colorSpaceConversion16 (resImg, params.icm, embProfile); StdImageSource::colorSpaceConversion16 (resImg, params.icm, embProfile);