Pixelshift: Added per channel brightness equalization

This commit is contained in:
heckflosse 2017-04-10 20:39:00 +02:00
parent 14f544fcc2
commit e043e792db
10 changed files with 134 additions and 34 deletions

View File

@ -720,6 +720,7 @@ HISTORY_MSG_471;PS Motion correction
HISTORY_MSG_472;PS Smooth transitions
HISTORY_MSG_473;PS Use lmmse
HISTORY_MSG_474;PS Equalize
HISTORY_MSG_475;PS Equalize channel
HISTORY_NEWSNAPSHOT;Add
HISTORY_NEWSNAPSHOT_TOOLTIP;Shortcut: <b>Alt-s</b>
HISTORY_SNAPSHOT;Snapshot
@ -1728,6 +1729,8 @@ TP_RAW_PIXELSHIFTEPERISO;ISO adaption
TP_RAW_PIXELSHIFTEPERISO_TOOLTIP;The default value (0.0) should work fine for base ISO.\nIncrease the value to improve motion detection for higher ISO.\nIncrease in small steps and watch the motion mask while increasing.
TP_RAW_PIXELSHIFTEQUALBRIGHT;Equalize brightness of frames
TP_RAW_PIXELSHIFTEQUALBRIGHT_TOOLTIP;Equalize the brightness of the frames to the brightness of the selected frame.\nIf there are overexposed areas in the frames select the brightest frame to avoid magenta colour cast in overexposed areas or enable motion correction.
TP_RAW_PIXELSHIFTEQUALBRIGHTCHANNEL;Equalize per channel
TP_RAW_PIXELSHIFTEQUALBRIGHTCHANNEL_TOOLTIP;Enabled: Equalize the channels (RGB) individually.\nDisabled: Use same equalization factor for all channels.
TP_RAW_PIXELSHIFTEXP0;Experimental
TP_RAW_PIXELSHIFTGREEN;Check green channel for motion
TP_RAW_PIXELSHIFTHOLEFILL;Fill holes in motion mask

View File

@ -304,6 +304,29 @@ void floodFill4(int xStart, int xEnd, int yStart, int yEnd, array2D<uint8_t> &ma
}
}
void calcFrameBrightnessFactor(unsigned int frame, uint32_t datalen, LUT<uint32_t> *histo[4], float brightnessFactor[4])
{
float medians[4];
for(int i = 0; i < 4; ++i) {
//find median of histogram
uint32_t median = 0, count = 0;
while (count < datalen / 2) {
count += (*histo[i])[median];
++median;
}
const float weight = (count - datalen / 2.f) / (*histo[i])[median - 1];
medians[i] = rtengine::intp(weight, (float)(median - 2), (float)(median - 1));
}
for(int i = 0; i < 4; ++i) {
brightnessFactor[i] = medians[frame] / medians[i];
}
}
}
using namespace std;
@ -372,7 +395,7 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
multi_array2D<float,3> redTmp(W,H);
multi_array2D<float,3> greenTmp(W,H);
multi_array2D<float,3> blueTmp(W,H);
for(int i=0, frameIndex = 0;i<4;++i) {
for(unsigned int i=0, frameIndex = 0;i<4;++i) {
if(i != currFrame) {
if(bayerParams.pixelShiftLmmse) {
lmmse_interpolate_omp(winw, winh, *(rawDataFrames[i]), redTmp[frameIndex], greenTmp[frameIndex], blueTmp[frameIndex], bayerParams.lmmse_iterations);
@ -487,12 +510,12 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
const bool checkNonGreenCross2 = bayerParams.pixelShiftNonGreenCross2;
const float threshold = bayerParams.pixelShiftSum + 9.f;
const bool experimental0 = bayerParams.pixelShiftExp0;
const bool automatic = bayerParams.pixelShiftMotionCorrectionMethod == RAWParams::BayerSensor::Automatic;
#else
constexpr float threshold = 3.f + 9.f;
#endif
const bool holeFill = bayerParams.pixelShiftHoleFill;
const bool equalBrightness = bayerParams.pixelShiftEqualBright;
const bool equalChannel = bayerParams.pixelShiftEqualBrightChannel;
const bool smoothTransitions = blurMap && bayerParams.pixelShiftSmoothFactor > 0. && !showOnlyMask;
const float smoothFactor = 1.0 - bayerParams.pixelShiftSmoothFactor;
@ -741,24 +764,38 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
// calculate average green brightness for each frame
float greenBrightness[4] = {1.f, 1.f, 1.f, 1.f};
float redBrightness[4] = {1.f, 1.f, 1.f, 1.f};
float blueBrightness[4] = {1.f, 1.f, 1.f, 1.f};
if(equalBrightness) {
LUT<uint32_t> *histo[4];
LUT<uint32_t> *histogreen[4];
LUT<uint32_t> *histored[4];
LUT<uint32_t> *histoblue[4];
for(int i = 0; i < 4; ++i) {
histo[i] = new LUT<uint32_t>(65536);
histo[i]->clear();
histogreen[i] = new LUT<uint32_t>(65536);
histogreen[i]->clear();
histored[i] = new LUT<uint32_t>(65536);
histored[i]->clear();
histoblue[i] = new LUT<uint32_t>(65536);
histoblue[i]->clear();
}
#ifdef _OPENMP
#pragma omp parallel
#endif
{
LUT<uint32_t> *histoThr[4];
LUT<uint32_t> *histogreenThr[4];
LUT<uint32_t> *historedThr[4];
LUT<uint32_t> *histoblueThr[4];
for(int i = 0; i < 4; ++i) {
histoThr[i] = new LUT<uint32_t>(65536);
histoThr[i]->clear();
histogreenThr[i] = new LUT<uint32_t>(65536);
histogreenThr[i]->clear();
historedThr[i] = new LUT<uint32_t>(65536);
historedThr[i]->clear();
histoblueThr[i] = new LUT<uint32_t>(65536);
histoblueThr[i]->clear();
}
#ifdef _OPENMP
@ -766,44 +803,51 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
#endif
for(int i = winy + 1; i < winh - 1; ++i) {
int j = winx + 1;
int c = FC(i, j);
bool bluerow = (c + FC(i, j + 1)) == 3;
for(int j = winx + 1, offset = FC(i, j) & 1; j < winw - 1; ++j, offset ^= 1) {
(*histoThr[1 - offset])[(*rawDataFrames[1 - offset])[i - offset + 1][j]]++;
(*histoThr[3 - offset])[(*rawDataFrames[3 - offset])[i + offset][j + 1]]++;
(*histogreenThr[1 - offset])[(*rawDataFrames[1 - offset])[i - offset + 1][j]]++;
(*histogreenThr[3 - offset])[(*rawDataFrames[3 - offset])[i + offset][j + 1]]++;
if(bluerow) {
(*historedThr[2 - offset])[(*rawDataFrames[2 - offset])[i + 1][j - offset + 1]]++;
(*histoblueThr[(offset << 1) + offset])[(*rawDataFrames[(offset << 1) + offset])[i][j + offset]]++;
} else {
(*historedThr[(offset << 1) + offset])[(*rawDataFrames[(offset << 1) + offset])[i][j + offset]]++;
(*histoblueThr[2 - offset])[(*rawDataFrames[2 - offset])[i + 1][j - offset + 1]]++;
}
}
}
#pragma omp critical
{
for(int i = 0; i < 4; ++i) {
(*histo[i]) += (*histoThr[i]);
delete histoThr[i];
(*histogreen[i]) += (*histogreenThr[i]);
delete histogreenThr[i];
(*histored[i]) += (*historedThr[i]);
delete historedThr[i];
(*histoblue[i]) += (*histoblueThr[i]);
delete histoblueThr[i];
}
}
}
float medians[4];
calcFrameBrightnessFactor(frame, (winh - 2) * (winw - 2) / 4, histored, redBrightness);
calcFrameBrightnessFactor(frame, (winh - 2) * (winw - 2) / 4, histoblue, blueBrightness);
calcFrameBrightnessFactor(frame, (winh - 2) * (winw - 2) / 2, histogreen, greenBrightness);
for(int i = 0; i < 4; ++i) {
//find median of histogram
uint32_t median = 0, count = 0;
uint32_t datalen = (winh - 2) * (winw - 2) / 2;
while (count < datalen / 2) {
count += (*histo[i])[median];
++median;
}
const float weight = (count - datalen / 2.f) / (*histo[i])[median - 1];
medians[i] = intp(weight, (float)(median - 2), (float)(median - 1));
delete histo[i];
}
for(int i = 0; i < 4; ++i) {
greenBrightness[i] = medians[frame] / medians[i];
delete histored[i];
delete histoblue[i];
delete histogreen[i];
}
#ifdef PIXELSHIFTDEV
std::cout << "brightness factors by median : " << greenBrightness[0] << " " << greenBrightness[1] << " " << greenBrightness[2] << " " << greenBrightness[3] << std::endl;
std::cout << "blue brightness factors by median : " << blueBrightness[0] << " " << blueBrightness[1] << " " << blueBrightness[2] << " " << blueBrightness[3] << std::endl;
std::cout << "red brightness factors by median : " << redBrightness[0] << " " << redBrightness[1] << " " << redBrightness[2] << " " << redBrightness[3] << std::endl;
std::cout << "green brightness factors by median : " << greenBrightness[0] << " " << greenBrightness[1] << " " << greenBrightness[2] << " " << greenBrightness[3] << std::endl;
#endif
}
@ -814,6 +858,12 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
array2D<float> psG2(winw + 32, winh);
array2D<float> psBlue(winw + 32, winh);
if(!equalChannel) {
for(int i = 0; i < 4; ++i ) {
redBrightness[i] = blueBrightness[i] = greenBrightness[i];
}
}
// fill channels psRed, psG1, psG2 and psBlue
#ifdef _OPENMP
#pragma omp parallel for schedule(dynamic,16)
@ -824,6 +874,10 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
float *greenDest2 = psG2[i];
float *nonGreenDest0 = psRed[i];
float *nonGreenDest1 = psBlue[i];
float ngbright[2][4] = {{redBrightness[0],redBrightness[1],redBrightness[2],redBrightness[3]},
{blueBrightness[0],blueBrightness[1],blueBrightness[2],blueBrightness[3]}
};
int ng = 0;
int j = winx + 1;
int c = FC(i, j);
@ -831,6 +885,7 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
// row with blue pixels => swap destination pointers for non green pixels
std::swap(nonGreenDest0, nonGreenDest1);
std::swap(greenDest1, greenDest2);
ng ^= 1;
}
// offset to keep the code short. It changes its value between 0 and 1 for each iteration of the loop
@ -840,8 +895,8 @@ void RawImageSource::pixelshift(int winx, int winy, int winw, int winh, const RA
// store the values from the 4 frames into 4 different temporary planes
greenDest1[j] = (*rawDataFrames[1 - offset])[i - offset + 1][j] * greenBrightness[1 - offset];
greenDest2[j] = (*rawDataFrames[3 - offset])[i + offset][j + 1] * greenBrightness[3 - offset];
nonGreenDest0[j] = (*rawDataFrames[(offset << 1) + offset])[i][j + offset] * greenBrightness[(offset << 1) + offset];
nonGreenDest1[j] = (*rawDataFrames[2 - offset])[i + 1][j - offset + 1] * greenBrightness[2 - offset];
nonGreenDest0[j] = (*rawDataFrames[(offset << 1) + offset])[i][j + offset] * ngbright[ng][(offset << 1) + offset];
nonGreenDest1[j] = (*rawDataFrames[2 - offset])[i + 1][j - offset + 1] * ngbright[ng^1][2 - offset];
offset ^= 1; // 0 => 1 or 1 => 0
}
}

View File

@ -501,6 +501,7 @@ enum ProcEvent {
EvPixelShiftSmooth = 471,
EvPixelShiftLmmse = 472,
EvPixelShiftEqualBright = 473,
EvPixelShiftEqualBrightChannel = 474,
NUMOFEVENTS
};

View File

@ -901,6 +901,7 @@ void RAWParams::BayerSensor::setPixelShiftDefaults()
pixelShiftExp0 = false;
pixelShiftLmmse = false;
pixelShiftEqualBright = false;
pixelShiftEqualBrightChannel = false;
pixelShiftNonGreenCross = true;
pixelShiftNonGreenCross2 = false;
pixelShiftNonGreenAmaze = false;
@ -3507,6 +3508,10 @@ int ProcParams::save (const Glib::ustring &fname, const Glib::ustring &fname2, b
keyFile.set_boolean ("RAW Bayer", "pixelShiftEqualBright", raw.bayersensor.pixelShiftEqualBright );
}
if (!pedited || pedited->raw.bayersensor.pixelShiftEqualBrightChannel) {
keyFile.set_boolean ("RAW Bayer", "pixelShiftEqualBrightChannel", raw.bayersensor.pixelShiftEqualBrightChannel );
}
if (!pedited || pedited->raw.bayersensor.pixelShiftNonGreenCross) {
keyFile.set_boolean ("RAW Bayer", "pixelShiftNonGreenCross", raw.bayersensor.pixelShiftNonGreenCross );
}
@ -7791,6 +7796,14 @@ int ProcParams::load (const Glib::ustring &fname, ParamsEdited* pedited)
}
}
if (keyFile.has_key ("RAW Bayer", "pixelShiftEqualBrightChannel")) {
raw.bayersensor.pixelShiftEqualBrightChannel = keyFile.get_boolean("RAW Bayer", "pixelShiftEqualBrightChannel");
if (pedited) {
pedited->raw.bayersensor.pixelShiftEqualBrightChannel = true;
}
}
if (keyFile.has_key ("RAW Bayer", "pixelShiftNonGreenCross")) {
raw.bayersensor.pixelShiftNonGreenCross = keyFile.get_boolean("RAW Bayer", "pixelShiftNonGreenCross");
@ -8278,6 +8291,7 @@ bool ProcParams::operator== (const ProcParams& other)
&& raw.bayersensor.pixelShiftExp0 == other.raw.bayersensor.pixelShiftExp0
&& raw.bayersensor.pixelShiftLmmse == other.raw.bayersensor.pixelShiftLmmse
&& raw.bayersensor.pixelShiftEqualBright == other.raw.bayersensor.pixelShiftEqualBright
&& raw.bayersensor.pixelShiftEqualBrightChannel == other.raw.bayersensor.pixelShiftEqualBrightChannel
&& raw.bayersensor.pixelShiftNonGreenCross == other.raw.bayersensor.pixelShiftNonGreenCross
&& raw.bayersensor.pixelShiftNonGreenCross2 == other.raw.bayersensor.pixelShiftNonGreenCross2
&& raw.bayersensor.pixelShiftNonGreenAmaze == other.raw.bayersensor.pixelShiftNonGreenAmaze

View File

@ -1235,6 +1235,7 @@ public:
bool pixelShiftExp0;
bool pixelShiftLmmse;
bool pixelShiftEqualBright;
bool pixelShiftEqualBrightChannel;
bool pixelShiftNonGreenCross;
bool pixelShiftNonGreenCross2;
bool pixelShiftNonGreenAmaze;

View File

@ -500,7 +500,8 @@ int refreshmap[rtengine::NUMOFEVENTS] = {
DEMOSAIC, // EvPixelShiftMotionMethod
DEMOSAIC, // EvPixelShiftSmooth
DEMOSAIC, // EvPixelShiftLmmse
DEMOSAIC // EvPixelShiftEqualBright
DEMOSAIC, // EvPixelShiftEqualBright
DEMOSAIC // EvPixelShiftEqualBrightChannel
};

View File

@ -101,6 +101,11 @@ BayerProcess::BayerProcess () : FoldableToolPanel(this, "bayerprocess", M("TP_RA
pixelShiftEqualBright->set_tooltip_text (M("TP_RAW_PIXELSHIFTEQUALBRIGHT_TOOLTIP"));
pixelShiftFrame->pack_start(*pixelShiftEqualBright);
pixelShiftEqualBrightChannel = Gtk::manage (new CheckBox(M("TP_RAW_PIXELSHIFTEQUALBRIGHTCHANNEL"), multiImage));
pixelShiftEqualBrightChannel->setCheckBoxListener (this);
pixelShiftEqualBrightChannel->set_tooltip_text (M("TP_RAW_PIXELSHIFTEQUALBRIGHTCHANNEL_TOOLTIP"));
pixelShiftFrame->pack_start(*pixelShiftEqualBrightChannel);
Gtk::HBox* hb3 = Gtk::manage (new Gtk::HBox ());
hb3->pack_start (*Gtk::manage (new Gtk::Label ( M("TP_RAW_PIXELSHIFTMOTIONMETHOD") + ": ")), Gtk::PACK_SHRINK, 4);
pixelShiftMotionMethod = Gtk::manage (new MyComboBoxText ());
@ -372,6 +377,8 @@ void BayerProcess::read(const rtengine::procparams::ProcParams* pp, const Params
pixelShiftSmooth->setValue (pp->raw.bayersensor.pixelShiftSmoothFactor);
pixelShiftLmmse->setValue (pp->raw.bayersensor.pixelShiftLmmse);
pixelShiftEqualBright->setValue (pp->raw.bayersensor.pixelShiftEqualBright);
pixelShiftEqualBrightChannel->set_sensitive (pp->raw.bayersensor.pixelShiftEqualBright);
pixelShiftEqualBrightChannel->setValue (pp->raw.bayersensor.pixelShiftEqualBrightChannel);
pixelShiftNonGreenCross->setValue (pp->raw.bayersensor.pixelShiftNonGreenCross);
ccSteps->setValue (pp->raw.bayersensor.ccSteps);
lmmseIterations->setValue (pp->raw.bayersensor.lmmse_iterations);
@ -421,6 +428,7 @@ void BayerProcess::read(const rtengine::procparams::ProcParams* pp, const Params
pixelShiftSmooth->setEditedState ( pedited->raw.bayersensor.pixelShiftSmooth ? Edited : UnEdited);
pixelShiftLmmse->setEdited (pedited->raw.bayersensor.pixelShiftLmmse);
pixelShiftEqualBright->setEdited (pedited->raw.bayersensor.pixelShiftEqualBright);
pixelShiftEqualBrightChannel->setEdited (pedited->raw.bayersensor.pixelShiftEqualBrightChannel);
pixelShiftNonGreenCross->setEdited (pedited->raw.bayersensor.pixelShiftNonGreenCross);
lmmseIterations->setEditedState ( pedited->raw.bayersensor.lmmseIterations ? Edited : UnEdited);
pixelShiftEperIso->setEditedState ( pedited->raw.bayersensor.pixelShiftEperIso ? Edited : UnEdited);
@ -524,6 +532,7 @@ void BayerProcess::write( rtengine::procparams::ProcParams* pp, ParamsEdited* pe
pp->raw.bayersensor.pixelShiftSmoothFactor = pixelShiftSmooth->getValue();
pp->raw.bayersensor.pixelShiftLmmse = pixelShiftLmmse->getLastActive ();
pp->raw.bayersensor.pixelShiftEqualBright = pixelShiftEqualBright->getLastActive ();
pp->raw.bayersensor.pixelShiftEqualBrightChannel = pixelShiftEqualBrightChannel->getLastActive ();
pp->raw.bayersensor.pixelShiftNonGreenCross = pixelShiftNonGreenCross->getLastActive ();
#ifdef PIXELSHIFTDEV
pp->raw.bayersensor.pixelShiftStddevFactorGreen = pixelShiftStddevFactorGreen->getValue();
@ -575,6 +584,7 @@ void BayerProcess::write( rtengine::procparams::ProcParams* pp, ParamsEdited* pe
pedited->raw.bayersensor.pixelShiftSmooth = pixelShiftSmooth->getEditedState();
pedited->raw.bayersensor.pixelShiftLmmse = !pixelShiftLmmse->get_inconsistent();
pedited->raw.bayersensor.pixelShiftEqualBright = !pixelShiftEqualBright->get_inconsistent();
pedited->raw.bayersensor.pixelShiftEqualBrightChannel = !pixelShiftEqualBrightChannel->get_inconsistent();
pedited->raw.bayersensor.pixelShiftNonGreenCross = !pixelShiftNonGreenCross->get_inconsistent();
#ifdef PIXELSHIFTDEV
pedited->raw.bayersensor.pixelShiftStddevFactorGreen = pixelShiftStddevFactorGreen->getEditedState ();
@ -839,9 +849,16 @@ void BayerProcess::checkBoxToggled (CheckBox* c, CheckValue newval)
listener->panelChanged (EvPixelShiftLmmse, pixelShiftLmmse->getValueAsStr ());
}
} else if (c == pixelShiftEqualBright) {
if (!batchMode) {
pixelShiftEqualBrightChannel->set_sensitive(newval != CheckValue::off);
}
if (listener) {
listener->panelChanged (EvPixelShiftEqualBright, pixelShiftEqualBright->getValueAsStr ());
}
} else if (c == pixelShiftEqualBrightChannel) {
if (listener) {
listener->panelChanged (EvPixelShiftEqualBrightChannel, pixelShiftEqualBrightChannel->getValueAsStr ());
}
} else if (c == pixelShiftNonGreenCross) {
if (listener) {
listener->panelChanged (EvPixelShiftNonGreenCross, pixelShiftNonGreenCross->getValueAsStr ());

View File

@ -51,6 +51,7 @@ protected:
CheckBox* pixelShiftMedian;
CheckBox* pixelShiftLmmse;
CheckBox* pixelShiftEqualBright;
CheckBox* pixelShiftEqualBrightChannel;
Adjuster* pixelShiftSmooth;
Adjuster* pixelShiftEperIso;
Adjuster* pixelShiftSigma;

View File

@ -397,6 +397,7 @@ void ParamsEdited::set (bool v)
raw.bayersensor.pixelShiftExp0 = v;
raw.bayersensor.pixelShiftLmmse = v;
raw.bayersensor.pixelShiftEqualBright = v;
raw.bayersensor.pixelShiftEqualBrightChannel = v;
raw.bayersensor.pixelShiftNonGreenCross = v;
raw.bayersensor.pixelShiftNonGreenCross2 = v;
raw.bayersensor.pixelShiftNonGreenAmaze = v;
@ -923,6 +924,7 @@ void ParamsEdited::initFrom (const std::vector<rtengine::procparams::ProcParams>
raw.bayersensor.pixelShiftExp0 = raw.bayersensor.pixelShiftExp0 && p.raw.bayersensor.pixelShiftExp0 == other.raw.bayersensor.pixelShiftExp0;
raw.bayersensor.pixelShiftLmmse = raw.bayersensor.pixelShiftLmmse && p.raw.bayersensor.pixelShiftLmmse == other.raw.bayersensor.pixelShiftLmmse;
raw.bayersensor.pixelShiftEqualBright = raw.bayersensor.pixelShiftEqualBright && p.raw.bayersensor.pixelShiftEqualBright == other.raw.bayersensor.pixelShiftEqualBright;
raw.bayersensor.pixelShiftEqualBrightChannel = raw.bayersensor.pixelShiftEqualBrightChannel && p.raw.bayersensor.pixelShiftEqualBrightChannel == other.raw.bayersensor.pixelShiftEqualBrightChannel;
raw.bayersensor.pixelShiftNonGreenCross = raw.bayersensor.pixelShiftNonGreenCross && p.raw.bayersensor.pixelShiftNonGreenCross == other.raw.bayersensor.pixelShiftNonGreenCross;
raw.bayersensor.pixelShiftNonGreenCross2 = raw.bayersensor.pixelShiftNonGreenCross2 && p.raw.bayersensor.pixelShiftNonGreenCross2 == other.raw.bayersensor.pixelShiftNonGreenCross2;
raw.bayersensor.pixelShiftNonGreenAmaze = raw.bayersensor.pixelShiftNonGreenAmaze && p.raw.bayersensor.pixelShiftNonGreenAmaze == other.raw.bayersensor.pixelShiftNonGreenAmaze;
@ -2446,6 +2448,10 @@ void ParamsEdited::combine (rtengine::procparams::ProcParams& toEdit, const rten
toEdit.raw.bayersensor.pixelShiftEqualBright = mods.raw.bayersensor.pixelShiftEqualBright;
}
if (raw.bayersensor.pixelShiftEqualBrightChannel) {
toEdit.raw.bayersensor.pixelShiftEqualBrightChannel = mods.raw.bayersensor.pixelShiftEqualBrightChannel;
}
if (raw.bayersensor.pixelShiftNonGreenCross) {
toEdit.raw.bayersensor.pixelShiftNonGreenCross = mods.raw.bayersensor.pixelShiftNonGreenCross;
}
@ -2970,7 +2976,7 @@ bool RAWParamsEdited::BayerSensor::isUnchanged() const
return method && imageNum && dcbIterations && dcbEnhance && lmmseIterations/*&& allEnhance*/ && greenEq
&& pixelShiftMotion && pixelShiftMotionCorrection && pixelShiftMotionCorrectionMethod && pixelShiftStddevFactorGreen && pixelShiftStddevFactorRed && pixelShiftStddevFactorBlue && pixelShiftEperIso
&& pixelShiftNreadIso && pixelShiftPrnu && pixelShiftSigma && pixelShiftSum && pixelShiftRedBlueWeight && pixelShiftShowMotion && pixelShiftShowMotionMaskOnly
&& pixelShiftAutomatic && pixelShiftNonGreenHorizontal && pixelShiftNonGreenVertical && pixelShiftHoleFill && pixelShiftMedian && pixelShiftMedian3 && pixelShiftNonGreenCross && pixelShiftNonGreenCross2 && pixelShiftNonGreenAmaze && pixelShiftGreen && pixelShiftBlur && pixelShiftSmooth && pixelShiftExp0 && pixelShiftLmmse && pixelShiftEqualBright
&& pixelShiftAutomatic && pixelShiftNonGreenHorizontal && pixelShiftNonGreenVertical && pixelShiftHoleFill && pixelShiftMedian && pixelShiftMedian3 && pixelShiftNonGreenCross && pixelShiftNonGreenCross2 && pixelShiftNonGreenAmaze && pixelShiftGreen && pixelShiftBlur && pixelShiftSmooth && pixelShiftExp0 && pixelShiftLmmse && pixelShiftEqualBright && pixelShiftEqualBrightChannel
&& linenoise && exBlack0 && exBlack1 && exBlack2 && exBlack3 && exTwoGreen;
}

View File

@ -718,6 +718,7 @@ public:
bool pixelShiftExp0;
bool pixelShiftLmmse;
bool pixelShiftEqualBright;
bool pixelShiftEqualBrightChannel;
bool pixelShiftNonGreenCross;
bool pixelShiftNonGreenCross2;
bool pixelShiftNonGreenAmaze;