Whitebalance - Removed GUI Itcwb from whitebalance and preferences (#6710)
* Change Preferences for observer whitebalance * Change label white balance preferences * Added Preferences 2 parameters Whitebalance auto correlation * Add Preference Temperature correlation - sort and tooltip * Change to rtengine cmakelist * Apply patch from Lawrence37 * Small comment code * Change defaut order prefrences wba * Added force extra algoritm to Preferences * Harmonize itcwb sorted * Add fields to Preferences Itcwb * Change settings precision Itcwb in Preferences * Change tooltip Itcwb preferences * First stage Itwcwb settings in main with pp3 and selction in preferences * Second stage Itwcwb settings in main with pp3 and selction in preferences * Third stage Itwcwb settings in main with pp3 and selction in preferences * Add itcwb_fgreen student - green optimize * Add Itcwb green range * Itcwb history msg - first tooltips * Remove force-extra because always used * reused force-extra to use entire CIExy for sampling datas * Removed inwanted text in console * Set sensitive for Itcwbframe * Various change - comment .. * Small code review - chnage tooltips * Remove settings itcwb_delta in Rawimagesource.cc to simplify * Remove Itcwb Observer - put a single observer for everything - general - itcwb * Fixed conflicts in colortemp.cc * Various change - fixed bug - simplify * Fixed limits for settings pp3 - chnage tooltip * Clean unused code * Put itcwb_findgreen in GUI * Added checkbox 'Low sampling' to find the settings of 5.9 * Set Observer to Observer 10° - preferences default * Missing setting Low sampling * Show white balance multipliers * Change default settings - Itcwb_sorted * Move observer from preferences to WB * Make observer selectable for camera WB * Ensure observer checkbox is in sync with PP3 * Set default ITCWB low sampling for PP3s from <=5.9 Ensure temperature correlation white balance algorithm 1 is used when opening edits from versions 5.9 and earlier. * Removed unused White-balance frame in Preferences * Comment some GUI sliders checkbox * Removed all GUI itcwb in preferences and whitebalance * Removed forgotten code in preferences * Remove labels tooltips history Itcwb --------- Co-authored-by: Lawrence Lee <45837045+Lawrence37@users.noreply.github.com>
This commit is contained in:
parent
ca08a279d5
commit
69c1caafa1
@ -1528,6 +1528,7 @@ HISTORY_MSG_WAVSTREND;Strength soft
|
||||
HISTORY_MSG_WAVTHRDEN;Threshold local contrast
|
||||
HISTORY_MSG_WAVTHREND;Threshold local contrast
|
||||
HISTORY_MSG_WAVUSHAMET;Clarity method
|
||||
HISTORY_MSG_WBALANCE_OBSERVER10;Observer 10°
|
||||
HISTORY_NEWSNAPSHOT;Add
|
||||
HISTORY_NEWSNAPSHOT_TOOLTIP;Shortcut: <b>Alt-s</b>
|
||||
HISTORY_SNAPSHOT;Snapshot
|
||||
@ -1831,6 +1832,7 @@ PREFERENCES_CHUNKSIZE_RAW_XT;Xtrans demosaic
|
||||
PREFERENCES_CHUNKSIZE_RGB;RGB processing
|
||||
PREFERENCES_CIE;Ciecam
|
||||
PREFERENCES_CIEARTIF;Avoid artifacts
|
||||
PREFERENCES_WBA;White Balance
|
||||
PREFERENCES_CLIPPINGIND;Clipping Indication
|
||||
PREFERENCES_CLUTSCACHE;HaldCLUT Cache
|
||||
PREFERENCES_CLUTSCACHE_LABEL;Maximum number of cached CLUTs
|
||||
@ -4079,6 +4081,10 @@ TP_WBALANCE_LED_CRS;CRS SP12 WWMR16
|
||||
TP_WBALANCE_LED_HEADER;LED
|
||||
TP_WBALANCE_LED_LSI;LSI Lumelex 2040
|
||||
TP_WBALANCE_METHOD;Method
|
||||
TP_WBALANCE_MULLABEL;Multipliers: r=%1 g=%2 b=%3
|
||||
TP_WBALANCE_MULLABEL_TOOLTIP;Values given for information purposes. You cannot change them.
|
||||
TP_WBALANCE_OBSERVER10;Observer 10° instead of Observer 2°
|
||||
TP_WBALANCE_OBSERVER10_TOOLTIP;The color management in Rawtherapee (White balance, channel multipliers, highlight recovery,...) uses the spectral data of the illuminants and colors. Observer is an important parameter of this management which takes into account the angle of perception of the eye. In 1931 it was fixed at 2° (privileges the use of the cones). In 1964 it was fixed at 10° (privileges the use of the cones, but partially takes into account the rods).\nTo avoid a (rare) drift of the colors due to the choice Observer 10° - probably due to the conversion matrix - Observer 2° must be selected.\nIn a majority of cases Observer 10° (default) will be a more relevant choice.
|
||||
TP_WBALANCE_PICKER;Pick
|
||||
TP_WBALANCE_SHADE;Shade
|
||||
TP_WBALANCE_SIZE;Size:
|
||||
|
@ -171,7 +171,7 @@ static const color_match_type cie_colour_match_jd = {//350nm to 830nm 5 nm J.D
|
||||
|
||||
|
||||
|
||||
ColorTemp::ColorTemp (double t, double g, double e, const std::string &m) : temp(t), green(g), equal(e), method(m)
|
||||
ColorTemp::ColorTemp (double t, double g, double e, const std::string &m, StandardObserver o) : temp(t), green(g), equal(e), method(m), observer(o)
|
||||
{
|
||||
clip (temp, green, equal);
|
||||
}
|
||||
@ -189,12 +189,24 @@ void ColorTemp::clip (double &temp, double &green, double &equal)
|
||||
equal = rtengine::LIM(equal, MINEQUAL, MAXEQUAL);
|
||||
}
|
||||
|
||||
ColorTemp::ColorTemp (double mulr, double mulg, double mulb, double e) : equal(e), method("Custom")
|
||||
ColorTemp::ColorTemp (double mulr, double mulg, double mulb, double e, StandardObserver observer) : equal(e), method("Custom"), observer(observer)
|
||||
{
|
||||
mul2temp (mulr, mulg, mulb, equal, temp, green);
|
||||
mul2temp (mulr, mulg, mulb, equal, observer, temp, green);
|
||||
}
|
||||
|
||||
void ColorTemp::mul2temp (const double rmul, const double gmul, const double bmul, const double equal, double& temp, double& green) const
|
||||
ColorTemp ColorTemp::convertObserver(StandardObserver observer) const
|
||||
{
|
||||
if (observer == this->observer) {
|
||||
return *this;
|
||||
}
|
||||
double r;
|
||||
double g;
|
||||
double b;
|
||||
getMultipliers(r, g, b);
|
||||
return ColorTemp(r, g, b, equal, observer);
|
||||
}
|
||||
|
||||
void ColorTemp::mul2temp (const double rmul, const double gmul, const double bmul, const double equal, StandardObserver observer, double& temp, double& green) const
|
||||
{
|
||||
|
||||
double maxtemp = MAXTEMP, mintemp = MINTEMP;
|
||||
@ -202,7 +214,7 @@ void ColorTemp::mul2temp (const double rmul, const double gmul, const double bmu
|
||||
temp = (maxtemp + mintemp) / 2;
|
||||
|
||||
while (maxtemp - mintemp > 1) {
|
||||
temp2mul (temp, 1.0, equal, tmpr, tmpg, tmpb);
|
||||
temp2mul (temp, 1.0, equal, observer, tmpr, tmpg, tmpb);
|
||||
|
||||
if (tmpb / tmpr > bmul / rmul) {
|
||||
maxtemp = temp;
|
||||
@ -2957,14 +2969,19 @@ void ColorTemp::icieCAT02float(float Xw, float Yw, float Zw, float &iCAM02BB00,
|
||||
}
|
||||
|
||||
|
||||
void ColorTemp::temp2mulxyz (double temp, const std::string &method, double &Xxyz, double &Zxyz)
|
||||
void ColorTemp::temp2mulxyz (double temp, const std::string &method, StandardObserver observer, double &Xxyz, double &Zxyz)
|
||||
{
|
||||
double x, y, z;
|
||||
|
||||
// We first test for specially handled methods
|
||||
const auto iterator = spectMap.find(method);
|
||||
const auto &color_match = (settings->observer10 == true) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
|
||||
const auto &color_match = (observer == StandardObserver::TEN_DEGREES) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
/* if(observer == StandardObserver::TEN_DEGREES){
|
||||
printf("General Observer 10°\n");
|
||||
} else {
|
||||
printf("General Observer 2°\n");
|
||||
}
|
||||
*/
|
||||
if (iterator != spectMap.end()) {
|
||||
spectrum_to_xyz_preset(iterator->second, x, y, z, color_match);
|
||||
} else {
|
||||
@ -2999,11 +3016,11 @@ void ColorTemp::temp2mulxyz (double temp, const std::string &method, double &Xxy
|
||||
Zxyz = (1.0 - x - y) / y;
|
||||
}
|
||||
|
||||
void ColorTemp::temp2mul (double temp, double green, double equal, double& rmul, double& gmul, double& bmul) const
|
||||
void ColorTemp::temp2mul (double temp, double green, double equal, StandardObserver observer, double& rmul, double& gmul, double& bmul) const
|
||||
{
|
||||
clip(temp, green, equal);
|
||||
double Xwb, Zwb;
|
||||
temp2mulxyz(temp, method, Xwb, Zwb);
|
||||
temp2mulxyz(temp, method, observer, Xwb, Zwb);
|
||||
|
||||
double adj = 1.0;
|
||||
|
||||
@ -3170,7 +3187,13 @@ void ColorTemp::temp2mul (double temp, double green, double equal, double& rmul,
|
||||
float CRI_RT = 0.0, CRI[50];
|
||||
float CRI_RTs = 0.0, CRIs[8];
|
||||
|
||||
const auto &color_match = (settings->observer10 == true) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
const auto &color_match = (observer == StandardObserver::TEN_DEGREES) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
//exceptional must be used by advice people
|
||||
if(observer == StandardObserver::TEN_DEGREES){
|
||||
printf("CRI Observer 10°\n");
|
||||
} else {
|
||||
printf("CRI Observer 2°\n");
|
||||
}
|
||||
|
||||
for(int i = 0; i < N_c; i++) {
|
||||
spectrum_to_color_xyz_preset(spec_color[i], spect_illum[illum + 3], XchkLamp[i], YchkLamp[i], ZchkLamp[i], color_match);
|
||||
@ -3764,17 +3787,9 @@ void ColorTemp::tempxy(bool separated, int repref, float **Tx, float **Ty, float
|
||||
Refxyz[i].Zref = 0.f;
|
||||
}
|
||||
|
||||
/* if (settings->verbose) {
|
||||
const color_match_type &color_match = (wbpar.observer == StandardObserver::TEN_DEGREES) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
|
||||
if (settings->itcwb_stdobserver10 == false) {//I will try to change settings by main
|
||||
printf("Use standard observer 2°\n");
|
||||
} else {
|
||||
printf("Use standard observer 10°\n");
|
||||
}
|
||||
}
|
||||
*/
|
||||
const color_match_type &color_match = (settings->observer10 == true) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
// const color_match_type &color_match = (settings->itcwb_stdobserver10 == true) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
// const color_match_type &color_match = (wbpar.observer == StandardObserver::TEN_DEGREES) ? cie_colour_match_jd : cie_colour_match_jd2;
|
||||
|
||||
if (separated) {
|
||||
const double tempw = Txyz[repref].Tem;
|
||||
|
@ -36,6 +36,10 @@ constexpr double MINEQUAL = 0.8;
|
||||
constexpr double MAXEQUAL = 1.5;
|
||||
constexpr double INITIALBLACKBODY = 4000.0;
|
||||
|
||||
enum class StandardObserver {
|
||||
TWO_DEGREES,
|
||||
TEN_DEGREES,
|
||||
};
|
||||
|
||||
class ColorTemp
|
||||
{
|
||||
@ -45,32 +49,36 @@ private:
|
||||
double green;
|
||||
double equal;
|
||||
std::string method;
|
||||
StandardObserver observer{StandardObserver::TEN_DEGREES};
|
||||
static void clip (double &temp, double &green);
|
||||
static void clip (double &temp, double &green, double &equal);
|
||||
int XYZtoCorColorTemp(double x0, double y0 , double z0, double &temp) const;
|
||||
void temp2mul (double temp, double green, double equal, double& rmul, double& gmul, double& bmul) const;
|
||||
void temp2mul (double temp, double green, double equal, StandardObserver observer, double& rmul, double& gmul, double& bmul) const;
|
||||
const static std::map<std::string,const double *> spectMap;
|
||||
public:
|
||||
static constexpr StandardObserver DEFAULT_OBSERVER = StandardObserver::TEN_DEGREES;
|
||||
|
||||
ColorTemp () : temp(-1.), green(-1.), equal (1.), method("Custom") {}
|
||||
explicit ColorTemp (double e) : temp(-1.), green(-1.), equal (e), method("Custom") {}
|
||||
ColorTemp (double t, double g, double e, const std::string &m);
|
||||
ColorTemp (double mulr, double mulg, double mulb, double e);
|
||||
ColorTemp (double t, double g, double e, const std::string &m, StandardObserver o);
|
||||
ColorTemp (double mulr, double mulg, double mulb, double e, StandardObserver observer);
|
||||
static void tempxy(bool separated, int repref, float **Tx, float **Ty, float **Tz, float **Ta, float **Tb, float **TL, double *TX, double *TY, double *TZ, const procparams::WBParams & wbpar);
|
||||
|
||||
void update (const double rmul, const double gmul, const double bmul, const double equal, const double tempBias=0.0)
|
||||
void update (const double rmul, const double gmul, const double bmul, const double equal, StandardObserver observer, const double tempBias=0.0)
|
||||
{
|
||||
this->equal = equal;
|
||||
mul2temp (rmul, gmul, bmul, this->equal, temp, green);
|
||||
this->observer = observer;
|
||||
mul2temp (rmul, gmul, bmul, this->equal, observer, temp, green);
|
||||
if (tempBias != 0.0 && tempBias >= -1.0 && tempBias <= 1.0) {
|
||||
temp += temp * tempBias;
|
||||
}
|
||||
}
|
||||
void useDefaults (const double equal)
|
||||
void useDefaults (const double equal, StandardObserver observer)
|
||||
{
|
||||
temp = 6504; // Values copied from procparams.cc
|
||||
green = 1.0;
|
||||
this->equal = equal;
|
||||
this->observer = observer;
|
||||
}
|
||||
|
||||
inline std::string getMethod() const
|
||||
@ -89,14 +97,20 @@ public:
|
||||
{
|
||||
return equal;
|
||||
}
|
||||
inline StandardObserver getObserver() const
|
||||
{
|
||||
return observer;
|
||||
}
|
||||
|
||||
ColorTemp convertObserver(StandardObserver observer) const;
|
||||
|
||||
void getMultipliers (double &mulr, double &mulg, double &mulb) const
|
||||
{
|
||||
temp2mul (temp, green, equal, mulr, mulg, mulb);
|
||||
temp2mul (temp, green, equal, observer, mulr, mulg, mulb);
|
||||
}
|
||||
|
||||
void mul2temp (const double rmul, const double gmul, const double bmul, const double equal, double& temp, double& green) const;
|
||||
static void temp2mulxyz (double tem, const std::string &method, double &Xxyz, double &Zxyz);
|
||||
void mul2temp (const double rmul, const double gmul, const double bmul, const double equal, StandardObserver observer, double& temp, double& green) const;
|
||||
static void temp2mulxyz (double tem, const std::string &method, StandardObserver observer, double &Xxyz, double &Zxyz);
|
||||
|
||||
static void cieCAT02(double Xw, double Yw, double Zw, double &CAM02BB00, double &CAM02BB01, double &CAM02BB02, double &CAM02BB10, double &CAM02BB11, double &CAM02BB12, double &CAM02BB20, double &CAM02BB21, double &CAM02BB22, double adap );
|
||||
static void cieCAT02float(float Xw, float Yw, float Zw, float &CAM02BB00, float &CAM02BB01, float &CAM02BB02, float &CAM02BB10, float &CAM02BB11, float &CAM02BB12, float &CAM02BB20, float &CAM02BB21, float &CAM02BB22, float adap);
|
||||
@ -104,7 +118,7 @@ public:
|
||||
|
||||
bool operator== (const ColorTemp& other) const
|
||||
{
|
||||
return fabs(temp - other.temp) < 1e-10 && fabs(green - other.green) < 1e-10;
|
||||
return fabs(temp - other.temp) < 1e-10 && fabs(green - other.green) < 1e-10 && observer != other.observer;
|
||||
}
|
||||
bool operator!= (const ColorTemp& other) const
|
||||
{
|
||||
|
@ -340,7 +340,7 @@ bool rtengine::ImProcFunctions::filmNegativeProcess(
|
||||
imgsrc->getWBMults(currWB, params->raw, scale_mul, autoGainComp, rm, gm, bm);
|
||||
|
||||
float rm2, gm2, bm2;
|
||||
imgsrc->getWBMults(rtengine::ColorTemp(3500., 1., 1., "Custom"), params->raw, scale_mul, autoGainComp, rm2, gm2, bm2);
|
||||
imgsrc->getWBMults(rtengine::ColorTemp(3500., 1., 1., "Custom", currWB.getObserver()), params->raw, scale_mul, autoGainComp, rm2, gm2, bm2);
|
||||
float mg = rtengine::max(rm2, gm2, bm2);
|
||||
rm2 /= mg;
|
||||
gm2 /= mg;
|
||||
@ -611,7 +611,7 @@ void rtengine::Thumbnail::processFilmNegativeV2(
|
||||
// as in the main image processing.
|
||||
|
||||
double r, g, b;
|
||||
ColorTemp(3500., 1., 1., "Custom").getMultipliers(r, g, b);
|
||||
ColorTemp(3500., 1., 1., "Custom", params.wb.observer).getMultipliers(r, g, b);
|
||||
//iColorMatrix is cam_rgb
|
||||
const double rm = camwbRed / (iColorMatrix[0][0] * r + iColorMatrix[0][1] * g + iColorMatrix[0][2] * b);
|
||||
const double gm = camwbGreen / (iColorMatrix[1][0] * r + iColorMatrix[1][1] * g + iColorMatrix[1][2] * b);
|
||||
|
@ -229,7 +229,7 @@ void mappingToCurve(const std::vector<int> &mapping, std::vector<double> &curve)
|
||||
} // namespace
|
||||
|
||||
|
||||
void RawImageSource::getAutoMatchedToneCurve(const ColorManagementParams &cp, std::vector<double> &outCurve)
|
||||
void RawImageSource::getAutoMatchedToneCurve(const ColorManagementParams &cp, StandardObserver observer, std::vector<double> &outCurve)
|
||||
{
|
||||
BENCHFUN
|
||||
|
||||
@ -313,7 +313,7 @@ void RawImageSource::getAutoMatchedToneCurve(const ColorManagementParams &cp, st
|
||||
eSensorType sensor_type;
|
||||
double scale;
|
||||
int w = fw / skip, h = fh / skip;
|
||||
std::unique_ptr<Thumbnail> thumb(Thumbnail::loadFromRaw(getFileName(), rml, sensor_type, w, h, 1, false, false, true));
|
||||
std::unique_ptr<Thumbnail> thumb(Thumbnail::loadFromRaw(getFileName(), rml, sensor_type, w, h, 1, false, observer, false, true));
|
||||
if (!thumb) {
|
||||
if (settings->verbose) {
|
||||
std::cout << "histogram matching: raw decoding failed, generating a neutral curve" << std::endl;
|
||||
|
@ -119,9 +119,9 @@ public:
|
||||
virtual void getAutoWBMultipliers (double &rm, double &gm, double &bm) = 0;
|
||||
virtual void getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double & greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const procparams::WBParams & wbpar, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw, const procparams::ToneCurveParams &hrp) = 0;
|
||||
virtual ColorTemp getWB () const = 0;
|
||||
virtual ColorTemp getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal) = 0;
|
||||
virtual ColorTemp getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal, StandardObserver observer) = 0;
|
||||
virtual void WBauto(double &tempref, double &greenref, array2D<float> &redloc, array2D<float> &greenloc, array2D<float> &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, double &tempitc, double &greenitc, float &studgood, bool &twotimes, const procparams::WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw, const procparams::ToneCurveParams &hrp) = 0;
|
||||
virtual void getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w) = 0;
|
||||
virtual void getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, const procparams::WBParams & wbpar) = 0;
|
||||
|
||||
virtual double getDefGain () const
|
||||
{
|
||||
@ -167,7 +167,7 @@ public:
|
||||
}
|
||||
|
||||
// for RAW files, compute a tone curve using histogram matching on the embedded thumbnail
|
||||
virtual void getAutoMatchedToneCurve(const procparams::ColorManagementParams &cp, std::vector<double> &outCurve)
|
||||
virtual void getAutoMatchedToneCurve(const procparams::ColorManagementParams &cp, StandardObserver observer, std::vector<double> &outCurve)
|
||||
{
|
||||
outCurve = { 0.0 };
|
||||
}
|
||||
|
@ -489,7 +489,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange)
|
||||
|
||||
if (todo & (M_INIT | M_LINDENOISE | M_HDR)) {
|
||||
if (params->wb.method == "autitcgreen") {
|
||||
imgsrc->getrgbloc(0, 0, fh, fw, 0, 0, fh, fw);
|
||||
imgsrc->getrgbloc(0, 0, fh, fw, 0, 0, fh, fw, params->wb);
|
||||
}
|
||||
}
|
||||
|
||||
@ -522,7 +522,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange)
|
||||
printf("Applying white balance, color correction & sRBG conversion...\n");
|
||||
}
|
||||
|
||||
currWB = ColorTemp(params->wb.temperature, params->wb.green, params->wb.equal, params->wb.method);
|
||||
currWB = ColorTemp(params->wb.temperature, params->wb.green, params->wb.equal, params->wb.method, params->wb.observer);
|
||||
float studgood = 1000.f;
|
||||
|
||||
if (!params->wb.enabled) {
|
||||
@ -531,7 +531,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange)
|
||||
currWB = imgsrc->getWB();
|
||||
lastAwbauto = ""; //reinitialize auto
|
||||
} else if (autowb) {
|
||||
if (params->wb.method == "autitcgreen" || lastAwbEqual != params->wb.equal || lastAwbTempBias != params->wb.tempBias || lastAwbauto != params->wb.method) {
|
||||
if (params->wb.method == "autitcgreen" || lastAwbEqual != params->wb.equal || lastAwbObserver != params->wb.observer || lastAwbTempBias != params->wb.tempBias || lastAwbauto != params->wb.method) {
|
||||
double rm, gm, bm;
|
||||
double tempitc = 5000.f;
|
||||
double greenitc = 1.;
|
||||
@ -547,7 +547,9 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange)
|
||||
if (params->wb.method == "autitcgreen") {
|
||||
params->wb.temperature = tempitc;
|
||||
params->wb.green = greenitc;
|
||||
currWB = ColorTemp(params->wb.temperature, params->wb.green, 1., params->wb.method);
|
||||
currWB = ColorTemp(params->wb.temperature, params->wb.green, 1., params->wb.method, params->wb.observer);
|
||||
//printf("tempitc=%f greitc=%f\n", tempitc, greenitc);
|
||||
|
||||
currWB.getMultipliers(rm, gm, bm);
|
||||
}
|
||||
|
||||
@ -558,15 +560,17 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange)
|
||||
bias = 0.;
|
||||
}
|
||||
|
||||
autoWB.update(rm, gm, bm, params->wb.equal, bias);
|
||||
autoWB.update(rm, gm, bm, params->wb.equal, params->wb.observer, bias);
|
||||
lastAwbEqual = params->wb.equal;
|
||||
lastAwbObserver = params->wb.observer;
|
||||
lastAwbTempBias = params->wb.tempBias;
|
||||
lastAwbauto = params->wb.method;
|
||||
} else {
|
||||
lastAwbEqual = -1.;
|
||||
lastAwbObserver = ColorTemp::DEFAULT_OBSERVER;
|
||||
lastAwbTempBias = 0.0;
|
||||
lastAwbauto = "";
|
||||
autoWB.useDefaults(params->wb.equal);
|
||||
autoWB.useDefaults(params->wb.equal, params->wb.observer);
|
||||
}
|
||||
|
||||
|
||||
@ -574,17 +578,24 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange)
|
||||
|
||||
currWB = autoWB;
|
||||
}
|
||||
double rw = 1.;
|
||||
double gw = 1.;
|
||||
double bw = 1.;
|
||||
|
||||
if (params->wb.enabled) {
|
||||
params->wb.temperature = currWB.getTemp();
|
||||
currWB = currWB.convertObserver(params->wb.observer);
|
||||
params->wb.temperature = static_cast<int>(currWB.getTemp());
|
||||
params->wb.green = currWB.getGreen();
|
||||
currWB.getMultipliers(rw, gw, bw);
|
||||
imgsrc->wbMul2Camera(rw, gw, bw);
|
||||
// printf("ra=%f ga=%f ba=%f\n", rw, gw, bw);
|
||||
}
|
||||
|
||||
if (autowb && awbListener) {
|
||||
if (awbListener) {
|
||||
if (params->wb.method == "autitcgreen") {
|
||||
awbListener->WBChanged(params->wb.temperature, params->wb.green, studgood);
|
||||
} else if (params->wb.method == "autold") {
|
||||
awbListener->WBChanged(params->wb.temperature, params->wb.green, -1.f);
|
||||
awbListener->WBChanged(params->wb.temperature, params->wb.green, rw, gw, bw, studgood);
|
||||
} else {
|
||||
awbListener->WBChanged(params->wb.temperature, params->wb.green, rw, gw, bw, -1.f);
|
||||
}
|
||||
}
|
||||
|
||||
@ -782,7 +793,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange)
|
||||
|
||||
if (params->toneCurve.histmatching) {
|
||||
if (!params->toneCurve.fromHistMatching) {
|
||||
imgsrc->getAutoMatchedToneCurve(params->icm, params->toneCurve.curve);
|
||||
imgsrc->getAutoMatchedToneCurve(params->icm, params->wb.observer, params->toneCurve.curve);
|
||||
}
|
||||
|
||||
if (params->toneCurve.autoexp) {
|
||||
@ -2452,11 +2463,11 @@ bool ImProcCoordinator::updateWaveforms()
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ImProcCoordinator::getAutoWB(double& temp, double& green, double equal, double tempBias)
|
||||
bool ImProcCoordinator::getAutoWB(double& temp, double& green, double equal, StandardObserver observer, double tempBias)
|
||||
{
|
||||
|
||||
if (imgsrc) {
|
||||
if (lastAwbEqual != equal || lastAwbTempBias != tempBias || lastAwbauto != params->wb.method) {
|
||||
if (lastAwbEqual != equal || lastAwbObserver != observer || lastAwbTempBias != tempBias || lastAwbauto != params->wb.method) {
|
||||
// Issue 2500 MyMutex::MyLock lock(minit); // Also used in crop window
|
||||
double rm, gm, bm;
|
||||
params->wb.method = "autold";//same result as before multiple Auto WB
|
||||
@ -2469,13 +2480,15 @@ bool ImProcCoordinator::getAutoWB(double& temp, double& green, double equal, dou
|
||||
imgsrc->getAutoWBMultipliersitc(tempref, greenref, tempitc, greenitc, studgood, 0, 0, fh, fw, 0, 0, fh, fw, rm, gm, bm, params->wb, params->icm, params->raw, params->toneCurve);
|
||||
|
||||
if (rm != -1) {
|
||||
autoWB.update(rm, gm, bm, equal, tempBias);
|
||||
autoWB.update(rm, gm, bm, equal, observer, tempBias);
|
||||
lastAwbEqual = equal;
|
||||
lastAwbObserver = observer;
|
||||
lastAwbTempBias = tempBias;
|
||||
lastAwbauto = params->wb.method;
|
||||
} else {
|
||||
lastAwbEqual = -1.;
|
||||
autoWB.useDefaults(equal);
|
||||
lastAwbObserver = ColorTemp::DEFAULT_OBSERVER;
|
||||
autoWB.useDefaults(equal, observer);
|
||||
lastAwbauto = "";
|
||||
lastAwbTempBias = 0.0;
|
||||
}
|
||||
@ -2492,12 +2505,13 @@ bool ImProcCoordinator::getAutoWB(double& temp, double& green, double equal, dou
|
||||
}
|
||||
}
|
||||
|
||||
void ImProcCoordinator::getCamWB(double& temp, double& green)
|
||||
void ImProcCoordinator::getCamWB(double& temp, double& green, StandardObserver observer)
|
||||
{
|
||||
|
||||
if (imgsrc) {
|
||||
temp = imgsrc->getWB().getTemp();
|
||||
green = imgsrc->getWB().getGreen();
|
||||
const ColorTemp color_temp = imgsrc->getWB().convertObserver(observer);
|
||||
temp = color_temp.getTemp();
|
||||
green = color_temp.getGreen();
|
||||
}
|
||||
}
|
||||
|
||||
@ -2519,8 +2533,8 @@ void ImProcCoordinator::getSpotWB(int x, int y, int rect, double& temp, double&
|
||||
|
||||
int tr = getCoarseBitMask(params->coarse);
|
||||
|
||||
ret = imgsrc->getSpotWB(red, green, blue, tr, params->wb.equal);
|
||||
currWB = ColorTemp(params->wb.temperature, params->wb.green, params->wb.equal, params->wb.method);
|
||||
ret = imgsrc->getSpotWB(red, green, blue, tr, params->wb.equal, params->wb.observer);
|
||||
currWB = ColorTemp(params->wb.temperature, params->wb.green, params->wb.equal, params->wb.method, params->wb.observer);
|
||||
//double rr,gg,bb;
|
||||
//currWB.getMultipliers(rr,gg,bb);
|
||||
|
||||
@ -2626,23 +2640,25 @@ void ImProcCoordinator::saveInputICCReference(const Glib::ustring& fname, bool a
|
||||
imgsrc->preprocess(ppar.raw, ppar.lensProf, ppar.coarse);
|
||||
double dummy = 0.0;
|
||||
imgsrc->demosaic(ppar.raw, false, dummy);
|
||||
ColorTemp currWB = ColorTemp(validParams->wb.temperature, validParams->wb.green, validParams->wb.equal, validParams->wb.method);
|
||||
ColorTemp currWB = ColorTemp(validParams->wb.temperature, validParams->wb.green, validParams->wb.equal, validParams->wb.method, validParams->wb.observer);
|
||||
|
||||
if (validParams->wb.method == "Camera") {
|
||||
currWB = imgsrc->getWB();
|
||||
} else if (validParams->wb.method == "autold") {
|
||||
if (lastAwbEqual != validParams->wb.equal || lastAwbTempBias != validParams->wb.tempBias) {
|
||||
if (lastAwbEqual != validParams->wb.equal || lastAwbObserver != validParams->wb.observer || lastAwbTempBias != validParams->wb.tempBias) {
|
||||
double rm, gm, bm;
|
||||
imgsrc->getAutoWBMultipliers(rm, gm, bm);
|
||||
|
||||
if (rm != -1.) {
|
||||
autoWB.update(rm, gm, bm, validParams->wb.equal, validParams->wb.tempBias);
|
||||
autoWB.update(rm, gm, bm, validParams->wb.equal, validParams->wb.observer, validParams->wb.tempBias);
|
||||
lastAwbEqual = validParams->wb.equal;
|
||||
lastAwbObserver = validParams->wb.observer;
|
||||
lastAwbTempBias = validParams->wb.tempBias;
|
||||
} else {
|
||||
lastAwbEqual = -1.;
|
||||
lastAwbObserver = ColorTemp::DEFAULT_OBSERVER;
|
||||
lastAwbTempBias = 0.0;
|
||||
autoWB.useDefaults(validParams->wb.equal);
|
||||
autoWB.useDefaults(validParams->wb.equal, validParams->wb.observer);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -80,6 +80,7 @@ protected:
|
||||
ColorTemp currWBitc;
|
||||
|
||||
double lastAwbEqual;
|
||||
StandardObserver lastAwbObserver{ColorTemp::DEFAULT_OBSERVER};
|
||||
double lastAwbTempBias;
|
||||
Glib::ustring lastAwbauto;
|
||||
|
||||
@ -433,8 +434,8 @@ public:
|
||||
|
||||
void setTweakOperator (TweakOperator *tOperator) override;
|
||||
void unsetTweakOperator (TweakOperator *tOperator) override;
|
||||
bool getAutoWB (double& temp, double& green, double equal, double tempBias) override;
|
||||
void getCamWB (double& temp, double& green) override;
|
||||
bool getAutoWB (double& temp, double& green, double equal, StandardObserver observer, double tempBias) override;
|
||||
void getCamWB (double& temp, double& green, StandardObserver observer) override;
|
||||
void getSpotWB (int x, int y, int rectSize, double& temp, double& green) override;
|
||||
bool getFilmNegativeSpot(int x, int y, int spotSize, FilmNegativeParams::RGB &refInput, FilmNegativeParams::RGB &refOutput) override;
|
||||
void getAutoCrop (double ratio, int &x, int &y, int &w, int &h) override;
|
||||
|
@ -552,9 +552,9 @@ void ImProcFunctions::ciecam_02float(CieImage* ncie, float adap, int pW, int pwb
|
||||
|| (params->dirpyrequalizer.enabled && settings->autocielab) || (params->defringe.enabled && settings->autocielab) || (params->sharpenMicro.enabled && settings->autocielab)
|
||||
|| (params->impulseDenoise.enabled && settings->autocielab) || (params->colorappearance.badpixsl > 0 && settings->autocielab));
|
||||
|
||||
ColorTemp::temp2mulxyz(params->wb.temperature, params->wb.method, Xw, Zw); //compute white Xw Yw Zw : white current WB
|
||||
ColorTemp::temp2mulxyz(params->colorappearance.tempout, "Custom", Xwout, Zwout);
|
||||
ColorTemp::temp2mulxyz(params->colorappearance.tempsc, "Custom", Xwsc, Zwsc);
|
||||
ColorTemp::temp2mulxyz(params->wb.temperature, params->wb.method, params->wb.observer, Xw, Zw); //compute white Xw Yw Zw : white current WB
|
||||
ColorTemp::temp2mulxyz(params->colorappearance.tempout, "Custom", params->wb.observer, Xwout, Zwout);
|
||||
ColorTemp::temp2mulxyz(params->colorappearance.tempsc, "Custom", params->wb.observer, Xwsc, Zwsc);
|
||||
|
||||
//viewing condition for surrsrc
|
||||
if (params->colorappearance.surrsrc == "Average") {
|
||||
@ -5589,7 +5589,7 @@ double ImProcFunctions::getAutoDistor(const Glib::ustring &fname, int thumb_size
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
Thumbnail* raw = rtengine::Thumbnail::loadFromRaw(fname, ri, sensorType, w_raw, h_raw, 1, 1.0, FALSE);
|
||||
Thumbnail* raw = rtengine::Thumbnail::loadFromRaw(fname, ri, sensorType, w_raw, h_raw, 1, 1.0, ColorTemp::DEFAULT_OBSERVER, FALSE);
|
||||
|
||||
if (!raw) {
|
||||
delete thumb;
|
||||
|
@ -2804,9 +2804,9 @@ void ImProcFunctions::ciecamloc_02float(const struct local_params& lp, int sp, L
|
||||
}
|
||||
}
|
||||
|
||||
ColorTemp::temp2mulxyz(params->wb.temperature, params->wb.method, Xw, Zw); //compute white Xw Yw Zw : white current WB
|
||||
ColorTemp::temp2mulxyz(tempo, "Custom", Xwout, Zwout);
|
||||
ColorTemp::temp2mulxyz(5000, "Custom", Xwsc, Zwsc);
|
||||
ColorTemp::temp2mulxyz(params->wb.temperature, params->wb.method, params->wb.observer, Xw, Zw); //compute white Xw Yw Zw : white current WB
|
||||
ColorTemp::temp2mulxyz(tempo, "Custom", params->wb.observer, Xwout, Zwout);
|
||||
ColorTemp::temp2mulxyz(5000, "Custom", params->wb.observer, Xwsc, Zwsc);
|
||||
|
||||
//viewing condition for surrsrc
|
||||
f = 1.00f;
|
||||
|
@ -42,20 +42,20 @@ PreviewImage::PreviewImage (const Glib::ustring &fname, const Glib::ustring &ext
|
||||
|
||||
if (ext.lowercase() == "jpg" || ext.lowercase() == "jpeg") {
|
||||
// int deg = infoFromImage (fname);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, width, height, 1, 1., true);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, width, height, 1, 1., ColorTemp::DEFAULT_OBSERVER, true);
|
||||
|
||||
if (tpp) {
|
||||
data = tpp->getImage8Data();
|
||||
}
|
||||
} else if (ext.lowercase() == "png") {
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, width, height, 1, 1., true);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, width, height, 1, 1., ColorTemp::DEFAULT_OBSERVER, true);
|
||||
|
||||
if (tpp) {
|
||||
data = tpp->getImage8Data();
|
||||
}
|
||||
} else if (ext.lowercase() == "tif" || ext.lowercase() == "tiff") {
|
||||
// int deg = infoFromImage (fname);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, width, height, 1, 1., true);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, width, height, 1, 1., ColorTemp::DEFAULT_OBSERVER, true);
|
||||
|
||||
if (tpp) {
|
||||
data = tpp->getImage8Data();
|
||||
|
@ -27,6 +27,7 @@
|
||||
#include <glibmm/keyfile.h>
|
||||
|
||||
#include "color.h"
|
||||
#include "colortemp.h"
|
||||
#include "curves.h"
|
||||
#include "procparams.h"
|
||||
#include "utils.h"
|
||||
@ -1331,7 +1332,19 @@ WBParams::WBParams() :
|
||||
temperature(6504),
|
||||
green(1.0),
|
||||
equal(1.0),
|
||||
tempBias(0.0)
|
||||
tempBias(0.0),
|
||||
observer(ColorTemp::DEFAULT_OBSERVER),
|
||||
itcwb_thres(34),
|
||||
itcwb_precis(3),
|
||||
itcwb_size(3),
|
||||
itcwb_delta(2),
|
||||
itcwb_fgreen(5),
|
||||
itcwb_rgreen(1),
|
||||
itcwb_nopurple(true),
|
||||
itcwb_sorted(false),
|
||||
itcwb_forceextra(false),
|
||||
itcwb_sampling(false)
|
||||
|
||||
{
|
||||
}
|
||||
|
||||
@ -1351,6 +1364,7 @@ bool WBParams::isPanningRelatedChange(const WBParams& other) const
|
||||
&& green == other.green
|
||||
&& equal == other.equal
|
||||
&& tempBias == other.tempBias
|
||||
&& observer == other.observer
|
||||
)
|
||||
)
|
||||
);
|
||||
@ -1364,7 +1378,19 @@ bool WBParams::operator ==(const WBParams& other) const
|
||||
&& temperature == other.temperature
|
||||
&& green == other.green
|
||||
&& equal == other.equal
|
||||
&& tempBias == other.tempBias;
|
||||
&& tempBias == other.tempBias
|
||||
&& observer == other.observer
|
||||
&& itcwb_thres == other.itcwb_thres
|
||||
&& itcwb_precis == other.itcwb_precis
|
||||
&& itcwb_size == other.itcwb_size
|
||||
&& itcwb_delta == other.itcwb_delta
|
||||
&& itcwb_fgreen == other.itcwb_fgreen
|
||||
&& itcwb_rgreen == other.itcwb_rgreen
|
||||
&& itcwb_nopurple == other.itcwb_nopurple
|
||||
&& itcwb_sorted == other.itcwb_sorted
|
||||
&& itcwb_forceextra == other.itcwb_forceextra
|
||||
&& itcwb_sampling == other.itcwb_sampling;
|
||||
|
||||
}
|
||||
|
||||
bool WBParams::operator !=(const WBParams& other) const
|
||||
@ -6108,6 +6134,17 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo
|
||||
saveToKeyfile(!pedited || pedited->wb.green, "White Balance", "Green", wb.green, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.equal, "White Balance", "Equal", wb.equal, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.tempBias, "White Balance", "TemperatureBias", wb.tempBias, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.observer, "White Balance", "StandardObserver", Glib::ustring(wb.observer == StandardObserver::TWO_DEGREES ? "TWO_DEGREES" : "TEN_DEGREES"), keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_thres, "White Balance", "Itcwb_thres", wb.itcwb_thres, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_precis, "White Balance", "Itcwb_precis", wb.itcwb_precis, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_size, "White Balance", "Itcwb_size", wb.itcwb_size, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_delta, "White Balance", "Itcwb_delta", wb.itcwb_delta, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_fgreen, "White Balance", "Itcwb_findgreen", wb.itcwb_fgreen, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_rgreen, "White Balance", "Itcwb_rangegreen", wb.itcwb_rgreen, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_nopurple, "White Balance", "Itcwb_nopurple", wb.itcwb_nopurple, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_sorted, "White Balance", "Itcwb_sorted", wb.itcwb_sorted, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_forceextra, "White Balance", "Itcwb_forceextra", wb.itcwb_forceextra, keyFile);
|
||||
saveToKeyfile(!pedited || pedited->wb.itcwb_sampling, "White Balance", "Itcwb_sampling", wb.itcwb_sampling, keyFile);
|
||||
|
||||
// Colorappearance
|
||||
saveToKeyfile(!pedited || pedited->colorappearance.enabled, "Color appearance", "Enabled", colorappearance.enabled, keyFile);
|
||||
@ -8039,6 +8076,17 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited)
|
||||
assignFromKeyfile(keyFile, "Vibrance", "PastSatTog", pedited, vibrance.pastsattog, pedited->vibrance.pastsattog);
|
||||
assignFromKeyfile(keyFile, "Vibrance", "SkinTonesCurve", pedited, vibrance.skintonescurve, pedited->vibrance.skintonescurve);
|
||||
}
|
||||
if (ppVersion <= 346) { // 5.8 and earlier.
|
||||
wb.observer = StandardObserver::TWO_DEGREES;
|
||||
if (pedited) {
|
||||
pedited->wb.observer = true;
|
||||
}
|
||||
} else if (ppVersion <= 349) { // 5.9
|
||||
wb.observer = StandardObserver::TEN_DEGREES;
|
||||
if (pedited) {
|
||||
pedited->wb.observer = true;
|
||||
}
|
||||
}
|
||||
if (keyFile.has_group("White Balance")) {
|
||||
assignFromKeyfile(keyFile, "White Balance", "Enabled", pedited, wb.enabled, pedited->wb.enabled);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Setting", pedited, wb.method, pedited->wb.method);
|
||||
@ -8049,6 +8097,29 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited)
|
||||
assignFromKeyfile(keyFile, "White Balance", "Green", pedited, wb.green, pedited->wb.green);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Equal", pedited, wb.equal, pedited->wb.equal);
|
||||
assignFromKeyfile(keyFile, "White Balance", "TemperatureBias", pedited, wb.tempBias, pedited->wb.tempBias);
|
||||
Glib::ustring standard_observer;
|
||||
assignFromKeyfile(keyFile, "White Balance", "StandardObserver", pedited, standard_observer, pedited->wb.observer);
|
||||
if (standard_observer == "TEN_DEGREES") {
|
||||
wb.observer = StandardObserver::TEN_DEGREES;
|
||||
} else if (standard_observer == "TWO_DEGREES") {
|
||||
wb.observer = StandardObserver::TWO_DEGREES;
|
||||
}
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_thres", pedited, wb.itcwb_thres, pedited->wb.itcwb_thres);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_precis", pedited, wb.itcwb_precis, pedited->wb.itcwb_precis);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_size", pedited, wb.itcwb_size, pedited->wb.itcwb_size);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_delta", pedited, wb.itcwb_delta, pedited->wb.itcwb_delta);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_findgreen", pedited, wb.itcwb_fgreen, pedited->wb.itcwb_fgreen);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_rangegreen", pedited, wb.itcwb_rgreen, pedited->wb.itcwb_rgreen);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_nopurple", pedited, wb.itcwb_nopurple, pedited->wb.itcwb_nopurple);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_sorted", pedited, wb.itcwb_sorted, pedited->wb.itcwb_sorted);
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_forceextra", pedited, wb.itcwb_forceextra, pedited->wb.itcwb_forceextra);
|
||||
if (ppVersion <= 349) { // 5.9 and earlier.
|
||||
wb.itcwb_sampling = true;
|
||||
if (pedited) {
|
||||
pedited->wb.itcwb_sampling = true;
|
||||
}
|
||||
}
|
||||
assignFromKeyfile(keyFile, "White Balance", "Itcwb_sampling", pedited, wb.itcwb_sampling, pedited->wb.itcwb_sampling);
|
||||
}
|
||||
|
||||
if (keyFile.has_group("Defringing")) {
|
||||
|
@ -59,6 +59,8 @@ class LocLLmaskexpCurve;
|
||||
class LocCCmaskexpCurve;
|
||||
class LocHHmaskexpCurve;
|
||||
|
||||
enum class StandardObserver;
|
||||
|
||||
enum RenderingIntent : int {
|
||||
RI_PERCEPTUAL = INTENT_PERCEPTUAL,
|
||||
RI_RELATIVE = INTENT_RELATIVE_COLORIMETRIC,
|
||||
@ -639,6 +641,17 @@ struct WBParams {
|
||||
double green;
|
||||
double equal;
|
||||
double tempBias;
|
||||
StandardObserver observer;
|
||||
int itcwb_thres;
|
||||
int itcwb_precis;
|
||||
int itcwb_size;
|
||||
int itcwb_delta;
|
||||
int itcwb_fgreen;
|
||||
int itcwb_rgreen;
|
||||
bool itcwb_nopurple;
|
||||
bool itcwb_sorted;
|
||||
bool itcwb_forceextra;
|
||||
bool itcwb_sampling;
|
||||
|
||||
WBParams();
|
||||
|
||||
|
@ -847,7 +847,6 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima
|
||||
const bool doClip = (chmax[0] >= clmax[0] || chmax[1] >= clmax[1] || chmax[2] >= clmax[2]) && !hrp.hrenabled && hrp.clampOOG;
|
||||
bool doHr = (hrp.hrenabled && !iscolor);
|
||||
if (hrp.hrenabled && iscolor) {
|
||||
|
||||
if(hrp.method == "Coloropp" && opposed == 1) {//force Inpaint opposed if WB change, and opposed limited tne number to 1
|
||||
rgbSourceModified = false;
|
||||
}
|
||||
@ -1297,7 +1296,7 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly)
|
||||
double cam_r = imatrices.rgb_cam[0][0] * camwb_red + imatrices.rgb_cam[0][1] * camwb_green + imatrices.rgb_cam[0][2] * camwb_blue;
|
||||
double cam_g = imatrices.rgb_cam[1][0] * camwb_red + imatrices.rgb_cam[1][1] * camwb_green + imatrices.rgb_cam[1][2] * camwb_blue;
|
||||
double cam_b = imatrices.rgb_cam[2][0] * camwb_red + imatrices.rgb_cam[2][1] * camwb_green + imatrices.rgb_cam[2][2] * camwb_blue;
|
||||
camera_wb = ColorTemp (cam_r, cam_g, cam_b, 1.); // as shot WB
|
||||
camera_wb = ColorTemp (cam_r, cam_g, cam_b, 1., ColorTemp::DEFAULT_OBSERVER); // as shot WB
|
||||
|
||||
if (settings->verbose) {
|
||||
printf("Raw As Shot White balance: temp %f, tint %f\n", camera_wb.getTemp(), camera_wb.getGreen());
|
||||
@ -1384,7 +1383,7 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le
|
||||
const double ref_r = imatrices.rgb_cam[0][0] * refwb_red + imatrices.rgb_cam[0][1] * refwb_green + imatrices.rgb_cam[0][2] * refwb_blue;
|
||||
const double ref_g = imatrices.rgb_cam[1][0] * refwb_red + imatrices.rgb_cam[1][1] * refwb_green + imatrices.rgb_cam[1][2] * refwb_blue;
|
||||
const double ref_b = imatrices.rgb_cam[2][0] * refwb_red + imatrices.rgb_cam[2][1] * refwb_green + imatrices.rgb_cam[2][2] * refwb_blue;
|
||||
const ColorTemp ReferenceWB = ColorTemp (ref_r, ref_g, ref_b, 1.);
|
||||
const ColorTemp ReferenceWB = ColorTemp (ref_r, ref_g, ref_b, 1., ColorTemp::DEFAULT_OBSERVER);
|
||||
|
||||
if (settings->verbose) {
|
||||
printf("Raw Reference white balance: temp %f, tint %f, multipliers [%f %f %f | %f %f %f]\n", ReferenceWB.getTemp(), ReferenceWB.getGreen(), ref_r, ref_g, ref_b, refwb_red, refwb_blue, refwb_green);
|
||||
@ -4037,6 +4036,475 @@ void RawImageSource::getRowStartEnd (int x, int &start, int &end)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void histoxyY_low(int bfhitc, int bfwitc, const array2D<float> & xc, const array2D<float> & yc, const array2D<float> & Yc, LUTf &xxx, LUTf &yyy, LUTf &YYY, LUTu &histxy)
|
||||
{
|
||||
//calculate histogram x y in a range of 190 colors
|
||||
//this "choice" are guided by generally colors who are in nature skin, sky, etc. in those cases "steps" are small
|
||||
// of course we can change to be more precise
|
||||
#ifdef _OPENMP
|
||||
#pragma omp parallel
|
||||
#endif
|
||||
{
|
||||
LUTu histxythr(histxy.getSize());
|
||||
histxythr.clear();
|
||||
LUTf xxxthr(xxx.getSize());
|
||||
xxxthr.clear();
|
||||
LUTf yyythr(yyy.getSize());
|
||||
yyythr.clear();
|
||||
LUTf YYYthr(YYY.getSize());
|
||||
YYYthr.clear();
|
||||
#ifdef _OPENMP
|
||||
#pragma omp for schedule(dynamic, 4) nowait
|
||||
#endif
|
||||
for (int y = 0; y < bfhitc ; y++) {
|
||||
for (int x = 0; x < bfwitc ; x++) {
|
||||
int nh = -1;
|
||||
if (xc[y][x] < 0.12f && xc[y][x] > 0.03f && yc[y][x] > 0.1f) { // near Prophoto
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 0;
|
||||
//blue hard
|
||||
} else if (yc[y][x] < 0.3f) {
|
||||
nh = 1;
|
||||
//blue
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 2;
|
||||
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
//blue green
|
||||
nh = 3;
|
||||
} else if (yc[y][x] < 0.6f) {
|
||||
nh = 4;
|
||||
} else if (yc[y][x] < 0.82f) {
|
||||
//green
|
||||
nh = 5;
|
||||
}
|
||||
} else if (xc[y][x] < 0.24f && yc[y][x] > 0.05f) {
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 6;
|
||||
} else if (yc[y][x] < 0.3f) {
|
||||
nh = 7;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 8;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 9;
|
||||
} else if (yc[y][x] < 0.6f) {
|
||||
nh = 10;
|
||||
} else if (yc[y][x] < 0.75f) {
|
||||
nh = 11;
|
||||
}
|
||||
} else if (xc[y][x] < 0.28f && yc[y][x] > 0.1f) {//blue sky and other
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 12;
|
||||
} else if (yc[y][x] < 0.25f) {
|
||||
nh = 13;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 14;
|
||||
} else if (yc[y][x] < 0.33f) {
|
||||
nh = 15;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 16;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 17;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 18;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 19;
|
||||
} else if (yc[y][x] < 0.6f) {
|
||||
nh = 20;
|
||||
} else if (yc[y][x] < 0.75f) {
|
||||
nh = 21;
|
||||
}
|
||||
} else if (xc[y][x] < 0.31f && yc[y][x] > 0.1f) {//near neutral others
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 22;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 23;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 24;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 25;
|
||||
} else if (yc[y][x] < 0.36f) {
|
||||
nh = 26;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 27;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 28;
|
||||
} else if (yc[y][x] < 0.7f) {
|
||||
nh = 29;
|
||||
}
|
||||
} else if (xc[y][x] < 0.325f && yc[y][x] > 0.1f) {//neutral 34
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 30;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 31;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 32;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 33;
|
||||
} else if (yc[y][x] < 0.33f) {
|
||||
nh = 34;
|
||||
} else if (yc[y][x] < 0.335f) {
|
||||
nh = 35;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 36;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 37;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 38;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 39;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 40;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 41;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 42;
|
||||
} else if (yc[y][x] < 0.7f) {
|
||||
nh = 43;
|
||||
}
|
||||
} else if (xc[y][x] < 0.335f && yc[y][x] > 0.1f) {//neutral
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 44;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 45;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 46;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 47;
|
||||
} else if (yc[y][x] < 0.33f) {
|
||||
nh = 48;
|
||||
} else if (yc[y][x] < 0.335f) {
|
||||
nh = 49;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 50;
|
||||
} else if (yc[y][x] < 0.345f) {
|
||||
nh = 51;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 52;
|
||||
} else if (yc[y][x] < 0.355f) {
|
||||
nh = 53;
|
||||
} else if (yc[y][x] < 0.36f) {
|
||||
nh = 54;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 55;
|
||||
} else if (yc[y][x] < 0.38f) {
|
||||
nh = 56;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 57;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 58;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 59;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 60;
|
||||
} else if (yc[y][x] < 0.7f) {
|
||||
nh = 61;
|
||||
}
|
||||
} else if (xc[y][x] < 0.340f && yc[y][x] > 0.1f) {//neutral
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 62;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 63;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 64;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 65;
|
||||
} else if (yc[y][x] < 0.325f) {
|
||||
nh = 66;
|
||||
} else if (yc[y][x] < 0.33f) {
|
||||
nh = 67;
|
||||
} else if (yc[y][x] < 0.335f) {
|
||||
nh = 68;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 69;
|
||||
} else if (yc[y][x] < 0.345f) {
|
||||
nh = 70;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 71;
|
||||
} else if (yc[y][x] < 0.355f) {
|
||||
nh = 72;
|
||||
} else if (yc[y][x] < 0.36f) {
|
||||
nh = 73;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 74;
|
||||
} else if (yc[y][x] < 0.38f) {
|
||||
nh = 75;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 76;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 77;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 78;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 79;
|
||||
} else if (yc[y][x] < 0.7f) {
|
||||
nh = 80;
|
||||
}
|
||||
} else if (xc[y][x] < 0.345f && yc[y][x] > 0.1f) {//neutral 37
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 81;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 82;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 83;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 84;
|
||||
} else if (yc[y][x] < 0.33f) {
|
||||
nh = 85;
|
||||
} else if (yc[y][x] < 0.335f) {
|
||||
nh = 86;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 87;
|
||||
} else if (yc[y][x] < 0.345f) {
|
||||
nh = 88;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 89;
|
||||
} else if (yc[y][x] < 0.355f) {
|
||||
nh = 90;
|
||||
} else if (yc[y][x] < 0.36f) {
|
||||
nh = 91;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 92;
|
||||
} else if (yc[y][x] < 0.38f) {
|
||||
nh = 93;
|
||||
} else if (yc[y][x] < 0.39f) {
|
||||
nh = 94;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 95;
|
||||
} else if (yc[y][x] < 0.42f) {
|
||||
nh = 96;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 97;
|
||||
} else if (yc[y][x] < 0.48f) {
|
||||
nh = 98;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 99;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 100;
|
||||
} else if (yc[y][x] < 0.65f) {
|
||||
nh = 101;
|
||||
}
|
||||
} else if (xc[y][x] < 0.355f && yc[y][x] > 0.1f) {//neutral 37
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 102;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 103;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 104;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 105;
|
||||
} else if (yc[y][x] < 0.33f) {
|
||||
nh = 106;
|
||||
} else if (yc[y][x] < 0.335f) {
|
||||
nh = 107;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 108;
|
||||
} else if (yc[y][x] < 0.345f) {
|
||||
nh = 109;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 110;
|
||||
} else if (yc[y][x] < 0.355f) {
|
||||
nh = 111;
|
||||
} else if (yc[y][x] < 0.36f) {
|
||||
nh = 112;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 113;
|
||||
} else if (yc[y][x] < 0.38f) {
|
||||
nh = 114;
|
||||
} else if (yc[y][x] < 0.39f) {
|
||||
nh = 115;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 116;
|
||||
} else if (yc[y][x] < 0.42f) {
|
||||
nh = 117;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 118;
|
||||
} else if (yc[y][x] < 0.48f) {
|
||||
nh = 119;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 120;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 121;
|
||||
} else if (yc[y][x] < 0.65f) {
|
||||
nh = 122;
|
||||
}
|
||||
} else if (xc[y][x] < 0.365f && yc[y][x] > 0.15f) { //0.4
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 123;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 124;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 125;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 126;
|
||||
} else if (yc[y][x] < 0.33f) {
|
||||
nh = 127;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 128;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 129;
|
||||
} else if (yc[y][x] < 0.36f) {
|
||||
nh = 130;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 131;
|
||||
} else if (yc[y][x] < 0.38f) {
|
||||
nh = 132;
|
||||
} else if (yc[y][x] < 0.39f) {
|
||||
nh = 133;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 134;
|
||||
} else if (yc[y][x] < 0.42f) {
|
||||
nh = 135;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 136;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 137;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 138;
|
||||
} else if (yc[y][x] < 0.63f) {
|
||||
nh = 139;
|
||||
}
|
||||
} else if (xc[y][x] < 0.405f && yc[y][x] > 0.15f) {//45
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 140;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 141;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 142;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 143;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 144;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 145;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 146;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 147;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 148;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 149;
|
||||
} else if (yc[y][x] < 0.6f) {
|
||||
nh = 150;
|
||||
}
|
||||
} else if (xc[y][x] < 0.445f && yc[y][x] > 0.15f) {//45
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 151;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 152;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 153;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 154;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 155;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 156;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 157;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 158;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 159;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 160;
|
||||
} else if (yc[y][x] < 0.58f) {
|
||||
nh = 161;
|
||||
}
|
||||
} else if (xc[y][x] < 0.495f && yc[y][x] > 0.15f) {
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 162;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 163;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 164;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 165;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 166;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 167;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 168;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 169;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 170;
|
||||
} else if (yc[y][x] < 0.55f) {
|
||||
nh = 171;
|
||||
}
|
||||
} else if (xc[y][x] < 0.545f && yc[y][x] > 0.15f) {
|
||||
if (yc[y][x] < 0.2f) {
|
||||
nh = 172;
|
||||
} else if (yc[y][x] < 0.24f) {
|
||||
nh = 173;
|
||||
} else if (yc[y][x] < 0.29f) {
|
||||
nh = 174;
|
||||
} else if (yc[y][x] < 0.32f) {
|
||||
nh = 175;
|
||||
} else if (yc[y][x] < 0.34f) {
|
||||
nh = 176;
|
||||
} else if (yc[y][x] < 0.37f) {
|
||||
nh = 177;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 178;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 179;
|
||||
} else if (yc[y][x] < 0.5f) {
|
||||
nh = 180;
|
||||
}
|
||||
} else if (xc[y][x] < 0.595f && yc[y][x] > 0.15f) {
|
||||
if (yc[y][x] < 0.22f) {
|
||||
nh = 181;
|
||||
} else if (yc[y][x] < 0.25f) {
|
||||
nh = 182;
|
||||
} else if (yc[y][x] < 0.3f) {
|
||||
nh = 183;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 184;
|
||||
} else if (yc[y][x] < 0.4f) {
|
||||
nh = 185;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 186;
|
||||
}
|
||||
} else if (xc[y][x] < 0.65f && yc[y][x] > 0.12f) {
|
||||
if (yc[y][x] < 0.25f) {
|
||||
nh = 187;
|
||||
} else if (yc[y][x] < 0.3f) {
|
||||
nh = 188;
|
||||
} else if (yc[y][x] < 0.35f) {
|
||||
nh = 189;
|
||||
} else if (yc[y][x] < 0.45f) {
|
||||
nh = 190;
|
||||
}
|
||||
} else if (xc[y][x] < 0.75f && yc[y][x] > 0.1f) {
|
||||
nh = 191;
|
||||
}
|
||||
if (nh >= 0) {
|
||||
histxythr[nh]++;
|
||||
xxxthr[nh] += xc[y][x];
|
||||
yyythr[nh] += yc[y][x];
|
||||
YYYthr[nh] += Yc[y][x];
|
||||
}
|
||||
}
|
||||
}
|
||||
#ifdef _OPENMP
|
||||
#pragma omp critical
|
||||
#endif
|
||||
{
|
||||
histxy += histxythr;
|
||||
xxx += xxxthr;
|
||||
yyy += yyythr;
|
||||
YYY += YYYthr;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
static void histoxyY(int bfhitc, int bfwitc, const array2D<float> & xc, const array2D<float> & yc, const array2D<float> & Yc, LUTf &xxx, LUTf &yyy, LUTf &YYY, LUTu &histxy, bool purp)
|
||||
{
|
||||
// calculate histogram x y in a range of 236 colors
|
||||
@ -4654,7 +5122,7 @@ float static studentXY(const array2D<float> & YYcurr, const array2D<float> & ref
|
||||
void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, array2D<float> &redloc, array2D<float> &greenloc, array2D<float> &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, const ColorManagementParams &cmp, const RAWParams &raw, const WBParams & wbpar, const ToneCurveParams &hrp)
|
||||
{
|
||||
/*
|
||||
Copyright (c) Jacques Desmis 6 - 2018 jdesmis@gmail.com, update 1 - 2023
|
||||
Copyright (c) Jacques Desmis 6 - 2018 jdesmis@gmail.com, update 2 - 2023
|
||||
Copyright (c) Ingo Weyrich 3 - 2020 (heckflosse67@gmx.de)
|
||||
|
||||
This algorithm try to find temperature correlation between 20 to 80 colors between 201 spectral color and about 20 to 55 color found in the image between 236, I just found the idea in the web "correlate with chroma" instead of RGB grey point,but I don't use any algo found on the web.
|
||||
@ -4693,7 +5161,7 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
22) we re-adjust references color for these xyY from 20)
|
||||
23) then find all Student correlation for each couple green / temp
|
||||
24) sort these Student values, and choose the minimum
|
||||
25) then for the 3 better couple "temp / green" choose the one where green is nearest from 1.
|
||||
25) then for the 5 better couple "temp / green" choose the one where green is nearest from 1.
|
||||
|
||||
Some variables or function are not used, keep in case of
|
||||
I have test with cat02 but result are not stable enough ! why ??, therefore cat02 neutralized
|
||||
@ -4704,28 +5172,37 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
You can used it in images :flowers, landscape, portrait, skin, where illuminants are "normal" (daylight, blackbody)
|
||||
You must avoid when illuminant is non standard (fluorescent, LED...) and also, when the subject is lost in the image (some target to generate profiles).
|
||||
|
||||
You can change parameters in option.cc
|
||||
You can change parameters in White Balance - Frame adapted to Itcwb
|
||||
Itcwb_thres : 34 by default ==> number of color used in final algorithm - between 10 and max 55
|
||||
Itcwb_sorted : true by default, can improve algorithm if true, ==> sort value in something near chroma order, instead of histogram number
|
||||
Itcwb_greenrange : 0 amplitude of green variation - between 0 to 2
|
||||
Itcwb_greendeltatemp : 1 - delta temp in green iterate loop for "extra" - between 0 to 4
|
||||
Itcwb_forceextra : true by default - if true force algorithm "extra" ("extra" is used when camera wbsettings are wrong) to all images
|
||||
Itcwb_sizereference : 3 by default, can be set to 5 ==> size of reference color compare to size of histogram real color
|
||||
Itcwb_greendelta : 1 - delta temp in green iterate loop for "extra" - between 0 to 4
|
||||
Itcwb_forceextra : false by default - Use all Ciexy diagram instead of sRGB
|
||||
//Itcwb_sizereference : repalce by int maxnb 3 by default, can be set to 5 ==> size of reference color compare to size of histogram real color
|
||||
itcwb_delta : 1 by default can be set between 0 to 5 ==> delta temp to build histogram xy - if camera temp is not probably good
|
||||
itcwb_stdobserver10 : true by default - use standard observer 10°, false = standard observer 2°
|
||||
itcwb_precis : 3 by default - can be set to 3 or 9 - 3 best sampling but more time...9 "old" settings - but low differences in times with 3 instead of 9 about twice time 160ms instead of 80ms for a big raw file
|
||||
//itcwb_precis : replace by int precision = 3 by default - can be set to 3 or 9 - 3 best sampling but more time...9 "old" settings - but low differences in times with 3 instead of 9 about twice time 160ms instead of 80ms for a big raw file
|
||||
itcwb_nopurple : true default - allow to bypass highlight recovery and inpait opposed when need flowers and not purple due to highlights...
|
||||
itcwb_fgreen : 5 by default - between 3 to 6 - find the compromise student / green to reach green near of 1
|
||||
|
||||
In file options.
|
||||
use standard observer 10°, false = standard observer 2°
|
||||
*/
|
||||
// BENCHFUN
|
||||
|
||||
TMatrix wprof = ICCStore::getInstance()->workingSpaceMatrix("sRGB");
|
||||
Glib::ustring profuse;
|
||||
profuse = "sRGB";//or "Adobe RGB"
|
||||
if( wbpar.itcwb_forceextra && wbpar.itcwb_sampling == false) {//Adobe RGB
|
||||
profuse = "ACESp0";//cover all CIE xy diagram
|
||||
}
|
||||
|
||||
TMatrix wprof = ICCStore::getInstance()->workingSpaceMatrix(profuse); //ACESp0 or sRGB
|
||||
const float wp[3][3] = {
|
||||
{static_cast<float>(wprof[0][0]), static_cast<float>(wprof[0][1]), static_cast<float>(wprof[0][2])},
|
||||
{static_cast<float>(wprof[1][0]), static_cast<float>(wprof[1][1]), static_cast<float>(wprof[1][2])},
|
||||
{static_cast<float>(wprof[2][0]), static_cast<float>(wprof[2][1]), static_cast<float>(wprof[2][2])}
|
||||
};
|
||||
|
||||
TMatrix wiprof = ICCStore::getInstance()->workingSpaceInverseMatrix("sRGB");
|
||||
TMatrix wiprof = ICCStore::getInstance()->workingSpaceInverseMatrix(profuse);//ACESp0 or sRGB
|
||||
//inverse matrix user select
|
||||
const float wip[3][3] = {
|
||||
{static_cast<float>(wiprof[0][0]), static_cast<float>(wiprof[0][1]), static_cast<float>(wiprof[0][2])},
|
||||
@ -4766,7 +5243,7 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
{0.680, 1.f},
|
||||
{0.690, 1.f},
|
||||
{0.700, 1.f},
|
||||
{0.714, 1.f},//usual range
|
||||
{0.714, 1.f},//usual 2 range
|
||||
{0.727, 1.f},
|
||||
{0.741, 1.f},
|
||||
{0.755, 1.f},
|
||||
@ -4775,7 +5252,7 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
{0.800, 1.f},
|
||||
{0.806, 1.f},
|
||||
{0.813, 1.f},
|
||||
{0.820, 1.f},
|
||||
{0.820, 1.f},//usual range
|
||||
{0.826, 1.f},
|
||||
{0.833, 1.f},
|
||||
{0.840, 1.f},
|
||||
@ -4822,13 +5299,13 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
{1.220, 1.f},
|
||||
{1.230, 1.f},
|
||||
{1.240, 1.f},
|
||||
{1.250, 1.f},
|
||||
{1.250, 1.f},// usual range
|
||||
{1.275, 1.f},
|
||||
{1.300, 1.f},
|
||||
{1.325, 1.f},
|
||||
{1.350, 1.f},
|
||||
{1.375, 1.f},
|
||||
{1.400, 1.f},//usual range
|
||||
{1.400, 1.f},//usual 2 range
|
||||
{1.425, 1.f},
|
||||
{1.450, 1.f},
|
||||
{1.475, 1.f},
|
||||
@ -4884,20 +5361,25 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
int end;
|
||||
} RangeGreen;
|
||||
|
||||
constexpr RangeGreen Rangestandard = {24, 86};//usual green range
|
||||
constexpr RangeGreen Rangestandard = {33, 80};//usual green range
|
||||
constexpr RangeGreen Rangestandard2 = {24, 86};//usual 2 green range
|
||||
constexpr RangeGreen Rangeextended = {15, 93};
|
||||
const RangeGreen Rangemax = {0, N_g};
|
||||
|
||||
RangeGreen Rangegreenused;
|
||||
|
||||
if (settings->itcwb_greenrange == 0) {
|
||||
if (wbpar.itcwb_rgreen == 0) {
|
||||
Rangegreenused = Rangestandard;
|
||||
} else if (settings->itcwb_greenrange == 1) {
|
||||
} else if (wbpar.itcwb_rgreen == 1) {
|
||||
Rangegreenused = Rangestandard2;
|
||||
} else if (wbpar.itcwb_rgreen == 2) {
|
||||
Rangegreenused = Rangeextended;
|
||||
} else {
|
||||
Rangegreenused = Rangemax;
|
||||
}
|
||||
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
Rangegreenused = Rangestandard2;
|
||||
}
|
||||
typedef struct WbTxyz {
|
||||
double Tem;
|
||||
double XX;
|
||||
@ -5044,8 +5526,10 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
float gmm[N_t];
|
||||
float bmm[N_t];
|
||||
|
||||
constexpr int siza = 237; //192 untill 01/2023 size of histogram
|
||||
|
||||
int siza = 237; //192 untill 01/2023 size of histogram
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
siza = 192;//old sampling 5.9 and before...
|
||||
}
|
||||
// tempref and greenref are camera wb values.
|
||||
// I used them by default to select good spectral values !! but they are changed after
|
||||
tempref = rtengine::min(tempref, 12000.0);
|
||||
@ -5062,12 +5546,12 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
//calculate R G B multiplier in function illuminant and temperature
|
||||
const bool isMono = (ri->getSensorType() == ST_FUJI_XTRANS && raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::MONO))
|
||||
|| (ri->getSensorType() == ST_BAYER && raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::MONO));
|
||||
|
||||
for (int tt = 0; tt < N_t; ++tt) {
|
||||
double r, g, b;
|
||||
float rm, gm, bm;
|
||||
ColorTemp WBiter = ColorTemp(Txyz[tt].Tem, greenitc, 1.f, "Custom");
|
||||
ColorTemp WBiter = ColorTemp(Txyz[tt].Tem, greenitc, 1.f, "Custom", wbpar.observer);
|
||||
WBiter.getMultipliers(r, g, b);
|
||||
|
||||
rm = imatrices.cam_rgb[0][0] * r + imatrices.cam_rgb[0][1] * g + imatrices.cam_rgb[0][2] * b;
|
||||
gm = imatrices.cam_rgb[1][0] * r + imatrices.cam_rgb[1][1] * g + imatrices.cam_rgb[1][2] * b;
|
||||
bm = imatrices.cam_rgb[2][0] * r + imatrices.cam_rgb[2][1] * g + imatrices.cam_rgb[2][2] * b;
|
||||
@ -5151,7 +5635,7 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
array2D<float> yc(bfwitc, bfhitc);
|
||||
array2D<float> Yc(bfwitc, bfhitc);
|
||||
|
||||
const int deltarepref = settings->itcwb_delta;
|
||||
const int deltarepref = 1; //settings->itcwb_delta;
|
||||
|
||||
for (int nn = 0, drep = -deltarepref; nn <= 2; ++nn, drep += deltarepref) {
|
||||
//three loop to refine color if temp camera is probably not very good
|
||||
@ -5167,7 +5651,7 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
const float RR = rmm[rep] * redloc[y][x];
|
||||
const float GG = gmm[rep] * greenloc[y][x];
|
||||
const float BB = bmm[rep] * blueloc[y][x];
|
||||
Color::rgbxyY(RR, GG, BB, xc[y][x], yc[y][x], Yc[y][x], wp);
|
||||
Color::rgbxyY(RR, GG, BB, xc[y][x], yc[y][x], Yc[y][x], wp);//use sRGB or ACESp0
|
||||
}
|
||||
}
|
||||
|
||||
@ -5182,12 +5666,18 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
|
||||
bool purp = true;//if inpaint-opposed or something else enable purp
|
||||
|
||||
if (hrp.hrenabled && hrp.method == "Coloropp" && settings->itcwb_nopurple == true) {//we disabled (user) with settings if image are naturally with purple (flowers...)
|
||||
// if (hrp.hrenabled && hrp.method == "Coloropp" && settings->itcwb_nopurple == true) {//we disabled (user) with settings if image are naturally with purple (flowers...)
|
||||
if (hrp.hrenabled && hrp.method == "Coloropp" && wbpar.itcwb_nopurple == true) {//we disabled (user) with settings if image are naturally with purple (flowers...)
|
||||
purp = false;
|
||||
}
|
||||
|
||||
if(wbpar.itcwb_sampling == false) {
|
||||
//printf("Use high smapling\n");
|
||||
histoxyY(bfhitc, bfwitc, xc, yc, Yc, xxx, yyy, YYY, histxy, purp);//purp enable, enable purple color in WB
|
||||
//return histogram x and y for each temp and in a range of 235 colors (siza)
|
||||
} else {
|
||||
//printf("Use low smapling - 5.9\n");
|
||||
histoxyY_low(bfhitc, bfwitc, xc, yc, Yc, xxx, yyy, YYY, histxy);//low scaling
|
||||
}
|
||||
}
|
||||
|
||||
// free some memory
|
||||
@ -5255,7 +5745,11 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
|
||||
int sizcurr2ref = sizcurrref - ntr;
|
||||
const int sizcu30 = sizcurrref - n30;
|
||||
const int sizcu4 = rtengine::min(sizcu30, 55);//
|
||||
int nbm = 77;//number max of color used = 1.4 * 55 in case all CIExy diagram
|
||||
if(profuse == "sRGB" || wbpar.itcwb_sampling == true) {
|
||||
nbm = 55;
|
||||
}
|
||||
const int sizcu4 = rtengine::min(sizcu30, nbm);//size of chroma values
|
||||
|
||||
if (settings->verbose) {
|
||||
printf("ntr=%i sizcurr2ref=%i sizcu30=%i sizcu4=%i\n", ntr, sizcurr2ref, sizcu30, sizcu4);
|
||||
@ -5292,12 +5786,21 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
if (settings->verbose) {
|
||||
printf("estimchrom=%f\n", estimchrom);
|
||||
}
|
||||
bool issorted = wbpar.itcwb_sorted;
|
||||
|
||||
if (settings->itcwb_sorted) { //sort in ascending with chroma values
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
issorted = false;
|
||||
}
|
||||
|
||||
|
||||
if (issorted) { //sort in ascending with chroma values
|
||||
std::sort(wbchro, wbchro + sizcu4, wbchro[0]);
|
||||
}
|
||||
|
||||
const int maxval = rtengine::LIM(settings->itcwb_thres, 10, 55);//max values of color to find correlation
|
||||
int maxval = rtengine::LIM(wbpar.itcwb_thres, 10, 55);//max values of color to find correlation
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
maxval = 34;
|
||||
}
|
||||
|
||||
sizcurr2ref = rtengine::min(sizcurr2ref, maxval); //keep about the biggest values,
|
||||
|
||||
@ -5312,10 +5815,13 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
}
|
||||
|
||||
//calculate deltaE xx to find best values of spectrals data - limited to chroma values
|
||||
int maxnb = rtengine::LIM(settings->itcwb_sizereference, 1, 5);
|
||||
// int maxnb = rtengine::LIM(settings->itcwb_sizereference, 1, 5);
|
||||
// int maxnb = rtengine::LIM(wbpar.itcwb_size, 1, 5);
|
||||
int maxnb = 3;
|
||||
//wbpar.itcwb_size to verify if this setting is usefull...diificulties with High gamut and limited patch spectral colors.
|
||||
|
||||
if (settings->itcwb_thres > 55) {
|
||||
maxnb = 201 / settings->itcwb_thres;
|
||||
if (wbpar.itcwb_thres > 55) {//normally never used
|
||||
maxnb = 201 / wbpar.itcwb_thres;
|
||||
}
|
||||
|
||||
for (int nb = 1; nb <= maxnb; ++nb) { //max 5 iterations for Itcwb_thres=33, after trial 3 is good in most cases but in some cases 5
|
||||
@ -5423,10 +5929,12 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
Tgstud[i].student = 1000.f;//max value to initialize
|
||||
Tgstud[i].tempref = 57;//5002K position in the list
|
||||
Tgstud[i].greenref = 55;// 1.f position in the list
|
||||
|
||||
}
|
||||
|
||||
const int dgoodref = rtengine::min(settings->itcwb_greendeltatemp, 4);
|
||||
int dgoodref = rtengine::LIM(wbpar.itcwb_delta,1, 4);
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
dgoodref = 2;
|
||||
}
|
||||
const int scantempbeg = rtengine::max(goodref - (dgoodref + 1), 1);
|
||||
const int scantempend = rtengine::min(goodref + dgoodref, N_t - 1);
|
||||
|
||||
@ -5436,7 +5944,7 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
|
||||
for (int tt = scantempbeg; tt < scantempend; ++tt) {
|
||||
double r, g, b;
|
||||
ColorTemp WBiter(Txyz[tt].Tem, gree[gr].green, 1.f, "Custom");
|
||||
ColorTemp WBiter(Txyz[tt].Tem, gree[gr].green, 1.f, "Custom", wbpar.observer);
|
||||
WBiter.getMultipliers(r, g, b);
|
||||
float rm = imatrices.cam_rgb[0][0] * r + imatrices.cam_rgb[0][1] * g + imatrices.cam_rgb[0][2] * b;
|
||||
float gm = imatrices.cam_rgb[1][0] * r + imatrices.cam_rgb[1][1] * g + imatrices.cam_rgb[1][2] * b;
|
||||
@ -5508,7 +6016,12 @@ void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double
|
||||
// perhaps we can used a Snedecor test ? but why...at least we have confidence interval > 90%
|
||||
int greengood = 55;
|
||||
|
||||
int maxkgood = 5;//we can change ...to test 3, 4, 5. High values perhaps less good student, but it is a compromise...
|
||||
int maxkgood = wbpar.itcwb_fgreen;//we can change ...to test 3, 4, 5. High values perhaps less good student, but it is a compromise...
|
||||
maxkgood = rtengine::LIM(maxkgood, 3, 6);
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
maxkgood = 3; // force to 3 with old low sampling
|
||||
}
|
||||
|
||||
int mingood = std::min(std::fabs(Tgstud[0].greenref - 55), std::fabs(Tgstud[1].greenref - 55));
|
||||
|
||||
for (int k = 2; k < maxkgood; ++k) {
|
||||
@ -5558,14 +6071,11 @@ void RawImageSource::WBauto(double & tempref, double & greenref, array2D<float>
|
||||
//put green (tint) in reasonable limits for an Daylight illuminant
|
||||
// avoid too bi or too low values
|
||||
if (wbpar.method == "autitcgreen") {
|
||||
bool extra = false;
|
||||
bool extra = true;
|
||||
|
||||
if (greenref > 0.5 && greenref < 1.3) {// 0.5 and 1.3 arbitraties values
|
||||
greenitc = greenref;
|
||||
|
||||
if (settings->itcwb_forceextra) {
|
||||
extra = true;
|
||||
}
|
||||
} else {
|
||||
greenitc = 1.;
|
||||
extra = true;
|
||||
@ -5576,22 +6086,16 @@ void RawImageSource::WBauto(double & tempref, double & greenref, array2D<float>
|
||||
}
|
||||
}
|
||||
|
||||
void RawImageSource::getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w)
|
||||
void RawImageSource::getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, const WBParams & wbpar)
|
||||
{
|
||||
// BENCHFUN
|
||||
//used by auto WB local to calculate red, green, blue in local region
|
||||
|
||||
int precision = 5;
|
||||
|
||||
if (settings->itcwb_precis == 5) {
|
||||
int precision = 3;//must be 3 5 or 9
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
precision = 5;
|
||||
} else if (settings->itcwb_precis < 5) {
|
||||
precision = 3;
|
||||
} else if (settings->itcwb_precis > 5) {
|
||||
precision = 9;
|
||||
}
|
||||
|
||||
|
||||
const int bfw = W / precision + ((W % precision) > 0 ? 1 : 0);// 5 arbitrary value can be change to 3 or 9 ;
|
||||
const int bfh = H / precision + ((H % precision) > 0 ? 1 : 0);
|
||||
|
||||
@ -5851,14 +6355,9 @@ void RawImageSource::getAutoWBMultipliersitc(double & tempref, double & greenref
|
||||
|
||||
if (wbpar.method == "autitcgreen") {
|
||||
bool twotimes = false;
|
||||
int precision = 5;
|
||||
|
||||
if (settings->itcwb_precis == 5) {
|
||||
int precision = 3;//must be 3 5 or 9
|
||||
if(wbpar.itcwb_sampling == true) {
|
||||
precision = 5;
|
||||
} else if (settings->itcwb_precis < 5) {
|
||||
precision = 3;
|
||||
} else if (settings->itcwb_precis > 5) {
|
||||
precision = 9;
|
||||
}
|
||||
|
||||
const int bfw = W / precision + ((W % precision) > 0 ? 1 : 0);// 5 arbitrary value can be change to 3 or 9 ;
|
||||
@ -6106,7 +6605,7 @@ void RawImageSource::getAutoWBMultipliers(double &rm, double &gm, double &bm)
|
||||
blueAWBMul = bm = imatrices.rgb_cam[2][0] * reds + imatrices.rgb_cam[2][1] * greens + imatrices.rgb_cam[2][2] * blues;
|
||||
}
|
||||
|
||||
ColorTemp RawImageSource::getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal)
|
||||
ColorTemp RawImageSource::getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal, StandardObserver observer)
|
||||
{
|
||||
|
||||
int x;
|
||||
@ -6314,7 +6813,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector<Coord2D> &red, std::vector<Coor
|
||||
double gm = imatrices.rgb_cam[1][0] * reds + imatrices.rgb_cam[1][1] * greens + imatrices.rgb_cam[1][2] * blues;
|
||||
double bm = imatrices.rgb_cam[2][0] * reds + imatrices.rgb_cam[2][1] * greens + imatrices.rgb_cam[2][2] * blues;
|
||||
|
||||
return ColorTemp (rm, gm, bm, equal);
|
||||
return ColorTemp (rm, gm, bm, equal, observer);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -143,7 +143,7 @@ public:
|
||||
void scaleColors (int winx, int winy, int winw, int winh, const procparams::RAWParams &raw, array2D<float> &rawData); // raw for cblack
|
||||
void WBauto(double &tempref, double &greenref, array2D<float> &redloc, array2D<float> &greenloc, array2D<float> &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, double &tempitc, double &greenitc, float &studgood, bool &twotimes, const procparams::WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw, const procparams::ToneCurveParams &hrp) override;
|
||||
void getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const procparams::WBParams & wbpar, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw, const procparams::ToneCurveParams &hrp) override;
|
||||
void getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w) override;
|
||||
void getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, const procparams::WBParams & wbpar) override;
|
||||
|
||||
void getWBMults (const ColorTemp &ctemp, const procparams::RAWParams &raw, std::array<float, 4>& scale_mul, float &autoGainComp, float &rm, float &gm, float &bm) const override;
|
||||
void getImage (const ColorTemp &ctemp, int tran, Imagefloat* image, const PreviewProps &pp, const procparams::ToneCurveParams &hrp, const procparams::RAWParams &raw, int opposed) override;
|
||||
@ -154,7 +154,7 @@ public:
|
||||
return camera_wb;
|
||||
}
|
||||
void getAutoWBMultipliers (double &rm, double &gm, double &bm) override;
|
||||
ColorTemp getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal) override;
|
||||
ColorTemp getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal, StandardObserver observer) override;
|
||||
bool isWBProviderReady () override
|
||||
{
|
||||
return rawData;
|
||||
@ -186,7 +186,7 @@ public:
|
||||
}
|
||||
void getAutoExpHistogram (LUTu & histogram, int& histcompr) override;
|
||||
void getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LUTu & histBlueRaw) override;
|
||||
void getAutoMatchedToneCurve(const procparams::ColorManagementParams &cp, std::vector<double> &outCurve) override;
|
||||
void getAutoMatchedToneCurve(const procparams::ColorManagementParams &cp, StandardObserver observer, std::vector<double> &outCurve) override;
|
||||
DCPProfile *getDCP(const procparams::ColorManagementParams &cmp, DCPProfileApplyState &as) override;
|
||||
|
||||
void convertColorSpace(Imagefloat* image, const procparams::ColorManagementParams &cmp, const ColorTemp &wb) override;
|
||||
|
@ -472,7 +472,7 @@ class AutoWBListener
|
||||
{
|
||||
public:
|
||||
virtual ~AutoWBListener() = default;
|
||||
virtual void WBChanged(double temp, double green, float studgood) = 0;
|
||||
virtual void WBChanged(double temp, double green, double rw, double gw, double bw, float studgood) = 0;
|
||||
};
|
||||
|
||||
class FrameCountListener
|
||||
@ -619,8 +619,8 @@ public:
|
||||
* @return a pointer to the Crop object that handles the image data trough its own pipeline */
|
||||
virtual DetailedCrop* createCrop (::EditDataProvider *editDataProvider, bool isDetailWindow) = 0;
|
||||
|
||||
virtual bool getAutoWB (double& temp, double& green, double equal, double tempBias) = 0;
|
||||
virtual void getCamWB (double& temp, double& green) = 0;
|
||||
virtual bool getAutoWB (double& temp, double& green, double equal, StandardObserver observer, double tempBias) = 0;
|
||||
virtual void getCamWB (double& temp, double& green, StandardObserver observer) = 0;
|
||||
virtual void getSpotWB (int x, int y, int rectSize, double& temp, double& green) = 0;
|
||||
virtual bool getFilmNegativeSpot(int x, int y, int spotSize, procparams::FilmNegativeParams::RGB &refInput, procparams::FilmNegativeParams::RGB &refOutput) = 0;
|
||||
|
||||
|
@ -194,7 +194,7 @@ namespace rtengine
|
||||
|
||||
using namespace procparams;
|
||||
|
||||
Thumbnail* Thumbnail::loadFromImage (const Glib::ustring& fname, int &w, int &h, int fixwh, double wbEq, bool inspectorMode)
|
||||
Thumbnail* Thumbnail::loadFromImage (const Glib::ustring& fname, int &w, int &h, int fixwh, double wbEq, StandardObserver wbObserver, bool inspectorMode)
|
||||
{
|
||||
|
||||
StdImageSource imgSrc;
|
||||
@ -310,8 +310,9 @@ Thumbnail* Thumbnail::loadFromImage (const Glib::ustring& fname, int &w, int &h,
|
||||
tpp->blueAWBMul = avg_b / double (n);
|
||||
tpp->wbEqual = wbEq;
|
||||
tpp->wbTempBias = 0.0;
|
||||
tpp->wbObserver = wbObserver;
|
||||
|
||||
cTemp.mul2temp (tpp->redAWBMul, tpp->greenAWBMul, tpp->blueAWBMul, tpp->wbEqual, tpp->autoWBTemp, tpp->autoWBGreen);
|
||||
cTemp.mul2temp (tpp->redAWBMul, tpp->greenAWBMul, tpp->blueAWBMul, tpp->wbEqual, tpp->wbObserver, tpp->autoWBTemp, tpp->autoWBGreen);
|
||||
}
|
||||
|
||||
tpp->init ();
|
||||
@ -543,7 +544,7 @@ RawMetaDataLocation Thumbnail::loadMetaDataFromRaw (const Glib::ustring& fname)
|
||||
return rml;
|
||||
}
|
||||
|
||||
Thumbnail* Thumbnail::loadFromRaw (const Glib::ustring& fname, RawMetaDataLocation& rml, eSensorType &sensorType, int &w, int &h, int fixwh, double wbEq, bool rotate, bool forHistogramMatching)
|
||||
Thumbnail* Thumbnail::loadFromRaw (const Glib::ustring& fname, RawMetaDataLocation& rml, eSensorType &sensorType, int &w, int &h, int fixwh, double wbEq, StandardObserver wbObserver, bool rotate, bool forHistogramMatching)
|
||||
{
|
||||
RawImage *ri = new RawImage (fname);
|
||||
unsigned int tempImageNum = 0;
|
||||
@ -982,9 +983,10 @@ Thumbnail* Thumbnail::loadFromRaw (const Glib::ustring& fname, RawMetaDataLocati
|
||||
tpp->blueAWBMul = ri->get_rgb_cam (2, 0) * reds + ri->get_rgb_cam (2, 1) * greens + ri->get_rgb_cam (2, 2) * blues;
|
||||
tpp->wbEqual = wbEq;
|
||||
tpp->wbTempBias = 0.0;
|
||||
tpp->wbObserver = wbObserver;
|
||||
|
||||
ColorTemp cTemp;
|
||||
cTemp.mul2temp (tpp->redAWBMul, tpp->greenAWBMul, tpp->blueAWBMul, tpp->wbEqual, tpp->autoWBTemp, tpp->autoWBGreen);
|
||||
cTemp.mul2temp (tpp->redAWBMul, tpp->greenAWBMul, tpp->blueAWBMul, tpp->wbEqual, tpp->wbObserver, tpp->autoWBTemp, tpp->autoWBGreen);
|
||||
}
|
||||
|
||||
if (rotate && ri->get_rotateDegree() > 0) {
|
||||
@ -1121,18 +1123,19 @@ IImage8* Thumbnail::processImage (const procparams::ProcParams& params, eSensorT
|
||||
float iso = metadata->getISOSpeed(imgNum);
|
||||
float fcomp = metadata->getExpComp(imgNum);
|
||||
|
||||
// check if the WB's equalizer value has changed
|
||||
if (wbEqual < (params.wb.equal - 5e-4) || wbEqual > (params.wb.equal + 5e-4) || wbTempBias < (params.wb.tempBias - 5e-4) || wbTempBias > (params.wb.tempBias + 5e-4)) {
|
||||
// check if the WB's equalizer, temperature bias, or observer value has changed
|
||||
if (wbEqual < (params.wb.equal - 5e-4) || wbEqual > (params.wb.equal + 5e-4) || wbTempBias < (params.wb.tempBias - 5e-4) || wbTempBias > (params.wb.tempBias + 5e-4) || wbObserver != params.wb.observer) {
|
||||
wbEqual = params.wb.equal;
|
||||
wbTempBias = params.wb.tempBias;
|
||||
wbObserver = params.wb.observer;
|
||||
// recompute the autoWB
|
||||
ColorTemp cTemp;
|
||||
cTemp.mul2temp (redAWBMul, greenAWBMul, blueAWBMul, wbEqual, autoWBTemp, autoWBGreen);
|
||||
cTemp.mul2temp (redAWBMul, greenAWBMul, blueAWBMul, wbEqual, wbObserver, autoWBTemp, autoWBGreen);
|
||||
autoWBTemp += autoWBTemp * wbTempBias;
|
||||
}
|
||||
|
||||
// compute WB multipliers
|
||||
ColorTemp currWB = ColorTemp (params.wb.temperature, params.wb.green, params.wb.equal, params.wb.method);
|
||||
ColorTemp currWB = ColorTemp (params.wb.temperature, params.wb.green, params.wb.equal, params.wb.method, params.wb.observer);
|
||||
|
||||
if (!params.wb.enabled) {
|
||||
currWB = ColorTemp();
|
||||
@ -1141,9 +1144,9 @@ IImage8* Thumbnail::processImage (const procparams::ProcParams& params, eSensorT
|
||||
double cam_r = colorMatrix[0][0] * camwbRed + colorMatrix[0][1] * camwbGreen + colorMatrix[0][2] * camwbBlue;
|
||||
double cam_g = colorMatrix[1][0] * camwbRed + colorMatrix[1][1] * camwbGreen + colorMatrix[1][2] * camwbBlue;
|
||||
double cam_b = colorMatrix[2][0] * camwbRed + colorMatrix[2][1] * camwbGreen + colorMatrix[2][2] * camwbBlue;
|
||||
currWB = ColorTemp (cam_r, cam_g, cam_b, params.wb.equal);
|
||||
currWB = ColorTemp (cam_r, cam_g, cam_b, params.wb.equal, params.wb.observer);
|
||||
} else if (params.wb.method == "autold") {
|
||||
currWB = ColorTemp (autoWBTemp, autoWBGreen, wbEqual, "Custom");
|
||||
currWB = ColorTemp (autoWBTemp, autoWBGreen, wbEqual, "Custom", wbObserver);
|
||||
}
|
||||
|
||||
double rm, gm, bm;
|
||||
@ -1588,27 +1591,28 @@ void Thumbnail::getDimensions (int& w, int& h, double& scaleFac)
|
||||
}
|
||||
}
|
||||
|
||||
void Thumbnail::getCamWB (double& temp, double& green)
|
||||
void Thumbnail::getCamWB (double& temp, double& green, StandardObserver observer)
|
||||
{
|
||||
|
||||
double cam_r = colorMatrix[0][0] * camwbRed + colorMatrix[0][1] * camwbGreen + colorMatrix[0][2] * camwbBlue;
|
||||
double cam_g = colorMatrix[1][0] * camwbRed + colorMatrix[1][1] * camwbGreen + colorMatrix[1][2] * camwbBlue;
|
||||
double cam_b = colorMatrix[2][0] * camwbRed + colorMatrix[2][1] * camwbGreen + colorMatrix[2][2] * camwbBlue;
|
||||
ColorTemp currWB = ColorTemp (cam_r, cam_g, cam_b, 1.0); // we do not take the equalizer into account here, because we want camera's WB
|
||||
ColorTemp currWB = ColorTemp (cam_r, cam_g, cam_b, 1.0, observer); // we do not take the equalizer into account here, because we want camera's WB
|
||||
temp = currWB.getTemp ();
|
||||
green = currWB.getGreen ();
|
||||
}
|
||||
|
||||
void Thumbnail::getAutoWB (double& temp, double& green, double equal, double tempBias)
|
||||
void Thumbnail::getAutoWB (double& temp, double& green, double equal, double tempBias, StandardObserver observer)
|
||||
{
|
||||
|
||||
if (equal != wbEqual || tempBias != wbTempBias) {
|
||||
if (equal != wbEqual || tempBias != wbTempBias || observer != wbObserver) {
|
||||
// compute the values depending on equal
|
||||
ColorTemp cTemp;
|
||||
wbEqual = equal;
|
||||
wbTempBias = tempBias;
|
||||
wbObserver = observer;
|
||||
// compute autoWBTemp and autoWBGreen
|
||||
cTemp.mul2temp (redAWBMul, greenAWBMul, blueAWBMul, wbEqual, autoWBTemp, autoWBGreen);
|
||||
cTemp.mul2temp (redAWBMul, greenAWBMul, blueAWBMul, wbEqual, wbObserver, autoWBTemp, autoWBGreen);
|
||||
autoWBTemp += autoWBTemp * tempBias;
|
||||
}
|
||||
|
||||
@ -1665,7 +1669,7 @@ void Thumbnail::getSpotWB (const procparams::ProcParams& params, int xp, int yp,
|
||||
double gm = colorMatrix[1][0] * reds + colorMatrix[1][1] * greens + colorMatrix[1][2] * blues;
|
||||
double bm = colorMatrix[2][0] * reds + colorMatrix[2][1] * greens + colorMatrix[2][2] * blues;
|
||||
|
||||
ColorTemp ct (rm, gm, bm, params.wb.equal);
|
||||
ColorTemp ct (rm, gm, bm, params.wb.equal, params.wb.observer);
|
||||
rtemp = ct.getTemp ();
|
||||
rgreen = ct.getGreen ();
|
||||
}
|
||||
|
@ -38,6 +38,8 @@ class ustring;
|
||||
namespace rtengine
|
||||
{
|
||||
|
||||
enum class StandardObserver;
|
||||
|
||||
class Thumbnail
|
||||
{
|
||||
|
||||
@ -55,6 +57,7 @@ class Thumbnail
|
||||
double camwbBlue;
|
||||
double redAWBMul, greenAWBMul, blueAWBMul; // multipliers for auto WB
|
||||
double autoWBTemp, autoWBGreen, wbEqual, wbTempBias; // autoWBTemp and autoWBGreen are updated each time autoWB is requested and if wbEqual has been modified
|
||||
StandardObserver wbObserver;
|
||||
LUTu aeHistogram;
|
||||
int aeHistCompression;
|
||||
bool aeValid;
|
||||
@ -95,12 +98,12 @@ public:
|
||||
void getDimensions (int& w, int& h, double& scaleFac);
|
||||
|
||||
static Thumbnail* loadQuickFromRaw (const Glib::ustring& fname, rtengine::RawMetaDataLocation& rml, eSensorType &sensorType, int &w, int &h, int fixwh, bool rotate, bool inspectorMode = false, bool forHistogramMatching = false);
|
||||
static Thumbnail* loadFromRaw (const Glib::ustring& fname, RawMetaDataLocation& rml, eSensorType &sensorType, int &w, int &h, int fixwh, double wbEq, bool rotate, bool forHistogramMatching = false);
|
||||
static Thumbnail* loadFromImage (const Glib::ustring& fname, int &w, int &h, int fixwh, double wbEq, bool inspectorMode = false);
|
||||
static Thumbnail* loadFromRaw (const Glib::ustring& fname, RawMetaDataLocation& rml, eSensorType &sensorType, int &w, int &h, int fixwh, double wbEq, StandardObserver wbObserver, bool rotate, bool forHistogramMatching = false);
|
||||
static Thumbnail* loadFromImage (const Glib::ustring& fname, int &w, int &h, int fixwh, double wbEq, StandardObserver wbObserver, bool inspectorMode = false);
|
||||
static RawMetaDataLocation loadMetaDataFromRaw (const Glib::ustring& fname);
|
||||
|
||||
void getCamWB (double& temp, double& green);
|
||||
void getAutoWB (double& temp, double& green, double equal, double tempBias);
|
||||
void getCamWB (double& temp, double& green, StandardObserver observer);
|
||||
void getAutoWB (double& temp, double& green, double equal, double tempBias, StandardObserver observer);
|
||||
void getAutoWBMultipliers (double& rm, double& gm, double& bm);
|
||||
void getSpotWB (const procparams::ProcParams& params, int x, int y, int rect, double& temp, double& green);
|
||||
void applyAutoExp (procparams::ProcParams& pparams);
|
||||
|
@ -44,7 +44,6 @@ public:
|
||||
bool monitorBPC; ///< Black Point Compensation for the Labimage->Monitor transform (directly, i.e. not soft-proofing and no WCS in between)
|
||||
bool autoMonitorProfile; ///< Try to auto-determine the correct monitor color profile
|
||||
bool autocielab;
|
||||
bool observer10;
|
||||
bool rgbcurveslumamode_gamut;// controls gamut enforcement for RGB curves in lumamode
|
||||
bool verbose;
|
||||
Glib::ustring darkFramesPath; ///< The default directory for dark frames
|
||||
@ -93,17 +92,7 @@ public:
|
||||
int previewselection;
|
||||
double cbdlsensi;
|
||||
// bool showtooltip;
|
||||
|
||||
int itcwb_thres;
|
||||
bool itcwb_sorted;
|
||||
int itcwb_greenrange;
|
||||
int itcwb_greendeltatemp;
|
||||
bool itcwb_forceextra;
|
||||
int itcwb_sizereference;
|
||||
int itcwb_delta;
|
||||
bool itcwb_stdobserver10;
|
||||
int itcwb_precis;
|
||||
bool itcwb_nopurple;
|
||||
bool itcwb_enable;
|
||||
//wavelet levels
|
||||
double edghi;
|
||||
double edglo;
|
||||
|
@ -269,7 +269,7 @@ private:
|
||||
}
|
||||
|
||||
// set the color temperature
|
||||
currWB = ColorTemp(params.wb.temperature, params.wb.green, params.wb.equal, params.wb.method);
|
||||
currWB = ColorTemp(params.wb.temperature, params.wb.green, params.wb.equal, params.wb.method, params.wb.observer);
|
||||
|
||||
if (!params.wb.enabled) {
|
||||
currWB = ColorTemp();
|
||||
@ -278,7 +278,7 @@ private:
|
||||
} else if (params.wb.method == "autold") {
|
||||
double rm, gm, bm;
|
||||
imgsrc->getAutoWBMultipliers(rm, gm, bm);
|
||||
currWB.update(rm, gm, bm, params.wb.equal, params.wb.tempBias);
|
||||
currWB.update(rm, gm, bm, params.wb.equal, params.wb.observer, params.wb.tempBias);
|
||||
}
|
||||
|
||||
calclum = nullptr ;
|
||||
@ -781,7 +781,7 @@ private:
|
||||
|
||||
if (params.toneCurve.histmatching) {
|
||||
if (!params.toneCurve.fromHistMatching) {
|
||||
imgsrc->getAutoMatchedToneCurve(params.icm, params.toneCurve.curve);
|
||||
imgsrc->getAutoMatchedToneCurve(params.icm, params.wb.observer, params.toneCurve.curve);
|
||||
}
|
||||
|
||||
if (params.toneCurve.autoexp) {
|
||||
|
@ -187,7 +187,7 @@ int StdImageSource::load (const Glib::ustring &fname)
|
||||
plistener->setProgress (1.0);
|
||||
}
|
||||
|
||||
wb = ColorTemp (1.0, 1.0, 1.0, 1.0);
|
||||
wb = ColorTemp (1.0, 1.0, 1.0, 1.0, ColorTemp::DEFAULT_OBSERVER);
|
||||
//this is probably a mistake if embedded profile is not D65
|
||||
|
||||
return 0;
|
||||
@ -348,7 +348,7 @@ void StdImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm)
|
||||
blueAWBMul = bm;
|
||||
}
|
||||
|
||||
ColorTemp StdImageSource::getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D>& blue, int tran, double equal)
|
||||
ColorTemp StdImageSource::getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D>& blue, int tran, double equal, StandardObserver observer)
|
||||
{
|
||||
int rn, gn, bn;
|
||||
double reds, greens, blues;
|
||||
@ -360,7 +360,7 @@ ColorTemp StdImageSource::getSpotWB (std::vector<Coord2D> &red, std::vector<Coor
|
||||
printf ("AVG: %g %g %g\n", reds / rn, greens / gn, blues / bn);
|
||||
}
|
||||
|
||||
return ColorTemp (reds / rn * img_r, greens / gn * img_g, blues / bn * img_b, equal);
|
||||
return ColorTemp (reds / rn * img_r, greens / gn * img_g, blues / bn * img_b, equal, observer);
|
||||
}
|
||||
|
||||
void StdImageSource::flush() {
|
||||
|
@ -59,13 +59,13 @@ public:
|
||||
int load (const Glib::ustring &fname) override;
|
||||
void getWBMults (const ColorTemp &ctemp, const procparams::RAWParams &raw, std::array<float, 4>& scale_mul, float &autoGainComp, float &rm, float &gm, float &bm) const override {};
|
||||
void getImage (const ColorTemp &ctemp, int tran, Imagefloat* image, const PreviewProps &pp, const procparams::ToneCurveParams &hrp, const procparams::RAWParams &raw, int opposed) override;
|
||||
void getrgbloc (int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w) override {};
|
||||
void getrgbloc (int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, const procparams::WBParams & wbpar) override {};
|
||||
ColorTemp getWB () const override
|
||||
{
|
||||
return wb;
|
||||
}
|
||||
void getAutoWBMultipliers (double &rm, double &gm, double &bm) override;
|
||||
ColorTemp getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal) override;
|
||||
ColorTemp getSpotWB (std::vector<Coord2D> &red, std::vector<Coord2D> &green, std::vector<Coord2D> &blue, int tran, double equal, StandardObserver observer) override;
|
||||
void WBauto(double &tempref, double &greenref, array2D<float> &redloc, array2D<float> &greenloc, array2D<float> &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, double &tempitc, double &greenitc, float &studgood, bool &twotimes, const procparams::WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw, const procparams::ToneCurveParams &hrp) override;
|
||||
void getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const procparams::WBParams & wbpar, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw, const procparams::ToneCurveParams &hrp) override;
|
||||
|
||||
|
@ -586,19 +586,19 @@ void BatchToolPanelCoordinator::unsetTweakOperator (rtengine::TweakOperator *tOp
|
||||
{
|
||||
}
|
||||
|
||||
void BatchToolPanelCoordinator::getAutoWB (double& temp, double& green, double equal, double tempBias)
|
||||
void BatchToolPanelCoordinator::getAutoWB (double& temp, double& green, double equal, rtengine::StandardObserver observer, double tempBias)
|
||||
{
|
||||
|
||||
if (!selected.empty()) {
|
||||
selected[0]->getAutoWB (temp, green, equal, tempBias);
|
||||
selected[0]->getAutoWB (temp, green, equal, observer, tempBias);
|
||||
}
|
||||
}
|
||||
|
||||
void BatchToolPanelCoordinator::getCamWB (double& temp, double& green)
|
||||
void BatchToolPanelCoordinator::getCamWB (double& temp, double& green, rtengine::StandardObserver observer)
|
||||
{
|
||||
|
||||
if (!selected.empty()) {
|
||||
selected[0]->getCamWB (temp, green);
|
||||
selected[0]->getCamWB (temp, green, observer);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -69,8 +69,8 @@ public:
|
||||
) override;
|
||||
|
||||
// wbprovider interface
|
||||
void getAutoWB (double& temp, double& green, double equal, double tempBias) override;
|
||||
void getCamWB (double& temp, double& green) override;
|
||||
void getAutoWB (double& temp, double& green, double equal, rtengine::StandardObserver observer, double tempBias) override;
|
||||
void getCamWB (double& temp, double& green, rtengine::StandardObserver observer) override;
|
||||
|
||||
// thumbnaillistener interface
|
||||
void procParamsChanged (Thumbnail* thm, int whoChangedIt) override;
|
||||
|
@ -80,7 +80,7 @@ void CheckBox::setValue (CheckValue newValue)
|
||||
break;
|
||||
case CheckValue::off:
|
||||
set_inconsistent (false);
|
||||
set_active(true);
|
||||
set_active(false);
|
||||
lastActive = false;
|
||||
break;
|
||||
case CheckValue::unchanged:
|
||||
|
@ -33,6 +33,12 @@ const Glib::ustring FilmNegative::TOOL_NAME = "filmnegative";
|
||||
namespace
|
||||
{
|
||||
|
||||
/**
|
||||
* Observer to use for displaying the temperature and tint equivalent of the
|
||||
* multipliers.
|
||||
*/
|
||||
constexpr rtengine::StandardObserver standard_observer = rtengine::ColorTemp::DEFAULT_OBSERVER;
|
||||
|
||||
double toAdjuster(double v)
|
||||
{
|
||||
return CLAMP(std::log2(v), 6, 16) - 6;
|
||||
@ -154,7 +160,7 @@ RGB getFilmNegativeExponents(const RGB &ref1, const RGB &ref2) // , const RGB &c
|
||||
|
||||
void temp2rgb(double outLev, double temp, double green, RGB &refOut)
|
||||
{
|
||||
rtengine::ColorTemp ct = rtengine::ColorTemp(temp, green, 1., "Custom");
|
||||
rtengine::ColorTemp ct = rtengine::ColorTemp(temp, green, 1., "Custom", standard_observer);
|
||||
|
||||
double rm, gm, bm;
|
||||
ct.getMultipliers(rm, gm, bm);
|
||||
@ -175,7 +181,8 @@ void rgb2temp(const RGB &refOut, double &outLev, double &temp, double &green)
|
||||
refOut.r / maxVal,
|
||||
refOut.g / maxVal,
|
||||
refOut.b / maxVal,
|
||||
1.);
|
||||
1.,
|
||||
standard_observer);
|
||||
|
||||
outLev = maxVal;
|
||||
temp = ct.getTemp();
|
||||
@ -188,7 +195,7 @@ void rgb2temp(const RGB &refOut, double &outLev, double &temp, double &green)
|
||||
FilmNegative::FilmNegative() :
|
||||
FoldableToolPanel(this, TOOL_NAME, M("TP_FILMNEGATIVE_LABEL"), false, true),
|
||||
EditSubscriber(ET_OBJECTS),
|
||||
NEUTRAL_TEMP(rtengine::ColorTemp(1., 1., 1., 1.)),
|
||||
NEUTRAL_TEMP(rtengine::ColorTemp(1., 1., 1., 1., rtengine::ColorTemp::DEFAULT_OBSERVER)),
|
||||
evFilmNegativeExponents(ProcEventMapper::getInstance()->newEvent(ALLNORAW, "HISTORY_MSG_FILMNEGATIVE_VALUES")),
|
||||
evFilmNegativeEnabled(ProcEventMapper::getInstance()->newEvent(ALLNORAW, "HISTORY_MSG_FILMNEGATIVE_ENABLED")),
|
||||
evFilmNegativeRefSpot(ProcEventMapper::getInstance()->newEvent(ALLNORAW, "HISTORY_MSG_FILMNEGATIVE_REF_SPOT")),
|
||||
|
@ -595,7 +595,6 @@ void Options::setDefaults()
|
||||
rtSettings.monitorIntent = rtengine::RI_RELATIVE;
|
||||
rtSettings.monitorBPC = true;
|
||||
rtSettings.autocielab = false;
|
||||
rtSettings.observer10 = false;
|
||||
rtSettings.autoMonitorProfile = false;
|
||||
rtSettings.adobe = "RTv2_Medium"; // put the name of yours profiles (here windows)
|
||||
rtSettings.prophoto = "RTv2_Large"; // these names appear in the menu "output profile"
|
||||
@ -623,18 +622,8 @@ void Options::setDefaults()
|
||||
rtSettings.previewselection = 5;//between 1 to 40
|
||||
rtSettings.cbdlsensi = 1.0;//between 0.001 to 1
|
||||
rtSettings.fftwsigma = true; //choice between sigma^2 or empirical formula
|
||||
|
||||
rtSettings.itcwb_thres = 34;//between 10 to 55
|
||||
rtSettings.itcwb_sorted = true;
|
||||
rtSettings.itcwb_greenrange = 0;//between 0 to 2
|
||||
rtSettings.itcwb_greendeltatemp = 2;//between 0 and 4
|
||||
rtSettings.itcwb_forceextra = true;
|
||||
rtSettings.itcwb_sizereference = 3;//between 1 and 5
|
||||
rtSettings.itcwb_delta = 1;//between 0 and 5
|
||||
rtSettings.itcwb_stdobserver10 = true;
|
||||
rtSettings.itcwb_precis = 3;//3 or 5 or 9
|
||||
rtSettings.itcwb_nopurple = true;
|
||||
// end locallab
|
||||
rtSettings.itcwb_enable = true;
|
||||
|
||||
//wavelet
|
||||
rtSettings.edghi = 3.0;//1.1 and 5.
|
||||
@ -1767,10 +1756,6 @@ void Options::readFromFile(Glib::ustring fname)
|
||||
rtSettings.autocielab = keyFile.get_boolean("Color Management", "Autocielab");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Observer10")) {
|
||||
rtSettings.observer10 = keyFile.get_boolean("Color Management", "Observer10");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "CRI")) {
|
||||
rtSettings.CRI_color = keyFile.get_integer("Color Management", "CRI");
|
||||
}
|
||||
@ -1802,45 +1787,10 @@ void Options::readFromFile(Glib::ustring fname)
|
||||
rtSettings.level123_cbdl = keyFile.get_double("Color Management", "CBDLlevel123");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_thres")) {
|
||||
rtSettings.itcwb_thres = keyFile.get_integer("Color Management", "Itcwb_thres");
|
||||
if (keyFile.has_key("Color Management", "Itcwb_enable")) {
|
||||
rtSettings.itcwb_enable = keyFile.get_boolean("Color Management", "Itcwb_enable");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_sorted")) {
|
||||
rtSettings.itcwb_sorted = keyFile.get_boolean("Color Management", "Itcwb_sorted");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_forceextra")) {
|
||||
rtSettings.itcwb_forceextra = keyFile.get_boolean("Color Management", "Itcwb_forceextra");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_nopurple")) {
|
||||
rtSettings.itcwb_nopurple = keyFile.get_boolean("Color Management", "Itcwb_nopurple");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_stdobserver10")) {
|
||||
rtSettings.itcwb_stdobserver10 = keyFile.get_boolean("Color Management", "Itcwb_stdobserver10");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_greenrange")) {
|
||||
rtSettings.itcwb_greenrange = keyFile.get_integer("Color Management", "Itcwb_greenrange");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_greendeltatemp")) {
|
||||
rtSettings.itcwb_greendeltatemp = keyFile.get_integer("Color Management", "Itcwb_greendeltatemp");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_sizereference")) {
|
||||
rtSettings.itcwb_sizereference = keyFile.get_integer("Color Management", "Itcwb_sizereference");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_delta")) {
|
||||
rtSettings.itcwb_delta = keyFile.get_integer("Color Management", "Itcwb_delta");
|
||||
}
|
||||
|
||||
if (keyFile.has_key("Color Management", "Itcwb_precis")) {
|
||||
rtSettings.itcwb_precis = keyFile.get_integer("Color Management", "Itcwb_precis");
|
||||
}
|
||||
|
||||
//if (keyFile.has_key ("Color Management", "Colortoningab")) rtSettings.colortoningab = keyFile.get_double("Color Management", "Colortoningab");
|
||||
//if (keyFile.has_key ("Color Management", "Decaction")) rtSettings.decaction = keyFile.get_double("Color Management", "Decaction");
|
||||
@ -2579,7 +2529,6 @@ void Options::saveToFile(Glib::ustring fname)
|
||||
keyFile.set_string("Color Management", "MonitorProfile", rtSettings.monitorProfile);
|
||||
keyFile.set_boolean("Color Management", "AutoMonitorProfile", rtSettings.autoMonitorProfile);
|
||||
keyFile.set_boolean("Color Management", "Autocielab", rtSettings.autocielab);
|
||||
keyFile.set_boolean("Color Management", "Observer10", rtSettings.observer10);
|
||||
keyFile.set_boolean("Color Management", "RGBcurvesLumamode_Gamut", rtSettings.rgbcurveslumamode_gamut);
|
||||
keyFile.set_integer("Color Management", "Intent", rtSettings.monitorIntent);
|
||||
keyFile.set_boolean("Color Management", "MonitorBPC", rtSettings.monitorBPC);
|
||||
@ -2612,16 +2561,7 @@ void Options::saveToFile(Glib::ustring fname)
|
||||
//keyFile.set_boolean ("Color Management", "Ciebadpixgauss", rtSettings.ciebadpixgauss);
|
||||
keyFile.set_double("Color Management", "CBDLlevel0", rtSettings.level0_cbdl);
|
||||
keyFile.set_double("Color Management", "CBDLlevel123", rtSettings.level123_cbdl);
|
||||
keyFile.set_integer("Color Management", "Itcwb_thres", rtSettings.itcwb_thres);
|
||||
keyFile.set_boolean("Color Management", "Itcwb_sorted", rtSettings.itcwb_sorted);
|
||||
keyFile.set_integer("Color Management", "Itcwb_greenrange", rtSettings.itcwb_greenrange);
|
||||
keyFile.set_integer("Color Management", "Itcwb_greendeltatemp", rtSettings.itcwb_greendeltatemp);
|
||||
keyFile.set_boolean("Color Management", "Itcwb_forceextra", rtSettings.itcwb_forceextra);
|
||||
keyFile.set_boolean("Color Management", "Itcwb_nopurple", rtSettings.itcwb_nopurple);
|
||||
keyFile.set_integer("Color Management", "Itcwb_sizereference", rtSettings.itcwb_sizereference);
|
||||
keyFile.set_integer("Color Management", "Itcwb_delta", rtSettings.itcwb_delta);
|
||||
keyFile.set_boolean("Color Management", "Itcwb_stdobserver10", rtSettings.itcwb_stdobserver10);
|
||||
keyFile.set_integer("Color Management", "Itcwb_precis", rtSettings.itcwb_precis);
|
||||
keyFile.set_boolean("Color Management", "Itcwb_enable", rtSettings.itcwb_enable);
|
||||
|
||||
//keyFile.set_double ("Color Management", "Colortoningab", rtSettings.colortoningab);
|
||||
//keyFile.set_double ("Color Management", "Decaction", rtSettings.decaction);
|
||||
|
@ -266,6 +266,17 @@ void ParamsEdited::set(bool v)
|
||||
wb.temperature = v;
|
||||
wb.equal = v;
|
||||
wb.tempBias = v;
|
||||
wb.observer = v;
|
||||
wb.itcwb_thres = v;
|
||||
wb.itcwb_precis = v;
|
||||
wb.itcwb_size = v;
|
||||
wb.itcwb_delta = v;
|
||||
wb.itcwb_fgreen = v;
|
||||
wb.itcwb_rgreen = v;
|
||||
wb.itcwb_nopurple = v;
|
||||
wb.itcwb_sorted = v;
|
||||
wb.itcwb_forceextra = v;
|
||||
wb.itcwb_sampling = v;
|
||||
//colorShift.a = v;
|
||||
//colorShift.b = v;
|
||||
//lumaDenoise.enabled = v;
|
||||
@ -967,6 +978,17 @@ void ParamsEdited::initFrom(const std::vector<rtengine::procparams::ProcParams>&
|
||||
wb.equal = wb.equal && p.wb.equal == other.wb.equal;
|
||||
wb.temperature = wb.temperature && p.wb.temperature == other.wb.temperature;
|
||||
wb.tempBias = wb.tempBias && p.wb.tempBias == other.wb.tempBias;
|
||||
wb.observer = wb.observer && p.wb.observer == other.wb.observer;
|
||||
wb.itcwb_thres = wb.itcwb_thres && p.wb.itcwb_thres == other.wb.itcwb_thres;
|
||||
wb.itcwb_precis = wb.itcwb_precis && p.wb.itcwb_precis == other.wb.itcwb_precis;
|
||||
wb.itcwb_size = wb.itcwb_size && p.wb.itcwb_size == other.wb.itcwb_size;
|
||||
wb.itcwb_delta = wb.itcwb_delta && p.wb.itcwb_delta == other.wb.itcwb_delta;
|
||||
wb.itcwb_fgreen = wb.itcwb_fgreen && p.wb.itcwb_fgreen == other.wb.itcwb_fgreen;
|
||||
wb.itcwb_rgreen = wb.itcwb_rgreen && p.wb.itcwb_rgreen == other.wb.itcwb_rgreen;
|
||||
wb.itcwb_nopurple = wb.itcwb_nopurple && p.wb.itcwb_nopurple == other.wb.itcwb_nopurple;
|
||||
wb.itcwb_sorted = wb.itcwb_sorted && p.wb.itcwb_sorted == other.wb.itcwb_sorted;
|
||||
wb.itcwb_forceextra = wb.itcwb_forceextra && p.wb.itcwb_forceextra == other.wb.itcwb_forceextra;
|
||||
wb.itcwb_sampling = wb.itcwb_sampling && p.wb.itcwb_sampling == other.wb.itcwb_sampling;
|
||||
//colorShift.a = colorShift.a && p.colorShift.a == other.colorShift.a;
|
||||
//colorShift.b = colorShift.b && p.colorShift.b == other.colorShift.b;
|
||||
//lumaDenoise.enabled = lumaDenoise.enabled && p.lumaDenoise.enabled == other.lumaDenoise.enabled;
|
||||
@ -2829,6 +2851,50 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng
|
||||
toEdit.wb.tempBias = dontforceSet && options.baBehav[ADDSET_WB_TEMPBIAS] ? toEdit.wb.tempBias + mods.wb.tempBias : mods.wb.tempBias;
|
||||
}
|
||||
|
||||
if (wb.observer) {
|
||||
toEdit.wb.observer = mods.wb.observer;
|
||||
}
|
||||
|
||||
if (wb.itcwb_thres) {
|
||||
toEdit.wb.itcwb_thres = mods.wb.itcwb_thres;
|
||||
}
|
||||
|
||||
if (wb.itcwb_precis) {
|
||||
toEdit.wb.itcwb_precis = mods.wb.itcwb_precis;
|
||||
}
|
||||
|
||||
if (wb.itcwb_size) {
|
||||
toEdit.wb.itcwb_size = mods.wb.itcwb_size;
|
||||
}
|
||||
|
||||
if (wb.itcwb_delta) {
|
||||
toEdit.wb.itcwb_delta = mods.wb.itcwb_delta;
|
||||
}
|
||||
|
||||
if (wb.itcwb_fgreen) {
|
||||
toEdit.wb.itcwb_fgreen = mods.wb.itcwb_fgreen;
|
||||
}
|
||||
|
||||
if (wb.itcwb_rgreen) {
|
||||
toEdit.wb.itcwb_rgreen = mods.wb.itcwb_rgreen;
|
||||
}
|
||||
|
||||
if (wb.itcwb_nopurple) {
|
||||
toEdit.wb.itcwb_nopurple = mods.wb.itcwb_nopurple;
|
||||
}
|
||||
|
||||
if (wb.itcwb_sorted) {
|
||||
toEdit.wb.itcwb_sorted = mods.wb.itcwb_sorted;
|
||||
}
|
||||
|
||||
if (wb.itcwb_forceextra) {
|
||||
toEdit.wb.itcwb_forceextra = mods.wb.itcwb_forceextra;
|
||||
}
|
||||
|
||||
if (wb.itcwb_sampling) {
|
||||
toEdit.wb.itcwb_sampling = mods.wb.itcwb_sampling;
|
||||
}
|
||||
|
||||
if (wb.green) {
|
||||
toEdit.wb.green = dontforceSet && options.baBehav[ADDSET_WB_GREEN] ? toEdit.wb.green + mods.wb.green : mods.wb.green;
|
||||
}
|
||||
|
@ -246,7 +246,19 @@ struct WBParamsEdited {
|
||||
bool temperature;
|
||||
bool green;
|
||||
bool equal;
|
||||
bool observer;
|
||||
bool tempBias;
|
||||
bool itcwb_thres;
|
||||
bool itcwb_precis;
|
||||
bool itcwb_size;
|
||||
bool itcwb_delta;
|
||||
bool itcwb_fgreen;
|
||||
bool itcwb_rgreen;
|
||||
bool itcwb_nopurple;
|
||||
bool itcwb_sorted;
|
||||
bool itcwb_forceextra;
|
||||
bool itcwb_sampling;
|
||||
|
||||
};
|
||||
|
||||
struct DefringeParamsEdited {
|
||||
|
@ -1,11 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
// This number has to be incremented whenever the PP3 file format is modified or the behaviour of a tool changes
|
||||
#define PPVERSION 349
|
||||
#define PPVERSION 350
|
||||
#define PPVERSION_AEXP 301 //value of PPVERSION when auto exposure algorithm was modified
|
||||
|
||||
/*
|
||||
Log of version changes
|
||||
350 2023-03-05
|
||||
introduced white balance standard observer
|
||||
349 2020-10-29
|
||||
replaced Haze removal Luminance checkbox with an adjuster to blend between luminance and normal mode
|
||||
348 2018-09-25
|
||||
|
@ -928,6 +928,10 @@ Gtk::Widget* Preferences::getColorManPanel ()
|
||||
fcie->add(*gcie);
|
||||
|
||||
vbColorMan->pack_start (*fcie, Gtk::PACK_SHRINK);
|
||||
|
||||
|
||||
//-------------
|
||||
|
||||
swColorMan->add(*vbColorMan);
|
||||
return swColorMan;
|
||||
}
|
||||
@ -1954,6 +1958,7 @@ void Preferences::fillPreferences()
|
||||
|
||||
monBPC->set_active(moptions.rtSettings.monitorBPC);
|
||||
mcie->set_active(moptions.rtSettings.autocielab);
|
||||
|
||||
cbAutoMonProfile->set_active(moptions.rtSettings.autoMonitorProfile);
|
||||
#endif
|
||||
|
||||
|
@ -135,6 +135,15 @@ class Preferences final :
|
||||
Gtk::CheckButton* cbdaubech;
|
||||
Gtk::SpinButton* hlThresh;
|
||||
Gtk::SpinButton* shThresh;
|
||||
// Gtk::CheckButton* mwbacorr;
|
||||
// Gtk::CheckButton* mwbaforc;
|
||||
// Gtk::CheckButton* mwbanopurp;
|
||||
|
||||
// Gtk::CheckButton* mwbasort;
|
||||
// Gtk::SpinButton* wbacorrnb;
|
||||
// Gtk::SpinButton* wbaprecis;
|
||||
// Gtk::SpinButton* wbasizeref;
|
||||
// Gtk::SpinButton* wbagreendelta;
|
||||
|
||||
Gtk::SpinButton* panFactor;
|
||||
Gtk::CheckButton* rememberZoomPanCheckbutton;
|
||||
@ -240,7 +249,7 @@ class Preferences final :
|
||||
|
||||
Options moptions;
|
||||
sigc::connection tconn, sconn, fconn, cpfconn, addc, setc, dfconn, ffconn, bpconn, rpconn, ipconn;
|
||||
sigc::connection autoMonProfileConn, sndEnableConn, langAutoDetectConn, autocielabConn;
|
||||
sigc::connection autoMonProfileConn, sndEnableConn, langAutoDetectConn, autocielabConn, observer10Conn;
|
||||
Glib::ustring initialTheme;
|
||||
Glib::ustring initialFontFamily;
|
||||
int initialFontSize;
|
||||
@ -305,6 +314,7 @@ public:
|
||||
void sndEnableToggled ();
|
||||
void langAutoDetectToggled ();
|
||||
void autocielabToggled ();
|
||||
void observer10Toggled ();
|
||||
|
||||
void selectStartupDir ();
|
||||
void addExtPressed ();
|
||||
|
@ -139,20 +139,20 @@ void Thumbnail::_generateThumbnailImage ()
|
||||
|
||||
if (ext == "jpg" || ext == "jpeg") {
|
||||
infoFromImage (fname);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, tw, th, -1, pparams->wb.equal);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, tw, th, -1, pparams->wb.equal, pparams->wb.observer);
|
||||
|
||||
if (tpp) {
|
||||
cfs.format = FT_Jpeg;
|
||||
}
|
||||
} else if (ext == "png") {
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, tw, th, -1, pparams->wb.equal);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, tw, th, -1, pparams->wb.equal, pparams->wb.observer);
|
||||
|
||||
if (tpp) {
|
||||
cfs.format = FT_Png;
|
||||
}
|
||||
} else if (ext == "tif" || ext == "tiff") {
|
||||
infoFromImage (fname);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, tw, th, -1, pparams->wb.equal);
|
||||
tpp = rtengine::Thumbnail::loadFromImage (fname, tw, th, -1, pparams->wb.equal, pparams->wb.observer);
|
||||
|
||||
if (tpp) {
|
||||
cfs.format = FT_Tiff;
|
||||
@ -173,7 +173,7 @@ void Thumbnail::_generateThumbnailImage ()
|
||||
|
||||
if ( tpp == nullptr ) {
|
||||
quick = false;
|
||||
tpp = rtengine::Thumbnail::loadFromRaw (fname, ri, sensorType, tw, th, 1, pparams->wb.equal, TRUE);
|
||||
tpp = rtengine::Thumbnail::loadFromRaw (fname, ri, sensorType, tw, th, 1, pparams->wb.equal, pparams->wb.observer, TRUE);
|
||||
}
|
||||
|
||||
cfs.sensortype = sensorType;
|
||||
@ -216,11 +216,11 @@ const ProcParams& Thumbnail::getProcParamsU ()
|
||||
|
||||
if (pparams->wb.method == "Camera") {
|
||||
double ct;
|
||||
getCamWB (ct, pparams->wb.green);
|
||||
getCamWB (ct, pparams->wb.green, pparams->wb.observer);
|
||||
pparams->wb.temperature = ct;
|
||||
} else if (pparams->wb.method == "autold") {
|
||||
double ct;
|
||||
getAutoWB (ct, pparams->wb.green, pparams->wb.equal, pparams->wb.tempBias);
|
||||
getAutoWB (ct, pparams->wb.green, pparams->wb.equal, pparams->wb.observer, pparams->wb.tempBias);
|
||||
pparams->wb.temperature = ct;
|
||||
}
|
||||
}
|
||||
@ -785,10 +785,10 @@ const Glib::DateTime& Thumbnail::getDateTime () const
|
||||
return dateTime;
|
||||
}
|
||||
|
||||
void Thumbnail::getAutoWB (double& temp, double& green, double equal, double tempBias)
|
||||
void Thumbnail::getAutoWB (double& temp, double& green, double equal, rtengine::StandardObserver observer, double tempBias)
|
||||
{
|
||||
if (cfs.redAWBMul != -1.0) {
|
||||
rtengine::ColorTemp ct(cfs.redAWBMul, cfs.greenAWBMul, cfs.blueAWBMul, equal);
|
||||
rtengine::ColorTemp ct(cfs.redAWBMul, cfs.greenAWBMul, cfs.blueAWBMul, equal, observer);
|
||||
temp = ct.getTemp();
|
||||
green = ct.getGreen();
|
||||
} else {
|
||||
@ -1155,10 +1155,10 @@ bool Thumbnail::imageLoad(bool loading)
|
||||
return false;
|
||||
}
|
||||
|
||||
void Thumbnail::getCamWB(double& temp, double& green) const
|
||||
void Thumbnail::getCamWB(double& temp, double& green, rtengine::StandardObserver observer) const
|
||||
{
|
||||
if (tpp) {
|
||||
tpp->getCamWB (temp, green);
|
||||
tpp->getCamWB (temp, green, observer);
|
||||
} else {
|
||||
temp = green = -1.0;
|
||||
}
|
||||
|
@ -127,8 +127,8 @@ public:
|
||||
const Glib::ustring& getExifString () const;
|
||||
const Glib::ustring& getDateTimeString () const;
|
||||
const Glib::DateTime& getDateTime () const;
|
||||
void getCamWB (double& temp, double& green) const;
|
||||
void getAutoWB (double& temp, double& green, double equal, double tempBias);
|
||||
void getCamWB (double& temp, double& green, rtengine::StandardObserver observer) const;
|
||||
void getAutoWB (double& temp, double& green, double equal, rtengine::StandardObserver observer, double tempBias);
|
||||
void getSpotWB (int x, int y, int rect, double& temp, double& green);
|
||||
void applyAutoExp (rtengine::procparams::ProcParams& pparams);
|
||||
|
||||
|
@ -398,16 +398,16 @@ public:
|
||||
void updateShowtooltipVisibility (bool showtooltip);
|
||||
|
||||
// wbprovider interface
|
||||
void getAutoWB (double& temp, double& green, double equal, double tempBias) override
|
||||
void getAutoWB (double& temp, double& green, double equal, rtengine::StandardObserver observer, double tempBias) override
|
||||
{
|
||||
if (ipc) {
|
||||
ipc->getAutoWB(temp, green, equal, tempBias);
|
||||
ipc->getAutoWB(temp, green, equal, observer, tempBias);
|
||||
}
|
||||
}
|
||||
void getCamWB (double& temp, double& green) override
|
||||
void getCamWB (double& temp, double& green, rtengine::StandardObserver observer) override
|
||||
{
|
||||
if (ipc) {
|
||||
ipc->getCamWB(temp, green);
|
||||
ipc->getCamWB(temp, green, observer);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -18,12 +18,19 @@
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
namespace rtengine
|
||||
{
|
||||
|
||||
enum class StandardObserver;
|
||||
|
||||
}
|
||||
|
||||
class WBProvider
|
||||
{
|
||||
|
||||
public:
|
||||
virtual ~WBProvider() {}
|
||||
virtual void getAutoWB (double& temp, double& green, double equal, double tempBias) {}
|
||||
virtual void getCamWB (double& temp, double& green) {}
|
||||
virtual void getAutoWB (double& temp, double& green, double equal, rtengine::StandardObserver observer, double tempBias) {}
|
||||
virtual void getCamWB (double& temp, double& green, rtengine::StandardObserver observer) {}
|
||||
virtual void spotWBRequested (int size) {}
|
||||
};
|
||||
|
@ -22,6 +22,9 @@
|
||||
|
||||
#include "rtimage.h"
|
||||
#include "options.h"
|
||||
#include "eventmapper.h"
|
||||
|
||||
#include "../rtengine/colortemp.h"
|
||||
|
||||
#define MINTEMP 1500 //1200
|
||||
#define MAXTEMP 60000 //12000
|
||||
@ -242,6 +245,10 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, TOOL_NAME, M("TP_WBALANC
|
||||
custom_equal = 1.0;
|
||||
}
|
||||
|
||||
auto m = ProcEventMapper::getInstance();
|
||||
EvWBObserver10 = m->newEvent(ALLNORAW, "HISTORY_MSG_WBALANCE_OBSERVER10");
|
||||
|
||||
|
||||
//Add the model columns to the Combo (which is a kind of view),
|
||||
//rendering them in the default way:
|
||||
method->pack_start(methodColumns.colIcon, false);
|
||||
@ -336,19 +343,27 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, TOOL_NAME, M("TP_WBALANC
|
||||
StudLabel = Gtk::manage(new Gtk::Label("---", Gtk::ALIGN_CENTER));
|
||||
StudLabel->set_tooltip_text(M("TP_WBALANCE_STUDLABEL_TOOLTIP"));
|
||||
|
||||
mulLabel = Gtk::manage(new Gtk::Label("---", Gtk::ALIGN_CENTER));
|
||||
mulLabel->set_tooltip_text(M("TP_WBALANCE_MULLABEL_TOOLTIP"));
|
||||
mulLabel->show();
|
||||
|
||||
temp = Gtk::manage (new Adjuster (M("TP_WBALANCE_TEMPERATURE"), MINTEMP, MAXTEMP, 5, CENTERTEMP, itempL, itempR, &wbSlider2Temp, &wbTemp2Slider));
|
||||
green = Gtk::manage (new Adjuster (M("TP_WBALANCE_GREEN"), MINGREEN, MAXGREEN, 0.001, 1.0, igreenL, igreenR));
|
||||
equal = Gtk::manage (new Adjuster (M("TP_WBALANCE_EQBLUERED"), MINEQUAL, MAXEQUAL, 0.001, 1.0, iblueredL, iblueredR));
|
||||
tempBias = Gtk::manage (new Adjuster(M("TP_WBALANCE_TEMPBIAS"), -0.5, 0.5, 0.01, 0.0, itempbiasL, itempbiasR));
|
||||
observer10 = Gtk::manage(new CheckBox(M("TP_WBALANCE_OBSERVER10"), multiImage));
|
||||
|
||||
cache_customTemp (0);
|
||||
cache_customGreen (0);
|
||||
cache_customEqual (0);
|
||||
equal->set_tooltip_markup (M("TP_WBALANCE_EQBLUERED_TOOLTIP"));
|
||||
tempBias->set_tooltip_markup (M("TP_WBALANCE_TEMPBIAS_TOOLTIP"));
|
||||
observer10->set_tooltip_text(M("TP_WBALANCE_OBSERVER10_TOOLTIP"));
|
||||
temp->show ();
|
||||
green->show ();
|
||||
equal->show ();
|
||||
tempBias->show ();
|
||||
observer10->show();
|
||||
|
||||
/* Gtk::Box* boxgreen = Gtk::manage (new Gtk::Box ());
|
||||
boxgreen->show ();
|
||||
@ -356,6 +371,7 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, TOOL_NAME, M("TP_WBALANC
|
||||
boxgreen->pack_start(*igreenL);
|
||||
boxgreen->pack_start(*green);
|
||||
boxgreen->pack_start(*igreenR);*/
|
||||
pack_start(*mulLabel);
|
||||
pack_start(*StudLabel);
|
||||
|
||||
pack_start (*temp);
|
||||
@ -363,11 +379,14 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, TOOL_NAME, M("TP_WBALANC
|
||||
pack_start (*green);
|
||||
pack_start (*equal);
|
||||
pack_start (*tempBias);
|
||||
pack_start(*observer10);
|
||||
|
||||
|
||||
temp->setAdjusterListener (this);
|
||||
green->setAdjusterListener (this);
|
||||
equal->setAdjusterListener (this);
|
||||
tempBias->setAdjusterListener (this);
|
||||
observer10->setCheckBoxListener(this);
|
||||
|
||||
spotbutton->signal_pressed().connect( sigc::mem_fun(*this, &WhiteBalance::spotPressed) );
|
||||
methconn = method->signal_changed().connect( sigc::mem_fun(*this, &WhiteBalance::optChanged) );
|
||||
@ -394,6 +413,8 @@ void WhiteBalance::enabledChanged()
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void WhiteBalance::adjusterChanged(Adjuster* a, double newval)
|
||||
{
|
||||
int tVal = (int)temp->getValue();
|
||||
@ -456,6 +477,36 @@ void WhiteBalance::adjusterChanged(Adjuster* a, double newval)
|
||||
}
|
||||
}
|
||||
|
||||
void WhiteBalance::checkBoxToggled(CheckBox* c, CheckValue newval)
|
||||
{
|
||||
if (!(getEnabled() && listener)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (c == observer10) {
|
||||
// If camera WB, update the temperature and tint according to observer.
|
||||
const Gtk::TreeModel::Row row = getActiveMethod();
|
||||
unsigned int methodId = findWBEntryId(row[methodColumns.colLabel], WBLT_GUI);
|
||||
const WBEntry &currMethod = WBParams::getWbEntries()[methodId];
|
||||
if (row[methodColumns.colLabel] != M("GENERAL_UNCHANGED") && currMethod.type == WBEntry::Type::CAMERA && wbp) {
|
||||
double ctemp, cgreen;
|
||||
wbp->getCamWB(ctemp, cgreen,
|
||||
observer10->getValue() == CheckValue::off
|
||||
? rtengine::StandardObserver::TWO_DEGREES
|
||||
: rtengine::StandardObserver::TEN_DEGREES);
|
||||
temp->setValue(temp->getAddMode() ? 0.0 : static_cast<int>(ctemp));
|
||||
green->setValue(green->getAddMode() ? 0.0 : cgreen);
|
||||
}
|
||||
|
||||
listener->panelChanged(
|
||||
EvWBObserver10,
|
||||
c->getValue() == CheckValue::on ? M("GENERAL_ENABLED")
|
||||
: c->getValue() == CheckValue::off
|
||||
? M("GENERAL_DISABLED")
|
||||
: M("GENERAL_UNCHANGED"));
|
||||
}
|
||||
}
|
||||
|
||||
void WhiteBalance::optChanged ()
|
||||
{
|
||||
Gtk::TreeModel::Row row = getActiveMethod();
|
||||
@ -472,6 +523,7 @@ void WhiteBalance::optChanged ()
|
||||
return;
|
||||
}
|
||||
StudLabel->hide();
|
||||
mulLabel->show();
|
||||
|
||||
if (opt != row[methodColumns.colId]) {
|
||||
|
||||
@ -482,6 +534,7 @@ void WhiteBalance::optChanged ()
|
||||
green->setEditedState (UnEdited);
|
||||
equal->setEditedState (UnEdited);
|
||||
tempBias->setEditedState (UnEdited);
|
||||
observer10->setEdited(false);
|
||||
} else {
|
||||
unsigned int methodId = findWBEntryId (row[methodColumns.colLabel], WBLT_GUI);
|
||||
const WBEntry& currMethod = WBParams::getWbEntries()[methodId];
|
||||
@ -498,7 +551,10 @@ void WhiteBalance::optChanged ()
|
||||
case WBEntry::Type::CAMERA:
|
||||
if (wbp) {
|
||||
double ctemp, cgreen;
|
||||
wbp->getCamWB (ctemp, cgreen);
|
||||
wbp->getCamWB(ctemp, cgreen,
|
||||
observer10->getValue() == CheckValue::off
|
||||
? rtengine::StandardObserver::TWO_DEGREES
|
||||
: rtengine::StandardObserver::TEN_DEGREES);
|
||||
temp->setValue (temp->getAddMode() ? 0.0 : (int)ctemp);
|
||||
green->setValue (green->getAddMode() ? 0.0 : cgreen);
|
||||
equal->setValue (equal->getAddMode() ? 0.0 : 1.0);
|
||||
@ -507,6 +563,7 @@ void WhiteBalance::optChanged ()
|
||||
temp->setEditedState (UnEdited);
|
||||
green->setEditedState (UnEdited);
|
||||
equal->setEditedState (UnEdited);
|
||||
observer10->setEdited(false);
|
||||
}
|
||||
}
|
||||
|
||||
@ -517,7 +574,7 @@ void WhiteBalance::optChanged ()
|
||||
if (batchMode) {
|
||||
temp->setEditedState (UnEdited);
|
||||
green->setEditedState (UnEdited);
|
||||
// equal remain as is
|
||||
// equal and observer remain as is
|
||||
}
|
||||
|
||||
// Recomputing AutoWB will happen in improccoordinator.cc
|
||||
@ -540,6 +597,7 @@ void WhiteBalance::optChanged ()
|
||||
temp->setEditedState (Edited);
|
||||
green->setEditedState (Edited);
|
||||
equal->setEditedState (Edited);
|
||||
observer10->setEdited(true);
|
||||
}
|
||||
|
||||
break;
|
||||
@ -563,6 +621,7 @@ void WhiteBalance::optChanged ()
|
||||
temp->setEditedState (Edited);
|
||||
green->setEditedState (Edited);
|
||||
equal->setEditedState (Edited);
|
||||
observer10->setEdited(true);
|
||||
}
|
||||
|
||||
break;
|
||||
@ -578,6 +637,7 @@ void WhiteBalance::optChanged ()
|
||||
void WhiteBalance::spotPressed ()
|
||||
{
|
||||
StudLabel->hide();
|
||||
mulLabel->show();
|
||||
|
||||
if (wblistener) {
|
||||
wblistener->spotWBRequested (getSize());
|
||||
@ -599,6 +659,7 @@ void WhiteBalance::read (const ProcParams* pp, const ParamsEdited* pedited)
|
||||
|
||||
methconn.block (true);
|
||||
equal->setValue (pp->wb.equal);
|
||||
observer10->setValue(rtengine::StandardObserver::TEN_DEGREES == pp->wb.observer);
|
||||
tempBias->setValue (pp->wb.tempBias);
|
||||
tempBias->set_sensitive(true);
|
||||
|
||||
@ -608,6 +669,7 @@ void WhiteBalance::read (const ProcParams* pp, const ParamsEdited* pedited)
|
||||
green->setEditedState (UnEdited);
|
||||
equal->setEditedState (pedited->wb.equal ? Edited : UnEdited);
|
||||
tempBias->setEditedState (pedited->wb.tempBias ? Edited : UnEdited);
|
||||
observer10->setEdited(pedited->wb.observer);
|
||||
}
|
||||
|
||||
if (pedited && !pedited->wb.method) {
|
||||
@ -648,7 +710,7 @@ void WhiteBalance::read (const ProcParams* pp, const ParamsEdited* pedited)
|
||||
if (wbp) {
|
||||
double ctemp = -1.0;
|
||||
double cgreen = -1.0;
|
||||
wbp->getCamWB (ctemp, cgreen);
|
||||
wbp->getCamWB (ctemp, cgreen, pp->wb.observer);
|
||||
|
||||
if (ctemp != -1.0) {
|
||||
// Set the camera's temperature value, or 0.0 if in ADD mode
|
||||
@ -720,6 +782,7 @@ void WhiteBalance::read (const ProcParams* pp, const ParamsEdited* pedited)
|
||||
StudLabel->show();
|
||||
} else {
|
||||
StudLabel->hide();
|
||||
mulLabel->show();
|
||||
}
|
||||
|
||||
}
|
||||
@ -744,6 +807,7 @@ void WhiteBalance::write (ProcParams* pp, ParamsEdited* pedited)
|
||||
pedited->wb.green = green->getEditedState ();
|
||||
pedited->wb.equal = equal->getEditedState ();
|
||||
pedited->wb.tempBias = tempBias->getEditedState ();
|
||||
pedited->wb.observer = observer10->getEdited();
|
||||
pedited->wb.method = row[methodColumns.colLabel] != M("GENERAL_UNCHANGED");
|
||||
pedited->wb.enabled = !get_inconsistent();
|
||||
}
|
||||
@ -759,6 +823,12 @@ void WhiteBalance::write (ProcParams* pp, ParamsEdited* pedited)
|
||||
pp->wb.temperature = temp->getIntValue ();
|
||||
pp->wb.green = green->getValue ();
|
||||
pp->wb.equal = equal->getValue ();
|
||||
pp->wb.observer =
|
||||
observer10->getValue() == CheckValue::on
|
||||
? rtengine::StandardObserver::TEN_DEGREES
|
||||
: observer10->getValue() == CheckValue::off
|
||||
? rtengine::StandardObserver::TWO_DEGREES
|
||||
: pp->wb.observer;
|
||||
pp->wb.tempBias = tempBias->getValue ();
|
||||
}
|
||||
|
||||
@ -771,7 +841,7 @@ void WhiteBalance::setDefaults (const ProcParams* defParams, const ParamsEdited*
|
||||
if (wbp && defParams->wb.method == "Camera") {
|
||||
double ctemp;
|
||||
double cgreen;
|
||||
wbp->getCamWB (ctemp, cgreen);
|
||||
wbp->getCamWB (ctemp, cgreen, defParams->wb.observer);
|
||||
|
||||
// FIXME: Seems to be always -1.0, called too early? Broken!
|
||||
if (ctemp != -1.0) {
|
||||
@ -945,14 +1015,20 @@ inline Gtk::TreeRow WhiteBalance::getActiveMethod ()
|
||||
return *(method->get_active());
|
||||
}
|
||||
|
||||
void WhiteBalance::WBChanged(double temperature, double greenVal, float studgood)
|
||||
void WhiteBalance::WBChanged(double temperature, double greenVal, double rw, double gw, double bw, float studgood)
|
||||
{
|
||||
idle_register.add(
|
||||
[this, temperature, greenVal, studgood]() -> bool
|
||||
[this, temperature, greenVal, rw, gw, bw, studgood]() -> bool
|
||||
{
|
||||
disableListener();
|
||||
temp->setValue(temperature);
|
||||
green->setValue(greenVal);
|
||||
mulLabel->set_text(
|
||||
Glib::ustring::compose(M("TP_WBALANCE_MULLABEL"),
|
||||
Glib::ustring::format(std::fixed, std::setprecision(4), rw),
|
||||
Glib::ustring::format(std::fixed, std::setprecision(2), gw),
|
||||
Glib::ustring::format(std::fixed, std::setprecision(4), bw))
|
||||
);
|
||||
StudLabel->set_text(
|
||||
Glib::ustring::compose(M("TP_WBALANCE_STUDLABEL"),
|
||||
Glib::ustring::format(std::fixed, std::setprecision(4), studgood))
|
||||
|
@ -21,6 +21,7 @@
|
||||
#include <gtkmm.h>
|
||||
|
||||
#include "adjuster.h"
|
||||
#include "checkbox.h"
|
||||
#include "guiutils.h"
|
||||
#include "toolpanel.h"
|
||||
#include "wbprovider.h"
|
||||
@ -35,7 +36,7 @@ public:
|
||||
virtual void spotWBRequested(int size) = 0;
|
||||
};
|
||||
|
||||
class WhiteBalance final : public ToolParamBlock, public AdjusterListener, public FoldableToolPanel, public rtengine::AutoWBListener
|
||||
class WhiteBalance final : public ToolParamBlock, public AdjusterListener, public CheckBoxListener, public FoldableToolPanel, public rtengine::AutoWBListener
|
||||
{
|
||||
|
||||
enum WB_LabelType {
|
||||
@ -45,6 +46,7 @@ class WhiteBalance final : public ToolParamBlock, public AdjusterListener, publi
|
||||
|
||||
private:
|
||||
Gtk::Label* StudLabel;
|
||||
Gtk::Label* mulLabel;
|
||||
|
||||
protected:
|
||||
class MethodColumns : public Gtk::TreeModel::ColumnRecord
|
||||
@ -61,6 +63,8 @@ protected:
|
||||
}
|
||||
};
|
||||
|
||||
rtengine::ProcEvent EvWBObserver10;
|
||||
|
||||
static Glib::RefPtr<Gdk::Pixbuf> wbPixbufs[rtengine::toUnderlying(rtengine::procparams::WBEntry::Type::CUSTOM) + 1];
|
||||
Glib::RefPtr<Gtk::TreeStore> refTreeModel;
|
||||
MethodColumns methodColumns;
|
||||
@ -71,6 +75,7 @@ protected:
|
||||
Adjuster* green;
|
||||
Adjuster* equal;
|
||||
Adjuster* tempBias;
|
||||
CheckBox* observer10;
|
||||
|
||||
Gtk::Button* spotbutton;
|
||||
int opt;
|
||||
@ -114,6 +119,7 @@ public:
|
||||
void spotPressed ();
|
||||
void spotSizeChanged ();
|
||||
void adjusterChanged(Adjuster* a, double newval) override;
|
||||
void checkBoxToggled(CheckBox* c, CheckValue newval) override;
|
||||
int getSize ();
|
||||
void setWBProvider (WBProvider* p)
|
||||
{
|
||||
@ -125,7 +131,7 @@ public:
|
||||
}
|
||||
void setWB (int temp, double green);
|
||||
void resetWB ();
|
||||
void WBChanged (double temp, double green, float studgood) override;
|
||||
void WBChanged (double temp, double green, double rw, double gw, double bw, float studgood) override;
|
||||
|
||||
void setAdjusterBehavior (bool tempadd, bool greenadd, bool equaladd, bool tempbiasadd);
|
||||
void trimValues (rtengine::procparams::ProcParams* pp) override;
|
||||
|
Loading…
x
Reference in New Issue
Block a user