Refactor DCPProfile::DCPProfile()

- Rename members
- Styling
- C++11

Still to come:
- All the rest of DCPProfile
This commit is contained in:
Floessie 2016-06-05 21:30:51 +02:00
parent e0ca8ecdff
commit 2abd641c06
12 changed files with 358 additions and 297 deletions

View File

@ -601,67 +601,86 @@ double calibrationIlluminantToTemperature(int light)
}
DCPProfile::DCPProfile(const Glib::ustring &fname)
DCPProfile::DCPProfile(const Glib::ustring& filename) :
has_color_matrix_1(false),
has_color_matrix_2(false),
has_forward_matrix_1(false),
has_forward_matrix_2(false),
has_tone_curve(false),
has_baseline_exposure_offset(false),
will_interpolate(false),
baseline_exposure_offset(0.0),
deltas_1(nullptr),
deltas_2(nullptr),
look_table(nullptr)
{
const int TIFFFloatSize = 4;
const int TagColorMatrix1 = 50721, TagColorMatrix2 = 50722, TagProfileHueSatMapDims = 50937;
const int TagForwardMatrix1 = 50964, TagForwardMatrix2 = 50965;
const int TagProfileHueSatMapData1 = 50938, TagProfileHueSatMapData2 = 50939;
const int TagCalibrationIlluminant1 = 50778, TagCalibrationIlluminant2 = 50779;
const int TagProfileLookTableData = 50982, TagProfileLookTableDims = 50981; // ProfileLookup is the low quality variant
const int TagProfileHueSatMapEncoding = 51107, TagProfileLookTableEncoding = 51108;
const int TagProfileToneCurve = 50940, TagBaselineExposureOffset = 51109;
const int TagProfileCopyright = 50942;
constexpr int tiff_float_size = 4;
aDeltas1 = aDeltas2 = aLookTable = nullptr;
enum class TagKey : int {
COLOR_MATRIX_1 = 50721,
COLOR_MATRIX_2 = 50722,
PROFILE_HUE_SAT_MAP_DIMS = 50937,
PROFILE_HUE_SAT_MAP_DATA_1 = 50938,
PROFILE_HUE_SAT_MAP_DATA_2 = 50939,
PROFILE_TONE_CURVE = 50940,
PROFILE_TONE_COPYRIGHT = 50942,
CALIBRATION_ILLUMINANT_1 = 50778,
CALIBRATION_ILLUMINANT_2 = 50779,
FORWARD_MATRIX_1 = 50964,
FORWARD_MATRIX_2 = 50965,
PROFILE_LOOK_TABLE_DIMS = 50981, // ProfileLookup is the low quality variant
PROFILE_LOOK_TABLE_DATA = 50982,
PROFILE_HUE_SAT_MAP_ENCODING = 51107,
PROFILE_LOOK_TABLE_ENCODING = 51108,
BASELINE_EXPOSURE_OFFSET = 51109
};
FILE *pFile = g_fopen(fname.c_str (), "rb");
FILE* const file = g_fopen(filename.c_str(), "rb");
TagDirectory *tagDir = ExifManager::parseTIFF(pFile, false);
std::unique_ptr<TagDirectory> tagDir(ExifManager::parseTIFF(file, false));
Tag* tag = tagDir->getTag(TagCalibrationIlluminant1);
iLightSource1 = (tag != nullptr ? tag->toInt(0, rtexif::SHORT) : -1);
tag = tagDir->getTag(TagCalibrationIlluminant2);
iLightSource2 = (tag != nullptr ? tag->toInt(0, rtexif::SHORT) : -1);
temperature1 = calibrationIlluminantToTemperature(iLightSource1);
temperature2 = calibrationIlluminantToTemperature(iLightSource2);
Tag* tag = tagDir->getTag(toUnderlying(TagKey::CALIBRATION_ILLUMINANT_1));
light_source_1 =
tag
? tag->toInt(0, rtexif::SHORT)
: -1;
tag = tagDir->getTag(toUnderlying(TagKey::CALIBRATION_ILLUMINANT_2));
light_source_2 =
tag
? tag->toInt(0, rtexif::SHORT)
: -1;
temperature_1 = calibrationIlluminantToTemperature(light_source_1);
temperature_2 = calibrationIlluminantToTemperature(light_source_2);
bool hasSecondHueSat = tagDir->getTag(TagProfileHueSatMapData2) != nullptr; // some profiles have two matrices, but just one huesat
const bool has_second_hue_sat = tagDir->getTag(toUnderlying(TagKey::PROFILE_HUE_SAT_MAP_DATA_2)); // Some profiles have two matrices, but just one huesat
// Fetch Forward Matrices, if any
hasForwardMatrix1 = false;
hasForwardMatrix2 = false;
hasColorMatrix1 = false;
hasColorMatrix2 = false;
hasToneCurve = false;
hasBaselineExposureOffset = false;
baselineExposureOffset = 0;
tag = tagDir->getTag(TagForwardMatrix1);
tag = tagDir->getTag(toUnderlying(TagKey::FORWARD_MATRIX_1));
if (tag) {
hasForwardMatrix1 = true;
has_forward_matrix_1 = true;
for (int row = 0; row < 3; row++) {
for (int col = 0; col < 3; col++) {
mForwardMatrix1[row][col] = (float)tag->toDouble((col + row * 3) * 8);
for (int row = 0; row < 3; ++row) {
for (int col = 0; col < 3; ++col) {
forward_matrix_1[row][col] = tag->toDouble((col + row * 3) * 8);
}
}
}
tag = tagDir->getTag(TagForwardMatrix2);
tag = tagDir->getTag(toUnderlying(TagKey::FORWARD_MATRIX_2));
if (tag) {
hasForwardMatrix2 = true;
has_forward_matrix_2 = true;
for (int row = 0; row < 3; row++) {
for (int col = 0; col < 3; col++) {
mForwardMatrix2[row][col] = (float)tag->toDouble((col + row * 3) * 8);
for (int row = 0; row < 3; ++row) {
for (int col = 0; col < 3; ++col) {
forward_matrix_2[row][col] = tag->toDouble((col + row * 3) * 8);
}
}
}
// Color Matrix (1 is always there)
tag = tagDir->getTag(TagColorMatrix1);
// Color Matrix (one is always there)
tag = tagDir->getTag(toUnderlying(TagKey::COLOR_MATRIX_1));
if (!tag) {
// FIXME: better error handling
@ -669,223 +688,235 @@ DCPProfile::DCPProfile(const Glib::ustring &fname)
abort();
}
hasColorMatrix1 = true;
has_color_matrix_1 = true;
for (int row = 0; row < 3; row++) {
for (int col = 0; col < 3; col++) {
mColorMatrix1[row][col] = (float)tag->toDouble((col + row * 3) * 8);
for (int row = 0; row < 3; ++row) {
for (int col = 0; col < 3; ++col) {
color_matrix_1[row][col] = tag->toDouble((col + row * 3) * 8);
}
}
tag = tagDir->getTag(TagProfileLookTableDims);
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_LOOK_TABLE_DIMS));
if (tag != nullptr) {
LookInfo.iHueDivisions = tag->toInt(0);
LookInfo.iSatDivisions = tag->toInt(4);
LookInfo.iValDivisions = tag->toInt(8);
if (tag) {
look_info.hue_divisions = tag->toInt(0);
look_info.sat_divisions = tag->toInt(4);
look_info.val_divisions = tag->toInt(8);
tag = tagDir->getTag(TagProfileLookTableEncoding);
LookInfo.sRGBGamma = tag != nullptr && tag->toInt(0);
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_LOOK_TABLE_ENCODING));
look_info.srgb_gamma = tag && tag->toInt(0);
tag = tagDir->getTag(TagProfileLookTableData);
LookInfo.iArrayCount = tag->getCount() / 3;
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_LOOK_TABLE_DATA));
look_info.array_count = tag->getCount() / 3;
aLookTable = new HSBModify[LookInfo.iArrayCount];
look_table = new HSBModify[look_info.array_count];
for (int i = 0; i < LookInfo.iArrayCount; i++) {
aLookTable[i].fHueShift = tag->toDouble((i * 3) * TIFFFloatSize);
aLookTable[i].fSatScale = tag->toDouble((i * 3 + 1) * TIFFFloatSize);
aLookTable[i].fValScale = tag->toDouble((i * 3 + 2) * TIFFFloatSize);
for (int i = 0; i < look_info.array_count; i++) {
look_table[i].hue_shift = tag->toDouble((i * 3) * tiff_float_size);
look_table[i].sat_scale = tag->toDouble((i * 3 + 1) * tiff_float_size);
look_table[i].val_scale = tag->toDouble((i * 3 + 2) * tiff_float_size);
}
// precalculated constants for table application
LookInfo.pc.hScale = (LookInfo.iHueDivisions < 2) ? 0.0f : (LookInfo.iHueDivisions * (1.0f / 6.0f));
LookInfo.pc.sScale = (float) (LookInfo.iSatDivisions - 1);
LookInfo.pc.vScale = (float) (LookInfo.iValDivisions - 1);
LookInfo.pc.maxHueIndex0 = LookInfo.iHueDivisions - 1;
LookInfo.pc.maxSatIndex0 = LookInfo.iSatDivisions - 2;
LookInfo.pc.maxValIndex0 = LookInfo.iValDivisions - 2;
LookInfo.pc.hueStep = LookInfo.iSatDivisions;
LookInfo.pc.valStep = LookInfo.iHueDivisions * LookInfo.pc.hueStep;
// Precalculated constants for table application
look_info.pc.h_scale =
look_info.hue_divisions < 2
? 0.0f
: static_cast<float>(look_info.hue_divisions) / 6.0f;
look_info.pc.s_scale = look_info.sat_divisions - 1;
look_info.pc.v_scale = look_info.val_divisions - 1;
look_info.pc.maxHueIndex0 = look_info.hue_divisions - 1;
look_info.pc.maxSatIndex0 = look_info.sat_divisions - 2;
look_info.pc.maxValIndex0 = look_info.val_divisions - 2;
look_info.pc.hueStep = look_info.sat_divisions;
look_info.pc.valStep = look_info.hue_divisions * look_info.pc.hueStep;
}
tag = tagDir->getTag(TagProfileHueSatMapDims);
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_HUE_SAT_MAP_DIMS));
if (tag != nullptr) {
DeltaInfo.iHueDivisions = tag->toInt(0);
DeltaInfo.iSatDivisions = tag->toInt(4);
DeltaInfo.iValDivisions = tag->toInt(8);
if (tag) {
delta_info.hue_divisions = tag->toInt(0);
delta_info.sat_divisions = tag->toInt(4);
delta_info.val_divisions = tag->toInt(8);
tag = tagDir->getTag(TagProfileHueSatMapEncoding);
DeltaInfo.sRGBGamma = tag != nullptr && tag->toInt(0);
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_HUE_SAT_MAP_ENCODING));
delta_info.srgb_gamma = tag && tag->toInt(0);
tag = tagDir->getTag(TagProfileHueSatMapData1);
DeltaInfo.iArrayCount = tag->getCount() / 3;
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_HUE_SAT_MAP_DATA_1));
delta_info.array_count = tag->getCount() / 3;
aDeltas1 = new HSBModify[DeltaInfo.iArrayCount];
deltas_1 = new HSBModify[delta_info.array_count];
for (int i = 0; i < DeltaInfo.iArrayCount; i++) {
aDeltas1[i].fHueShift = tag->toDouble((i * 3) * TIFFFloatSize);
aDeltas1[i].fSatScale = tag->toDouble((i * 3 + 1) * TIFFFloatSize);
aDeltas1[i].fValScale = tag->toDouble((i * 3 + 2) * TIFFFloatSize);
for (int i = 0; i < delta_info.array_count; ++i) {
deltas_1[i].hue_shift = tag->toDouble((i * 3) * tiff_float_size);
deltas_1[i].sat_scale = tag->toDouble((i * 3 + 1) * tiff_float_size);
deltas_1[i].val_scale = tag->toDouble((i * 3 + 2) * tiff_float_size);
}
DeltaInfo.pc.hScale = (DeltaInfo.iHueDivisions < 2) ? 0.0f : (DeltaInfo.iHueDivisions * (1.0f / 6.0f));
DeltaInfo.pc.sScale = (float) (DeltaInfo.iSatDivisions - 1);
DeltaInfo.pc.vScale = (float) (DeltaInfo.iValDivisions - 1);
DeltaInfo.pc.maxHueIndex0 = DeltaInfo.iHueDivisions - 1;
DeltaInfo.pc.maxSatIndex0 = DeltaInfo.iSatDivisions - 2;
DeltaInfo.pc.maxValIndex0 = DeltaInfo.iValDivisions - 2;
DeltaInfo.pc.hueStep = DeltaInfo.iSatDivisions;
DeltaInfo.pc.valStep = DeltaInfo.iHueDivisions * DeltaInfo.pc.hueStep;
delta_info.pc.h_scale =
delta_info.hue_divisions < 2
? 0.0f
: static_cast<float>(delta_info.hue_divisions) / 6.0f;
delta_info.pc.s_scale = delta_info.sat_divisions - 1;
delta_info.pc.v_scale = delta_info.val_divisions - 1;
delta_info.pc.maxHueIndex0 = delta_info.hue_divisions - 1;
delta_info.pc.maxSatIndex0 = delta_info.sat_divisions - 2;
delta_info.pc.maxValIndex0 = delta_info.val_divisions - 2;
delta_info.pc.hueStep = delta_info.sat_divisions;
delta_info.pc.valStep = delta_info.hue_divisions * delta_info.pc.hueStep;
}
if (iLightSource2 != -1) {
if (light_source_2 != -1) {
// Second matrix
tag = tagDir->getTag(TagColorMatrix2);
hasColorMatrix2 = true;
has_color_matrix_2 = true;
for (int row = 0; row < 3; row++) {
for (int col = 0; col < 3; col++) {
mColorMatrix2[row][col] = (tag != nullptr ? (float)tag->toDouble((col + row * 3) * 8) : mColorMatrix1[row][col]);
tag = tagDir->getTag(toUnderlying(TagKey::COLOR_MATRIX_2));
for (int row = 0; row < 3; ++row) {
for (int col = 0; col < 3; ++col) {
color_matrix_2[row][col] =
tag
? tag->toDouble((col + row * 3) * 8)
: color_matrix_1[row][col];
}
}
// Second huesatmap
if (hasSecondHueSat) {
aDeltas2 = new HSBModify[DeltaInfo.iArrayCount];
if (has_second_hue_sat) {
deltas_2 = new HSBModify[delta_info.array_count];
// Saturation maps. Need to be unwinded.
tag = tagDir->getTag(TagProfileHueSatMapData2);
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_HUE_SAT_MAP_DATA_2));
for (int i = 0; i < DeltaInfo.iArrayCount; i++) {
aDeltas2[i].fHueShift = tag->toDouble((i * 3) * TIFFFloatSize);
aDeltas2[i].fSatScale = tag->toDouble((i * 3 + 1) * TIFFFloatSize);
aDeltas2[i].fValScale = tag->toDouble((i * 3 + 2) * TIFFFloatSize);
for (int i = 0; i < delta_info.array_count; ++i) {
deltas_2[i].hue_shift = tag->toDouble((i * 3) * tiff_float_size);
deltas_2[i].sat_scale = tag->toDouble((i * 3 + 1) * tiff_float_size);
deltas_2[i].val_scale = tag->toDouble((i * 3 + 2) * tiff_float_size);
}
}
}
tag = tagDir->getTag(TagBaselineExposureOffset);
tag = tagDir->getTag(toUnderlying(TagKey::BASELINE_EXPOSURE_OFFSET));
if (tag) {
hasBaselineExposureOffset = true;
baselineExposureOffset = tag->toDouble();
has_baseline_exposure_offset = true;
baseline_exposure_offset = tag->toDouble();
}
// Read tone curve points, if any, but disable to RTs own profiles
tag = tagDir->getTag(TagProfileToneCurve);
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_TONE_CURVE));
if (tag != nullptr) {
std::vector<double> cPoints;
cPoints.push_back(double(DCT_Spline)); // The first value is the curve type
if (tag) {
std::vector<double> curve_points = {
static_cast<double>(DCT_Spline) // The first value is the curve type
};
// push back each X/Y coordinates in a loop
// Push back each X/Y coordinates in a loop
bool curve_is_linear = true;
for (int i = 0; i < tag->getCount(); i += 2) {
double x = tag->toDouble((i + 0) * TIFFFloatSize);
double y = tag->toDouble((i + 1) * TIFFFloatSize);
const double x = tag->toDouble((i + 0) * tiff_float_size);
const double y = tag->toDouble((i + 1) * tiff_float_size);
if (x != y) {
curve_is_linear = false;
}
cPoints.push_back( x );
cPoints.push_back( y );
curve_points.push_back(x);
curve_points.push_back(y);
}
if (!curve_is_linear) {
// Create the curve
DiagonalCurve rawCurve(cPoints, CURVES_MIN_POLY_POINTS);
toneCurve.Set(rawCurve);
hasToneCurve = true;
has_tone_curve = true;
tone_curve.Set(DiagonalCurve(curve_points, CURVES_MIN_POLY_POINTS));
}
} else if (tag == nullptr) {
tag = tagDir->getTag(TagProfileCopyright);
} else {
tag = tagDir->getTag(toUnderlying(TagKey::PROFILE_TONE_COPYRIGHT));
if (tag != nullptr && tag->valueToString().find("Adobe Systems") != std::string::npos) {
// an Adobe profile without tone curve is expected to have the Adobe Default Curve, we add that
std::vector<double> cPoints;
cPoints.push_back(double(DCT_Spline));
const size_t tc_len = sizeof(adobe_camera_raw_default_curve) / sizeof(adobe_camera_raw_default_curve[0]);
if (tag && tag->valueToString().find("Adobe Systems") != std::string::npos) {
// An Adobe profile without tone curve is expected to have the Adobe Default Curve, we add that
std::vector<double> curve_points = {
static_cast<double>(DCT_Spline)
};
for (size_t i = 0; i < tc_len; i++) {
double x = (double)i / (tc_len - 1);
double y = (double)adobe_camera_raw_default_curve[i];
cPoints.push_back( x );
cPoints.push_back( y );
constexpr size_t tc_len = sizeof(adobe_camera_raw_default_curve) / sizeof(adobe_camera_raw_default_curve[0]);
for (size_t i = 0; i < tc_len; ++i) {
const double x = static_cast<double>(i) / (tc_len - 1);
const double y = adobe_camera_raw_default_curve[i];
curve_points.push_back(x);
curve_points.push_back(y);
}
DiagonalCurve rawCurve(cPoints, CURVES_MIN_POLY_POINTS);
toneCurve.Set(rawCurve);
hasToneCurve = true;
has_tone_curve = true;
tone_curve.Set(DiagonalCurve(curve_points, CURVES_MIN_POLY_POINTS));
}
}
willInterpolate = false;
will_interpolate = false;
if (hasForwardMatrix1) {
if (hasForwardMatrix2) {
if (memcmp(mForwardMatrix1, mForwardMatrix2, sizeof(mForwardMatrix1)) != 0) {
// common that forward matrices are the same!
willInterpolate = true;
if (has_forward_matrix_1) {
if (has_forward_matrix_2) {
if (memcmp(forward_matrix_1, forward_matrix_2, sizeof(forward_matrix_1)) != 0) {
// Common that forward matrices are the same!
will_interpolate = true;
}
if (aDeltas1 && aDeltas2) {
// we assume tables are different
willInterpolate = true;
if (deltas_1 && deltas_2) {
// We assume tables are different
will_interpolate = true;
}
}
}
if (hasColorMatrix1 && hasColorMatrix2) {
if (memcmp(mColorMatrix1, mColorMatrix2, sizeof(mColorMatrix1)) != 0) {
willInterpolate = true;
if (has_color_matrix_1 && has_color_matrix_2) {
if (memcmp(color_matrix_1, color_matrix_2, sizeof(color_matrix_1)) != 0) {
will_interpolate = true;
}
if (aDeltas1 && aDeltas2) {
willInterpolate = true;
if (deltas_1 && deltas_2) {
will_interpolate = true;
}
}
if (pFile != nullptr) {
fclose(pFile);
if (file) {
fclose(file);
}
delete tagDir;
}
DCPProfile::~DCPProfile()
{
delete[] aDeltas1;
delete[] aDeltas2;
delete[] aLookTable;
delete[] deltas_1;
delete[] deltas_2;
delete[] look_table;
}
bool DCPProfile::getHasToneCurve() const
{
return hasToneCurve;
return has_tone_curve;
}
bool DCPProfile::getHasLookTable() const
{
return !!aLookTable;
return look_table;
}
bool DCPProfile::getHasHueSatMap() const
{
return !!aDeltas1;
return deltas_1;
}
bool DCPProfile::getHasBaselineExposureOffset() const
{
return hasBaselineExposureOffset;
return has_baseline_exposure_offset;
}
void DCPProfile::getIlluminants(int &i1, double &temp1, int &i2, double &temp2, bool &willInterpolate_) const
{
i1 = iLightSource1;
i2 = iLightSource2;
temp1 = temperature1, temp2 = temperature2;
willInterpolate_ = willInterpolate;
i1 = light_source_1;
i2 = light_source_2;
temp1 = temperature_1, temp2 = temperature_2;
willInterpolate_ = will_interpolate;
};
void DCPProfile::Apply(Imagefloat *pImg, int preferredIlluminant, const Glib::ustring &workingSpace, const ColorTemp &wb, double pre_mul[3], double camWbMatrix[3][3], bool useToneCurve, bool applyHueSatMap, bool applyLookTable) const
@ -902,11 +933,11 @@ void DCPProfile::Apply(Imagefloat *pImg, int preferredIlluminant, const Glib::us
applyHueSatMap = false;
}
if (!aLookTable) {
if (!look_table) {
applyLookTable = false;
}
useToneCurve &= toneCurve;
useToneCurve &= tone_curve;
if (!applyHueSatMap && !applyLookTable && !useToneCurve) {
//===== The fast path: no LUT and not tone curve- Calculate matrix for direct conversion raw>working space
@ -969,11 +1000,11 @@ void DCPProfile::Apply(Imagefloat *pImg, int preferredIlluminant, const Glib::us
h *= 6.f; // RT calculates in [0,1]
if (applyHueSatMap) {
HSDApply(DeltaInfo, deltaBase, h, s, v);
HSDApply(delta_info, deltaBase, h, s, v);
}
if (applyLookTable) {
HSDApply(LookInfo, aLookTable, h, s, v);
HSDApply(look_info, look_table, h, s, v);
}
// RT range correction
@ -991,7 +1022,7 @@ void DCPProfile::Apply(Imagefloat *pImg, int preferredIlluminant, const Glib::us
// tone curve
if (useToneCurve) {
toneCurve.Apply(newr, newg, newb);
tone_curve.Apply(newr, newg, newb);
}
pImg->r(y, x) = m2Work[0][0] * newr + m2Work[0][1] * newg + m2Work[0][2] * newb;
@ -1006,23 +1037,23 @@ void DCPProfile::Apply(Imagefloat *pImg, int preferredIlluminant, const Glib::us
}
}
void DCPProfile::setStep2ApplyState(const Glib::ustring &workingSpace, bool useToneCurve, bool applyLookTable, bool applyBaselineExposure, dcpApplyState &asOut)
void DCPProfile::setStep2ApplyState(const Glib::ustring &workingSpace, bool useToneCurve, bool applyLookTable, bool applyBaselineExposure, ApplyState &asOut)
{
asOut.useToneCurve = useToneCurve;
asOut.applyLookTable = applyLookTable;
asOut.blScale = 1.0;
if (!aLookTable) {
if (!look_table) {
asOut.applyLookTable = false;
}
if (!hasToneCurve) {
if (!has_tone_curve) {
asOut.useToneCurve = false;
}
if (hasBaselineExposureOffset && applyBaselineExposure) {
asOut.blScale = powf(2, baselineExposureOffset);
if (has_baseline_exposure_offset && applyBaselineExposure) {
asOut.blScale = powf(2, baseline_exposure_offset);
}
if (workingSpace == "ProPhoto") {
@ -1051,7 +1082,7 @@ void DCPProfile::setStep2ApplyState(const Glib::ustring &workingSpace, bool useT
}
}
void DCPProfile::step2ApplyTile(float *rc, float *gc, float *bc, int width, int height, int tileWidth, const dcpApplyState &asIn) const
void DCPProfile::step2ApplyTile(float *rc, float *gc, float *bc, int width, int height, int tileWidth, const ApplyState &asIn) const
{
#define FCLIP(a) ((a)>0.0?((a)<65535.5?(a):65535.5):0.0)
@ -1107,7 +1138,7 @@ void DCPProfile::step2ApplyTile(float *rc, float *gc, float *bc, int width, int
Color::rgb2hsv(newr, newg, newb, h, s, v);
h *= 6.f; // RT calculates in [0,1]
HSDApply(LookInfo, aLookTable, h, s, v);
HSDApply(look_info, look_table, h, s, v);
s = CLIP01(s);
v = CLIP01(v);
@ -1125,7 +1156,7 @@ void DCPProfile::step2ApplyTile(float *rc, float *gc, float *bc, int width, int
}
if (asIn.useToneCurve) {
toneCurve.Apply(newr, newg, newb);
tone_curve.Apply(newr, newg, newb);
}
if (asIn.alreadyProPhoto) {
@ -1228,8 +1259,8 @@ void DCPProfile::dngref_XYCoord2Temperature(const double whiteXY[2], double *tem
void DCPProfile::dngref_FindXYZtoCamera(const double whiteXY[2], int preferredIlluminant, double (*xyzToCamera)[3]) const
{
bool hasCol1 = hasColorMatrix1;
bool hasCol2 = hasColorMatrix2;
bool hasCol1 = has_color_matrix_1;
bool hasCol2 = has_color_matrix_2;
if (preferredIlluminant == 1) {
if (hasCol1) {
@ -1252,13 +1283,13 @@ void DCPProfile::dngref_FindXYZtoCamera(const double whiteXY[2], int preferredIl
*/
dngref_XYCoord2Temperature(whiteXY, &wbtemp, nullptr);
if (wbtemp <= temperature1) {
if (wbtemp <= temperature_1) {
mix = 1.0;
} else if (wbtemp >= temperature2) {
} else if (wbtemp >= temperature_2) {
mix = 0.0;
} else {
double invT = 1.0 / wbtemp;
mix = (invT - (1.0 / temperature2)) / ((1.0 / temperature1) - (1.0 / temperature2));
mix = (invT - (1.0 / temperature_2)) / ((1.0 / temperature_1) - (1.0 / temperature_2));
}
}
@ -1268,16 +1299,16 @@ void DCPProfile::dngref_FindXYZtoCamera(const double whiteXY[2], int preferredIl
if (hasCol1 && hasCol2) {
// interpolate
if (mix >= 1.0) {
memcpy(mCol, mColorMatrix1, sizeof(mCol));
memcpy(mCol, color_matrix_1, sizeof(mCol));
} else if (mix <= 0.0) {
memcpy(mCol, mColorMatrix2, sizeof(mCol));
memcpy(mCol, color_matrix_2, sizeof(mCol));
} else {
mix3x3(mColorMatrix1, mix, mColorMatrix2, 1.0 - mix, mCol);
mix3x3(color_matrix_1, mix, color_matrix_2, 1.0 - mix, mCol);
}
} else if (hasCol1) {
memcpy(mCol, mColorMatrix1, sizeof(mCol));
memcpy(mCol, color_matrix_1, sizeof(mCol));
} else {
memcpy(mCol, mColorMatrix2, sizeof(mCol));
memcpy(mCol, color_matrix_2, sizeof(mCol));
}
memcpy(xyzToCamera, mCol, sizeof(mCol));
@ -1364,10 +1395,10 @@ void DCPProfile::MakeXYZCAM(const ColorTemp &wb, double pre_mul[3], double camWb
double white_xy[2];
dngref_NeutralToXY(neutral, preferredIlluminant, white_xy);
bool hasFwd1 = hasForwardMatrix1;
bool hasFwd2 = hasForwardMatrix2;
bool hasCol1 = hasColorMatrix1;
bool hasCol2 = hasColorMatrix2;
bool hasFwd1 = has_forward_matrix_1;
bool hasFwd2 = has_forward_matrix_2;
bool hasCol1 = has_color_matrix_1;
bool hasCol2 = has_color_matrix_2;
if (preferredIlluminant == 1) {
if (hasFwd1) {
@ -1397,13 +1428,13 @@ void DCPProfile::MakeXYZCAM(const ColorTemp &wb, double pre_mul[3], double camWb
use the DNG reference code here, but we do it for now. */
dngref_XYCoord2Temperature(white_xy, &wbtemp, nullptr);
if (wbtemp <= temperature1) {
if (wbtemp <= temperature_1) {
mix = 1.0;
} else if (wbtemp >= temperature2) {
} else if (wbtemp >= temperature_2) {
mix = 0.0;
} else {
double invT = 1.0 / wbtemp;
mix = (invT - (1.0 / temperature2)) / ((1.0 / temperature1) - (1.0 / temperature2));
mix = (invT - (1.0 / temperature_2)) / ((1.0 / temperature_1) - (1.0 / temperature_2));
}
}
@ -1413,16 +1444,16 @@ void DCPProfile::MakeXYZCAM(const ColorTemp &wb, double pre_mul[3], double camWb
if (hasCol1 && hasCol2) {
// interpolate
if (mix >= 1.0) {
memcpy(mCol, mColorMatrix1, sizeof(mCol));
memcpy(mCol, color_matrix_1, sizeof(mCol));
} else if (mix <= 0.0) {
memcpy(mCol, mColorMatrix2, sizeof(mCol));
memcpy(mCol, color_matrix_2, sizeof(mCol));
} else {
mix3x3(mColorMatrix1, mix, mColorMatrix2, 1.0 - mix, mCol);
mix3x3(color_matrix_1, mix, color_matrix_2, 1.0 - mix, mCol);
}
} else if (hasCol1) {
memcpy(mCol, mColorMatrix1, sizeof(mCol));
memcpy(mCol, color_matrix_1, sizeof(mCol));
} else {
memcpy(mCol, mColorMatrix2, sizeof(mCol));
memcpy(mCol, color_matrix_2, sizeof(mCol));
}
/*
@ -1445,16 +1476,16 @@ void DCPProfile::MakeXYZCAM(const ColorTemp &wb, double pre_mul[3], double camWb
if (hasFwd1 && hasFwd2) {
// interpolate
if (mix >= 1.0) {
memcpy(mFwd, mForwardMatrix1, sizeof(mFwd));
memcpy(mFwd, forward_matrix_1, sizeof(mFwd));
} else if (mix <= 0.0) {
memcpy(mFwd, mForwardMatrix2, sizeof(mFwd));
memcpy(mFwd, forward_matrix_2, sizeof(mFwd));
} else {
mix3x3(mForwardMatrix1, mix, mForwardMatrix2, 1.0 - mix, mFwd);
mix3x3(forward_matrix_1, mix, forward_matrix_2, 1.0 - mix, mFwd);
}
} else if (hasFwd1) {
memcpy(mFwd, mForwardMatrix1, sizeof(mFwd));
memcpy(mFwd, forward_matrix_1, sizeof(mFwd));
} else {
memcpy(mFwd, mForwardMatrix2, sizeof(mFwd));
memcpy(mFwd, forward_matrix_2, sizeof(mFwd));
}
// adapted from dng_color_spec::SetWhiteXY
@ -1525,34 +1556,34 @@ const DCPProfile::HSBModify* DCPProfile::MakeHueSatMap(const ColorTemp &wb, int
*deleteHandle = nullptr;
if (!aDeltas1) {
if (!deltas_1) {
return nullptr;
}
if (!aDeltas2) {
return aDeltas1;
if (!deltas_2) {
return deltas_1;
}
if (preferredIlluminant == 1) {
return aDeltas1;
return deltas_1;
} else if (preferredIlluminant == 2) {
return aDeltas2;
return deltas_2;
}
// Interpolate based on color temperature.
if (temperature1 <= 0.0 || temperature2 <= 0.0 || temperature1 == temperature2) {
return aDeltas1;
if (temperature_1 <= 0.0 || temperature_2 <= 0.0 || temperature_1 == temperature_2) {
return deltas_1;
}
bool reverseOrder = temperature1 > temperature2;
bool reverseOrder = temperature_1 > temperature_2;
double t1, t2;
if (reverseOrder) {
t1 = temperature2;
t2 = temperature1;
t1 = temperature_2;
t2 = temperature_1;
} else {
t1 = temperature1;
t2 = temperature2;
t1 = temperature_1;
t2 = temperature_2;
}
double mix;
@ -1571,21 +1602,21 @@ const DCPProfile::HSBModify* DCPProfile::MakeHueSatMap(const ColorTemp &wb, int
}
if (mix >= 1.0) {
return aDeltas1;
return deltas_1;
} else if (mix <= 0.0) {
return aDeltas2;
return deltas_2;
}
// Interpolate between the tables.
HSBModify *aDeltas = new HSBModify[DeltaInfo.iArrayCount];
HSBModify *aDeltas = new HSBModify[delta_info.array_count];
*deleteHandle = aDeltas;
float w1 = (float)mix;
float w2 = 1.0f - (float)mix;
for (int i = 0; i < DeltaInfo.iArrayCount; i++) {
aDeltas[i].fHueShift = w1 * aDeltas1[i].fHueShift + w2 * aDeltas2[i].fHueShift;
aDeltas[i].fSatScale = w1 * aDeltas1[i].fSatScale + w2 * aDeltas2[i].fSatScale;
aDeltas[i].fValScale = w1 * aDeltas1[i].fValScale + w2 * aDeltas2[i].fValScale;
for (int i = 0; i < delta_info.array_count; i++) {
aDeltas[i].hue_shift = w1 * deltas_1[i].hue_shift + w2 * deltas_2[i].hue_shift;
aDeltas[i].sat_scale = w1 * deltas_1[i].sat_scale + w2 * deltas_2[i].sat_scale;
aDeltas[i].val_scale = w1 * deltas_1[i].val_scale + w2 * deltas_2[i].val_scale;
}
return aDeltas;
@ -1598,9 +1629,9 @@ void DCPProfile::HSDApply(const HSDTableInfo &ti, const HSBModify *tableBase, fl
float hueShift, satScale, valScale;
float vEncoded = v;
if (ti.iValDivisions < 2) { // Optimize most common case of "2.5D" table.
float hScaled = h * ti.pc.hScale;
float sScaled = s * ti.pc.sScale;
if (ti.val_divisions < 2) { // Optimize most common case of "2.5D" table.
float hScaled = h * ti.pc.h_scale;
float sScaled = s * ti.pc.s_scale;
int hIndex0 = max((int)hScaled, 0);
int sIndex0 = max(min((int)sScaled, ti.pc.maxSatIndex0), 0);
@ -1621,21 +1652,21 @@ void DCPProfile::HSDApply(const HSDTableInfo &ti, const HSBModify *tableBase, fl
const HSBModify *entry00 = tableBase + hIndex0 * ti.pc.hueStep + sIndex0;
const HSBModify *entry01 = entry00 + (hIndex1 - hIndex0) * ti.pc.hueStep;
float hueShift0 = hFract0 * entry00->fHueShift + hFract1 * entry01->fHueShift;
float satScale0 = hFract0 * entry00->fSatScale + hFract1 * entry01->fSatScale;
float valScale0 = hFract0 * entry00->fValScale + hFract1 * entry01->fValScale;
float hueShift0 = hFract0 * entry00->hue_shift + hFract1 * entry01->hue_shift;
float satScale0 = hFract0 * entry00->sat_scale + hFract1 * entry01->sat_scale;
float valScale0 = hFract0 * entry00->val_scale + hFract1 * entry01->val_scale;
entry00++;
entry01++;
float hueShift1 = hFract0 * entry00->fHueShift +
hFract1 * entry01->fHueShift;
float hueShift1 = hFract0 * entry00->hue_shift +
hFract1 * entry01->hue_shift;
float satScale1 = hFract0 * entry00->fSatScale +
hFract1 * entry01->fSatScale;
float satScale1 = hFract0 * entry00->sat_scale +
hFract1 * entry01->sat_scale;
float valScale1 = hFract0 * entry00->fValScale +
hFract1 * entry01->fValScale;
float valScale1 = hFract0 * entry00->val_scale +
hFract1 * entry01->val_scale;
hueShift = sFract0 * hueShift0 + sFract1 * hueShift1;
satScale = sFract0 * satScale0 + sFract1 * satScale1;
@ -1643,14 +1674,14 @@ void DCPProfile::HSDApply(const HSDTableInfo &ti, const HSBModify *tableBase, fl
} else {
float hScaled = h * ti.pc.hScale;
float sScaled = s * ti.pc.sScale;
float hScaled = h * ti.pc.h_scale;
float sScaled = s * ti.pc.s_scale;
if (ti.sRGBGamma) {
if (ti.srgb_gamma) {
vEncoded = sRGBGammaForward(v);
}
float vScaled = vEncoded * ti.pc.vScale;
float vScaled = vEncoded * ti.pc.v_scale;
int hIndex0 = (int) hScaled;
int sIndex0 = max(min((int)sScaled, ti.pc.maxSatIndex0), 0);
@ -1678,40 +1709,40 @@ void DCPProfile::HSDApply(const HSDTableInfo &ti, const HSBModify *tableBase, fl
const HSBModify *entry10 = entry00 + ti.pc.valStep;
const HSBModify *entry11 = entry01 + ti.pc.valStep;
float hueShift0 = vFract0 * (hFract0 * entry00->fHueShift +
hFract1 * entry01->fHueShift) +
vFract1 * (hFract0 * entry10->fHueShift +
hFract1 * entry11->fHueShift);
float hueShift0 = vFract0 * (hFract0 * entry00->hue_shift +
hFract1 * entry01->hue_shift) +
vFract1 * (hFract0 * entry10->hue_shift +
hFract1 * entry11->hue_shift);
float satScale0 = vFract0 * (hFract0 * entry00->fSatScale +
hFract1 * entry01->fSatScale) +
vFract1 * (hFract0 * entry10->fSatScale +
hFract1 * entry11->fSatScale);
float satScale0 = vFract0 * (hFract0 * entry00->sat_scale +
hFract1 * entry01->sat_scale) +
vFract1 * (hFract0 * entry10->sat_scale +
hFract1 * entry11->sat_scale);
float valScale0 = vFract0 * (hFract0 * entry00->fValScale +
hFract1 * entry01->fValScale) +
vFract1 * (hFract0 * entry10->fValScale +
hFract1 * entry11->fValScale);
float valScale0 = vFract0 * (hFract0 * entry00->val_scale +
hFract1 * entry01->val_scale) +
vFract1 * (hFract0 * entry10->val_scale +
hFract1 * entry11->val_scale);
entry00++;
entry01++;
entry10++;
entry11++;
float hueShift1 = vFract0 * (hFract0 * entry00->fHueShift +
hFract1 * entry01->fHueShift) +
vFract1 * (hFract0 * entry10->fHueShift +
hFract1 * entry11->fHueShift);
float hueShift1 = vFract0 * (hFract0 * entry00->hue_shift +
hFract1 * entry01->hue_shift) +
vFract1 * (hFract0 * entry10->hue_shift +
hFract1 * entry11->hue_shift);
float satScale1 = vFract0 * (hFract0 * entry00->fSatScale +
hFract1 * entry01->fSatScale) +
vFract1 * (hFract0 * entry10->fSatScale +
hFract1 * entry11->fSatScale);
float satScale1 = vFract0 * (hFract0 * entry00->sat_scale +
hFract1 * entry01->sat_scale) +
vFract1 * (hFract0 * entry10->sat_scale +
hFract1 * entry11->sat_scale);
float valScale1 = vFract0 * (hFract0 * entry00->fValScale +
hFract1 * entry01->fValScale) +
vFract1 * (hFract0 * entry10->fValScale +
hFract1 * entry11->fValScale);
float valScale1 = vFract0 * (hFract0 * entry00->val_scale +
hFract1 * entry01->val_scale) +
vFract1 * (hFract0 * entry10->val_scale +
hFract1 * entry11->val_scale);
hueShift = sFract0 * hueShift0 + sFract1 * hueShift1;
satScale = sFract0 * satScale0 + sFract1 * satScale1;
@ -1723,7 +1754,7 @@ void DCPProfile::HSDApply(const HSDTableInfo &ti, const HSBModify *tableBase, fl
h += hueShift;
s *= satScale; // no clipping here, we are RT float :-)
if (ti.sRGBGamma) {
if (ti.srgb_gamma) {
v = sRGBGammaInverse(vEncoded * valScale);
} else {
v *= valScale;

View File

@ -35,7 +35,7 @@ namespace rtengine
class DCPProfile final
{
public:
struct dcpApplyState{
struct ApplyState {
double m2ProPhoto[3][3];
double m2Work[3][3];
bool alreadyProPhoto;
@ -44,33 +44,44 @@ public:
float blScale;
};
DCPProfile(const Glib::ustring &fname);
DCPProfile(const Glib::ustring& filename);
~DCPProfile();
bool getHasToneCurve() const;
bool getHasLookTable() const;
bool getHasHueSatMap() const;
bool getHasBaselineExposureOffset() const;
void getIlluminants(int &i1, double &temp1, int &i2, double &temp2, bool &willInterpolate_) const;
void Apply(Imagefloat *pImg, int preferredIlluminant, const Glib::ustring &workingSpace, const ColorTemp &wb, double pre_mul[3], double camMatrix[3][3], bool useToneCurve = false, bool applyHueSatMap = true, bool applyLookTable = false) const;
void setStep2ApplyState(const Glib::ustring &workingSpace, bool useToneCurve, bool applyLookTable, bool applyBaselineExposure, dcpApplyState &asOut);
void step2ApplyTile(float *r, float *g, float *b, int width, int height, int tileWidth, const dcpApplyState &asIn) const;
void setStep2ApplyState(const Glib::ustring &workingSpace, bool useToneCurve, bool applyLookTable, bool applyBaselineExposure, ApplyState &asOut);
void step2ApplyTile(float *r, float *g, float *b, int width, int height, int tileWidth, const ApplyState &asIn) const;
private:
struct HSBModify {
float fHueShift;
float fSatScale;
float fValScale;
float hue_shift;
float sat_scale;
float val_scale;
};
struct HSDTableInfo {
int iHueDivisions, iSatDivisions, iValDivisions;
int iHueStep, iValStep, iArrayCount;
bool sRGBGamma;
int hue_divisions;
int sat_divisions;
int val_divisions;
int iHueStep;
int iValStep;
int array_count;
bool srgb_gamma;
struct {
float hScale, sScale, vScale;
int maxHueIndex0, maxSatIndex0, maxValIndex0;
int hueStep, valStep;
float h_scale;
float s_scale;
float v_scale;
int maxHueIndex0;
int maxSatIndex0;
int maxValIndex0;
int hueStep;
int valStep;
} pc;
};
@ -81,16 +92,29 @@ private:
const HSBModify* MakeHueSatMap(const ColorTemp &wb, int preferredIlluminant, HSBModify **deleteHandle) const;
void HSDApply(const HSDTableInfo &ti, const HSBModify *tableBase, float &h, float &s, float &v) const;
double mColorMatrix1[3][3], mColorMatrix2[3][3];
bool hasColorMatrix1, hasColorMatrix2, hasForwardMatrix1, hasForwardMatrix2, hasToneCurve, hasBaselineExposureOffset, willInterpolate;
double mForwardMatrix1[3][3], mForwardMatrix2[3][3];
double temperature1, temperature2;
double baselineExposureOffset;
HSBModify *aDeltas1, *aDeltas2, *aLookTable;
HSDTableInfo DeltaInfo, LookInfo;
short iLightSource1, iLightSource2;
double color_matrix_1[3][3];
double color_matrix_2[3][3];
bool has_color_matrix_1;
bool has_color_matrix_2;
bool has_forward_matrix_1;
bool has_forward_matrix_2;
bool has_tone_curve;
bool has_baseline_exposure_offset;
bool will_interpolate;
double forward_matrix_1[3][3];
double forward_matrix_2[3][3];
double temperature_1;
double temperature_2;
double baseline_exposure_offset;
HSBModify* deltas_1;
HSBModify* deltas_2;
HSBModify* look_table;
HSDTableInfo delta_info;
HSDTableInfo look_info;
short light_source_1;
short light_source_2;
AdobeToneCurve toneCurve;
AdobeToneCurve tone_curve;
};
class DCPStore final

View File

@ -773,7 +773,7 @@ void Crop::update (int todo)
if (todo & M_RGBCURVE) {
double rrm, ggm, bbm;
DCPProfile::dcpApplyState as;
DCPProfile::ApplyState as;
DCPProfile *dcpProf = parent->imgsrc->getDCP(params.icm, parent->currWB, as);
parent->ipf.rgbProc (baseCrop, laboCrop, this, parent->hltonecurve, parent->shtonecurve, parent->tonecurve, cshmap,

View File

@ -109,7 +109,7 @@ public:
virtual ImageData* getImageData () = 0;
virtual ImageMatrices* getImageMatrices () = 0;
virtual bool isRAW() const = 0;
virtual DCPProfile* getDCP(const ColorManagementParams &cmp, ColorTemp &wb, DCPProfile::dcpApplyState &as)
virtual DCPProfile* getDCP(const ColorManagementParams &cmp, ColorTemp &wb, DCPProfile::ApplyState &as)
{
return NULL;
};

View File

@ -535,7 +535,7 @@ void ImProcCoordinator::updatePreviewImage (int todo, Crop* cropCall)
double ggm = 33.;
double bbm = 33.;
DCPProfile::dcpApplyState as;
DCPProfile::ApplyState as;
DCPProfile *dcpProf = imgsrc->getDCP(params.icm, currWB, as);
ipf.rgbProc (oprevi, oprevl, NULL, hltonecurve, shtonecurve, tonecurve, shmap, params.toneCurve.saturation,

View File

@ -2947,7 +2947,7 @@ filmlike_clip(float *r, float *g, float *b)
void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer *pipetteBuffer, LUTf & hltonecurve, LUTf & shtonecurve, LUTf & tonecurve,
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, DCPProfile *dcpProf, const DCPProfile::dcpApplyState &asIn )
const ToneCurve & customToneCurve1, const ToneCurve & customToneCurve2, const ToneCurve & customToneCurvebw1, const ToneCurve & customToneCurvebw2, double &rrm, double &ggm, double &bbm, float &autor, float &autog, float &autob, DCPProfile *dcpProf, const DCPProfile::ApplyState &asIn )
{
rgbProc (working, lab, pipetteBuffer, hltonecurve, shtonecurve, tonecurve, shmap, sat, rCurve, gCurve, bCurve, satLimit , satLimitOpacity, ctColorCurve, ctOpacityCurve, opautili, clToningcurve, cl2Toningcurve, customToneCurve1, customToneCurve2, customToneCurvebw1, customToneCurvebw2, rrm, ggm, bbm, autor, autog, autob, params->toneCurve.expcomp, params->toneCurve.hlcompr, params->toneCurve.hlcomprthresh, dcpProf, asIn);
}
@ -2955,7 +2955,7 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer
// Process RGB image and convert to LAB space
void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer *pipetteBuffer, LUTf & hltonecurve, LUTf & shtonecurve, LUTf & tonecurve,
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 DCPProfile::dcpApplyState &asIn )
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 DCPProfile::ApplyState &asIn )
{
Imagefloat *tmpImage = nullptr;

View File

@ -232,11 +232,11 @@ public:
void updateColorProfiles (const ColorManagementParams& icm, const Glib::ustring& monitorProfile, RenderingIntent monitorIntent);
void rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer *pipetteBuffer, LUTf & hltonecurve, LUTf & shtonecurve, LUTf & tonecurve,
SHMap* shmap, int sat, LUTf & rCurve, LUTf & gCurve, LUTf & bCurve, float satLimit , float satLimitOpacity, const ColorGradientCurve & ctColorCurve, const OpacityCurve & ctOpacityCurve, bool opautili, LUTf & clcurve, LUTf & cl2curve, const ToneCurve & customToneCurve1, const ToneCurve & customToneCurve2,
const ToneCurve & customToneCurvebw1, const ToneCurve & customToneCurvebw2, double &rrm, double &ggm, double &bbm, float &autor, float &autog, float &autob, DCPProfile *dcpProf, const DCPProfile::dcpApplyState &asIn );
const ToneCurve & customToneCurvebw1, const ToneCurve & customToneCurvebw2, double &rrm, double &ggm, double &bbm, float &autor, float &autog, float &autob, DCPProfile *dcpProf, const DCPProfile::ApplyState &asIn );
void rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer *pipetteBuffer, LUTf & hltonecurve, LUTf & shtonecurve, LUTf & tonecurve,
SHMap* shmap, int sat, LUTf & rCurve, LUTf & gCurve, LUTf & bCurve, float satLimit , float satLimitOpacity, const ColorGradientCurve & ctColorCurve, const OpacityCurve & ctOpacityCurve, bool opautili, LUTf & clcurve, LUTf & cl2curve, 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 DCPProfile::dcpApplyState &asIn );
double expcomp, int hlcompr, int hlcomprthresh, DCPProfile *dcpProf, const DCPProfile::ApplyState &asIn );
void labtoning (float r, float g, float b, float &ro, float &go, float &bo, int algm, int metchrom, int twoc, float satLimit, float satLimitOpacity, const ColorGradientCurve & ctColorCurve, const OpacityCurve & ctOpacityCurve, LUTf & clToningcurve, LUTf & cl2Toningcurve, float iplow, float iphigh, double wp[3][3], double wip[3][3] );
void toning2col (float r, float g, float b, float &ro, float &go, float &bo, float iplow, float iphigh, float rl, float gl, float bl, float rh, float gh, float bh, float SatLow, float SatHigh, float balanS, float balanH, float reducac, int mode, int preser, float strProtect);
void toningsmh (float r, float g, float b, float &ro, float &go, float &bo, float RedLow, float GreenLow, float BlueLow, float RedMed, float GreenMed, float BlueMed, float RedHigh, float GreenHigh, float BlueHigh, float reducac, int mode, int preser, float strProtect);

View File

@ -889,7 +889,7 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima
}
}
DCPProfile *RawImageSource::getDCP(const ColorManagementParams &cmp, ColorTemp &wb,DCPProfile::dcpApplyState &as)
DCPProfile *RawImageSource::getDCP(const ColorManagementParams &cmp, ColorTemp &wb,DCPProfile::ApplyState &as)
{
DCPProfile *dcpProf = NULL;
cmsHPROFILE dummy;

View File

@ -184,7 +184,7 @@ public:
}
void getAutoExpHistogram (LUTu & histogram, int& histcompr);
void getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LUTu & histBlueRaw);
DCPProfile *getDCP(const ColorManagementParams &cmp, ColorTemp &wb, DCPProfile::dcpApplyState &as);
DCPProfile *getDCP(const ColorManagementParams &cmp, ColorTemp &wb, DCPProfile::ApplyState &as);
void convertColorSpace(Imagefloat* image, const ColorManagementParams &cmp, const ColorTemp &wb);
static bool findInputProfile(Glib::ustring inProfile, cmsHPROFILE embedded, std::string camName, DCPProfile **dcpProf, cmsHPROFILE& in);

View File

@ -1041,7 +1041,7 @@ IImage8* Thumbnail::processImage (const procparams::ProcParams& params, int rhei
LabImage* labView = new LabImage (fw, fh);
DCPProfile *dcpProf = nullptr;
DCPProfile::dcpApplyState as;
DCPProfile::ApplyState as;
if (isRaw) {
cmsHPROFILE dummy;
RawImageSource::findInputProfile(params.icm.input, nullptr, camName, &dcpProf, dummy);

View File

@ -853,7 +853,7 @@ IImage16* processImage (ProcessingJob* pjob, int& errorCode, ProgressListener* p
}
autor = -9000.f; // This will ask to compute the "auto" values for the B&W tool (have to be inferior to -5000)
DCPProfile::dcpApplyState as;
DCPProfile::ApplyState as;
DCPProfile *dcpProf = imgsrc->getDCP(params.icm, currWB, as);
ipf.rgbProc (baseImg, labView, NULL, curve1, curve2, curve, shmap, params.toneCurve.saturation, rCurve, gCurve, bCurve, satLimit , satLimitOpacity, ctColorCurve, ctOpacityCurve, opautili, clToningcurve, cl2Toningcurve, customToneCurve1, customToneCurve2, customToneCurvebw1, customToneCurvebw2, rrm, ggm, bbm, autor, autog, autob, expcomp, hlcompr, hlcomprthresh, dcpProf, as);

View File

@ -16,8 +16,9 @@
* You should have received a copy of the GNU General Public License
* along with RawTherapee. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef _SIMPLEUTILS_
#define _SIMPLEUTILS_
#pragma once
#include <type_traits>
namespace rtengine
{
@ -35,5 +36,10 @@ void rotate (unsigned char* img, int& w, int& h, int deg);
void hflip (unsigned char* img, int w, int h);
void vflip (unsigned char* img, int w, int h);
template<typename ENUM>
typename std::underlying_type<ENUM>::type toUnderlying(ENUM value)
{
return static_cast<typename std::underlying_type<ENUM>::type>(value);
}
}
#endif