diff --git a/rtdata/languages/English (UK) b/rtdata/languages/English (UK) index 37b52708d..bb3deb741 100644 --- a/rtdata/languages/English (UK) +++ b/rtdata/languages/English (UK) @@ -1,4 +1,4 @@ -# +# # This file is part of RawTherapee. # # Copyright (c) 2004-2010 Gabor Horvath @@ -365,6 +365,10 @@ PREFERENCES_DCBENHANCE;Apply DCB enhancment step PREFERENCES_DCBITERATIONS;Number of DCB iterations #Emil's CA autocorrection PREFERENCES_CACORRECTION;Apply CA auto correction +#Emil's hot/dead pixel filter +PREFERENCES_HOTDEADPIXFILT;Apply hot/dead pixel filter +#Emil's line noise filter +PREFERENCES_LINEDENOISE;Line noise filter PREFERENCES_DEFAULTLANG;Default language PREFERENCES_DEFAULTTHEME;Default theme PREFERENCES_DEMOSAICINGALGO;Demosaicing Algorithm diff --git a/rtdata/languages/English (US) b/rtdata/languages/English (US) index 492a1b35c..2c9210fc5 100644 --- a/rtdata/languages/English (US) +++ b/rtdata/languages/English (US) @@ -367,6 +367,10 @@ PREFERENCES_DCBENHANCE;Apply DCB enhancement step PREFERENCES_DCBITERATIONS;Number of DCB iterations #Emil's CA autocorrection PREFERENCES_CACORRECTION;Apply CA auto correction +#Emil's hot/dead pixel filter +PREFERENCES_HOTDEADPIXFILT;Apply hot/dead pixel filter +#Emil's line noise filter +PREFERENCES_LINEDENOISE;Line noise filter PREFERENCES_DEFAULTLANG;Default language PREFERENCES_DEFAULTTHEME;Default theme PREFERENCES_DEMOSAICINGALGO;Demosaicing Algorithm diff --git a/rtengine/cfa_linedn_RT.cc b/rtengine/cfa_linedn_RT.cc new file mode 100644 index 000000000..151642dc0 --- /dev/null +++ b/rtengine/cfa_linedn_RT.cc @@ -0,0 +1,423 @@ +//////////////////////////////////////////////////////////////// +// +// CFA line denoise by DCT filtering +// +// copyright (c) 2008-2010 Emil Martinec +// +// +// code dated: June 7, 2010 +// +// cfa_linedn_RT.cc is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +//////////////////////////////////////////////////////////////// + + +#define TS 512 // Tile size + +#define CLASS + + +/*#include +#include +#include +#include +#include +#include +#include +#include +#include */ +#include + + +//#include "shrtdct_float.c" + + +#define SQR(x) ((x)*(x)) +//#define MIN(a,b) ((a) < (b) ? (a) : (b)) +//#define MAX(a,b) ((a) > (b) ? (a) : (b)) +//#define LIM(x,min,max) MAX(min,MIN(x,max)) +//#define ULIM(x,y,z) ((y) < (z) ? LIM(x,y,z) : LIM(x,z,y)) +//#define CLIP(x) LIM(x,0,65535) + +// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + + +// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + +void RawImageSource::CLASS cfa_linedn(float noise) +{ + // local variables + int height=H, width=W; + int top, bottom, left, right, row, col; + int rr, cc, rr1, cc1, c, indx, i, j; + int ex, ey; + int verbose=1; + + float eps=1e-10; //tolerance to avoid dividing by zero + + float gauss[5] = {0.20416368871516755, 0.18017382291138087, 0.1238315368057753, 0.0662822452863612, 0.02763055063889883}; + float rolloff[8] = {0, 0.135335, 0.249352, 0.411112, 0.606531, 0.800737, 0.945959, 1}; //gaussian with sigma=3 + float window[8] = {0, .25, .75, 1, 1, .75, .25, 0}; //sine squared + float noisevar, linehvar, linevvar, coeffsq; + + float aarr[8][8], *dctblock[8]; + for (i = 0; i < 8; i++) dctblock[i] = aarr[i]; + + char *buffer; // TS*TS*16 + float (*cfain); // TS*TS*4 + float (*cfablur); // TS*TS*4 + float (*cfadiff); // TS*TS*4 + float (*cfadn); // TS*TS*4 + + double dt; + clock_t t1, t2; + + //clock_t t1_main, t2_main = 0; + + // start + //if (verbose) fprintf (stderr,_("CFA line denoise ...\n")); + //t1 = clock(); + + + // assign working space + buffer = (char *) malloc(16*TS*TS); + //merror(buffer,"cfa_linedn()"); + memset(buffer,0,16*TS*TS); + // rgb array + cfain = (float (*)) buffer; //pointers to rows of array + cfablur = (float (*)) (buffer + 4*TS*TS); + cfadiff = (float (*)) (buffer + 8*TS*TS); + cfadn = (float (*)) (buffer + 12*TS*TS); + + // %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + + + // %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + + if (plistener) { + plistener->setProgressStr ("Line Denoise..."); + plistener->setProgress (0.0); + } + + // %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + + + noisevar=SQR(3*noise*65535); // _noise_ (as a fraction of saturation) is input to the algorithm + + // Main algorithm: Tile loop + for (top=0; top < height-16; top += TS-32) + for (left=0; left < width-16; left += TS-32) { + bottom = MIN( top+TS,height); + right = MIN(left+TS, width); + rr1 = bottom - top; + cc1 = right - left; + // load CFA data; data should be in linear gamma space, before white balance multipliers are applied + for (rr=0; rr < rr1; rr++) + for (row=rr+top, cc=0, indx=rr*TS+cc; cc < cc1; cc++, indx++) { + col = cc+left; + c = FC(rr,cc); + cfain[indx] = ri->data[row][col]; + } + //pad the block to a multiple of 16 on both sides + + if (cc1 < TS) { + indx=cc1 % 16; + for (i=0; i<(16-indx); i++) + for (rr=0; rrlinehvar) { + for (i=1; i<8; i++) { + coeffsq=SQR(dctblock[0][i]); + dctblock[0][i] *= coeffsq/(coeffsq+rolloff[i]*noisevar+eps); + } + } + if (noisevar>linevvar) { + for (i=1; i<8; i++) { + coeffsq=SQR(dctblock[i][0]); + dctblock[i][0] *= coeffsq/(coeffsq+rolloff[i]*noisevar+eps); + } + } + + ddct8x8s(1, dctblock); //inverse DCT + + //multiply by window fn and add to output (cfadn) + for (i=0; i<8; i++) + for (j=0; j<8; j++) { + cfadn[(rr+2*i)*TS+cc+2*j] += window[i]*window[j]*dctblock[i][j]; + } + } + + // %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + + // copy smoothed results back to image matrix + for (rr=16; rr < rr1-16; rr++) + for (row=rr+top, cc=16, indx=rr*TS+cc; cc < cc1-16; cc++, indx++) { + col = cc + left; + ri->data[row][col] = CLIP((int)(cfadn[indx]+ 0.5)); + } + if(plistener) plistener->setProgress(fabs((float)top/height)); + } + + // clean up + free(buffer); + + // done + /*t2 = clock(); + dt = ((double)(t2-t1)) / CLOCKS_PER_SEC; + if (verbose) { + fprintf(stderr,_("elapsed time = %5.3fs\n"),dt); + }*/ + + +} +#undef TS + + +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +/* + Discrete Cosine Transform Code + + Copyright(C) 1997 Takuya OOURA (email: ooura@mmm.t.u-tokyo.ac.jp). + You may use, copy, modify this code for any purpose and + without fee. You may distribute this ORIGINAL package. + */ + + +/* + Short Discrete Cosine Transform + data length :8x8 + method :row-column, radix 4 FFT + functions + ddct8x8s : 8x8 DCT + function prototypes + void ddct8x8s(int isgn, float **a); + */ + + +/* + -------- 8x8 DCT (Discrete Cosine Transform) / Inverse of DCT -------- + [definition] + Normalized 8x8 IDCT + C[k1][k2] = (1/4) * sum_j1=0^7 sum_j2=0^7 + a[j1][j2] * s[j1] * s[j2] * + cos(pi*j1*(k1+1/2)/8) * + cos(pi*j2*(k2+1/2)/8), 0<=k1<8, 0<=k2<8 + (s[0] = 1/sqrt(2), s[j] = 1, j > 0) + Normalized 8x8 DCT + C[k1][k2] = (1/4) * s[k1] * s[k2] * sum_j1=0^7 sum_j2=0^7 + a[j1][j2] * + cos(pi*(j1+1/2)*k1/8) * + cos(pi*(j2+1/2)*k2/8), 0<=k1<8, 0<=k2<8 + (s[0] = 1/sqrt(2), s[j] = 1, j > 0) + [usage] + + ddct8x8s(1, a); + + ddct8x8s(-1, a); + [parameters] + a[0...7][0...7] :input/output data (double **) + output data + a[k1][k2] = C[k1][k2], 0<=k1<8, 0<=k2<8 + */ + + +/* Cn_kR = sqrt(2.0/n) * cos(pi/2*k/n) */ +/* Cn_kI = sqrt(2.0/n) * sin(pi/2*k/n) */ +/* Wn_kR = cos(pi/2*k/n) */ +/* Wn_kI = sin(pi/2*k/n) */ +#define C8_1R 0.49039264020161522456 +#define C8_1I 0.09754516100806413392 +#define C8_2R 0.46193976625564337806 +#define C8_2I 0.19134171618254488586 +#define C8_3R 0.41573480615127261854 +#define C8_3I 0.27778511650980111237 +#define C8_4R 0.35355339059327376220 +#define W8_4R 0.70710678118654752440 + + +void RawImageSource::ddct8x8s(int isgn, float **a) +{ + int j; + float x0r, x0i, x1r, x1i, x2r, x2i, x3r, x3i; + float xr, xi; + + if (isgn < 0) { + for (j = 0; j <= 7; j++) { + x0r = a[0][j] + a[7][j]; + x1r = a[0][j] - a[7][j]; + x0i = a[2][j] + a[5][j]; + x1i = a[2][j] - a[5][j]; + x2r = a[4][j] + a[3][j]; + x3r = a[4][j] - a[3][j]; + x2i = a[6][j] + a[1][j]; + x3i = a[6][j] - a[1][j]; + xr = x0r + x2r; + xi = x0i + x2i; + a[0][j] = C8_4R * (xr + xi); + a[4][j] = C8_4R * (xr - xi); + xr = x0r - x2r; + xi = x0i - x2i; + a[2][j] = C8_2R * xr - C8_2I * xi; + a[6][j] = C8_2R * xi + C8_2I * xr; + xr = W8_4R * (x1i - x3i); + x1i = W8_4R * (x1i + x3i); + x3i = x1i - x3r; + x1i += x3r; + x3r = x1r - xr; + x1r += xr; + a[1][j] = C8_1R * x1r - C8_1I * x1i; + a[7][j] = C8_1R * x1i + C8_1I * x1r; + a[3][j] = C8_3R * x3r - C8_3I * x3i; + a[5][j] = C8_3R * x3i + C8_3I * x3r; + } + for (j = 0; j <= 7; j++) { + x0r = a[j][0] + a[j][7]; + x1r = a[j][0] - a[j][7]; + x0i = a[j][2] + a[j][5]; + x1i = a[j][2] - a[j][5]; + x2r = a[j][4] + a[j][3]; + x3r = a[j][4] - a[j][3]; + x2i = a[j][6] + a[j][1]; + x3i = a[j][6] - a[j][1]; + xr = x0r + x2r; + xi = x0i + x2i; + a[j][0] = C8_4R * (xr + xi); + a[j][4] = C8_4R * (xr - xi); + xr = x0r - x2r; + xi = x0i - x2i; + a[j][2] = C8_2R * xr - C8_2I * xi; + a[j][6] = C8_2R * xi + C8_2I * xr; + xr = W8_4R * (x1i - x3i); + x1i = W8_4R * (x1i + x3i); + x3i = x1i - x3r; + x1i += x3r; + x3r = x1r - xr; + x1r += xr; + a[j][1] = C8_1R * x1r - C8_1I * x1i; + a[j][7] = C8_1R * x1i + C8_1I * x1r; + a[j][3] = C8_3R * x3r - C8_3I * x3i; + a[j][5] = C8_3R * x3i + C8_3I * x3r; + } + } else { + for (j = 0; j <= 7; j++) { + x1r = C8_1R * a[1][j] + C8_1I * a[7][j]; + x1i = C8_1R * a[7][j] - C8_1I * a[1][j]; + x3r = C8_3R * a[3][j] + C8_3I * a[5][j]; + x3i = C8_3R * a[5][j] - C8_3I * a[3][j]; + xr = x1r - x3r; + xi = x1i + x3i; + x1r += x3r; + x3i -= x1i; + x1i = W8_4R * (xr + xi); + x3r = W8_4R * (xr - xi); + xr = C8_2R * a[2][j] + C8_2I * a[6][j]; + xi = C8_2R * a[6][j] - C8_2I * a[2][j]; + x0r = C8_4R * (a[0][j] + a[4][j]); + x0i = C8_4R * (a[0][j] - a[4][j]); + x2r = x0r - xr; + x2i = x0i - xi; + x0r += xr; + x0i += xi; + a[0][j] = x0r + x1r; + a[7][j] = x0r - x1r; + a[2][j] = x0i + x1i; + a[5][j] = x0i - x1i; + a[4][j] = x2r - x3i; + a[3][j] = x2r + x3i; + a[6][j] = x2i - x3r; + a[1][j] = x2i + x3r; + } + for (j = 0; j <= 7; j++) { + x1r = C8_1R * a[j][1] + C8_1I * a[j][7]; + x1i = C8_1R * a[j][7] - C8_1I * a[j][1]; + x3r = C8_3R * a[j][3] + C8_3I * a[j][5]; + x3i = C8_3R * a[j][5] - C8_3I * a[j][3]; + xr = x1r - x3r; + xi = x1i + x3i; + x1r += x3r; + x3i -= x1i; + x1i = W8_4R * (xr + xi); + x3r = W8_4R * (xr - xi); + xr = C8_2R * a[j][2] + C8_2I * a[j][6]; + xi = C8_2R * a[j][6] - C8_2I * a[j][2]; + x0r = C8_4R * (a[j][0] + a[j][4]); + x0i = C8_4R * (a[j][0] - a[j][4]); + x2r = x0r - xr; + x2i = x0i - xi; + x0r += xr; + x0i += xi; + a[j][0] = x0r + x1r; + a[j][7] = x0r - x1r; + a[j][2] = x0i + x1i; + a[j][5] = x0i - x1i; + a[j][4] = x2r - x3i; + a[j][3] = x2r + x3i; + a[j][6] = x2i - x3r; + a[j][1] = x2i + x3r; + } + } +} + diff --git a/rtengine/rawimagesource.cc b/rtengine/rawimagesource.cc index 8ef9b8a70..216ec0a1e 100644 --- a/rtengine/rawimagesource.cc +++ b/rtengine/rawimagesource.cc @@ -324,6 +324,59 @@ void RawImageSource::getImage (ColorTemp ctemp, int tran, Image16* image, Previe isrcMutex.unlock (); } + + +void RawImageSource::cfa_clean(float thresh) //Emil's hot/dead pixel removal -- only filters egregiously impulsive pixels + { + // local variables + int rr, cc; + int gin, g[8]; + + float eps=1e-10;//tolerance to avoid dividing by zero + float p[8]; + float pixave, pixratio; + + // %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + //The cleaning algorithm starts here + + for (rr=4; rr < H-4; rr++) + for (cc=4; cc < W-4; cc++) { + + //pixel neighbor average + gin=ri->data[rr][cc]; + g[0]=ri->data[rr-2][cc-2]; + g[1]=ri->data[rr-2][cc]; + g[2]=ri->data[rr-2][cc+2]; + g[3]=ri->data[rr][cc-2]; + g[4]=ri->data[rr][cc+2]; + g[5]=ri->data[rr+2][cc-2]; + g[6]=ri->data[rr+2][cc]; + g[7]=ri->data[rr+2][cc+2]; + + pixave=(float)(g[0]+g[1]+g[2]+g[3]+g[4]+g[5]+g[6]+g[7])/8; + pixratio=MIN(gin,pixave)/(eps+MAX(gin,pixave)); + + if (pixratio > thresh) continue; + + p[0]=1/(eps+fabs(g[0]-gin)+fabs(g[0]-ri->data[rr-4][cc-4])+fabs(ri->data[rr-1][cc-1]-ri->data[rr-3][cc-3])); + p[1]=1/(eps+fabs(g[1]-gin)+fabs(g[1]-ri->data[rr-4][cc])+fabs(ri->data[rr-1][cc]-ri->data[rr-3][cc])); + p[2]=1/(eps+fabs(g[2]-gin)+fabs(g[2]-ri->data[rr-4][cc+4])+fabs(ri->data[rr-1][cc+1]-ri->data[rr-3][cc+3])); + p[3]=1/(eps+fabs(g[3]-gin)+fabs(g[3]-ri->data[rr][cc-4])+fabs(ri->data[rr][cc-1]-ri->data[rr][cc-3])); + p[4]=1/(eps+fabs(g[4]-gin)+fabs(g[4]-ri->data[rr][cc+4])+fabs(ri->data[rr][cc+1]-ri->data[rr][cc+3])); + p[5]=1/(eps+fabs(g[5]-gin)+fabs(g[5]-ri->data[rr+4][cc-4])+fabs(ri->data[rr+1][cc-1]-ri->data[rr+3][cc-3])); + p[6]=1/(eps+fabs(g[6]-gin)+fabs(g[6]-ri->data[rr+4][cc])+fabs(ri->data[rr+1][cc]-ri->data[rr+3][cc])); + p[7]=1/(eps+fabs(g[7]-gin)+fabs(g[7]-ri->data[rr+4][cc+4])+fabs(ri->data[rr+1][cc+1]-ri->data[rr+3][cc+3])); + + ri->data[rr][cc] = (int)((g[0]*p[0]+g[1]*p[1]+g[2]*p[2]+g[3]*p[3]+g[4]*p[4]+ \ + g[5]*p[5]+g[6]*p[6]+g[7]*p[7])/(p[0]+p[1]+p[2]+p[3]+p[4]+p[5]+p[6]+p[7])); + + }//now impulsive values have been corrected + + + // %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + + } + void RawImageSource::rotateLine (unsigned short* line, unsigned short** channel, int tran, int i, int w, int h) { @@ -773,6 +826,29 @@ int RawImageSource::load (Glib::ustring fname) { */ } +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +//Emil's CFA hot/dead pixel filter + + if (settings->hotdeadpix_filt) { + if (plistener) { + plistener->setProgressStr ("Hot/Dead Pixel Filter..."); + plistener->setProgress (0.0); + } + + cfa_clean(0.1); + } + +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +//Emil's line noise filter + + if (settings->linenoise) { + if (plistener) { + plistener->setProgressStr ("Line Denoise..."); + plistener->setProgress (0.0); + } + + cfa_linedn(0.00002*(settings->linenoise)); + } //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% //Emil's CA auto correction @@ -3145,6 +3221,7 @@ void RawImageSource::dcb_demosaic(int iterations, int dcb_enhance) //Emil's code for AMaZE #include "amaze_interpolate_RT.cc"//AMaZE demosaic #include "CA_correct_RT.cc"//Emil's CA auto correction +#include "cfa_linedn_RT.cc"//Emil's CA auto correction //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% diff --git a/rtengine/rawimagesource.h b/rtengine/rawimagesource.h index bab0bafd4..e6ede29bd 100644 --- a/rtengine/rawimagesource.h +++ b/rtengine/rawimagesource.h @@ -138,6 +138,11 @@ class RawImageSource : public ImageSource { int LinEqSolve (int c, int dir, int nDim, float* pfMatr, float* pfVect, float* pfSolution);//Emil's CA auto correction void CA_correct_RT (); + void cfa_clean (float thresh);//Emil's hot/dead pixel filter + void ddct8x8s(int isgn, float **a); + + void cfa_linedn (float linenoiselevel);//Emil's line denoise + void eahd_demosaic (); void hphd_demosaic (); void vng4_demosaic (); diff --git a/rtengine/settings.h b/rtengine/settings.h index cd2dffa07..522eb8352 100644 --- a/rtengine/settings.h +++ b/rtengine/settings.h @@ -33,7 +33,9 @@ namespace rtengine { bool verbose; int dcb_iterations; // number of dcb iterations bool dcb_enhance; // whether to do image refinment - bool ca_autocorrect; // Emil's auto CA correction + bool ca_autocorrect; // Emil's CA auto correction + bool hotdeadpix_filt; // Emil's hot/dead pixel filter + int linenoise; //Emil's line denoise /** Creates a new instance of Settings. * @return a pointer to the new Settings instance. */ diff --git a/rtgui/options.cc b/rtgui/options.cc index c336bfb03..fccff63fb 100644 --- a/rtgui/options.cc +++ b/rtgui/options.cc @@ -121,6 +121,10 @@ void Options::setDefaults () { rtSettings.dualThreadEnabled = true; rtSettings.demosaicMethod = "amaze";//Emil's code for AMaZE rtSettings.ca_autocorrect = false;//Emil's CA correction + rtSettings.hotdeadpix_filt = true;//Emil's hot/dead pixel filter + + rtSettings.linenoise = 0;//Emil's line denoise + rtSettings.colorCorrectionSteps = 0; rtSettings.dcb_iterations = 2; rtSettings.dcb_enhance = true; @@ -262,6 +266,9 @@ if (keyFile.has_group ("Algorithms")) { if (keyFile.has_key ("Algorithms", "ColorCorrection")) rtSettings.colorCorrectionSteps = keyFile.get_integer ("Algorithms", "ColorCorrection"); if(keyFile.has_key("Algorithms", "DCBIterations")) rtSettings.dcb_iterations = keyFile.get_integer("Algorithms", "DCBIterations"); if(keyFile.has_key("Algorithms", "DCBEnhance")) rtSettings.dcb_enhance = keyFile.get_boolean("Algorithms", "DCBEnhance"); + if(keyFile.has_key("Algorithms", "CACorrect")) rtSettings.ca_autocorrect = keyFile.get_boolean("Algorithms", "CACorrect");//Emil's CA autocorrect + if(keyFile.has_key("Algorithms", "HotDeadPixFilt")) rtSettings.hotdeadpix_filt = keyFile.get_boolean("Algorithms", "HotDeadPixFilt");//Emil's hot/dead pixel filter + if(keyFile.has_key("Algorithms", "LineDenoise")) rtSettings.linenoise = keyFile.get_integer("Algorithms", "LineDenoise");//Emil's line denoise } if (keyFile.has_group ("Crop Settings")) { @@ -386,7 +393,9 @@ int Options::saveToFile (Glib::ustring fname) { keyFile.set_integer ("Algorithms", "DCBIterations", rtSettings.dcb_iterations); keyFile.set_boolean ("Algorithms", "DCBEnhance", rtSettings.dcb_enhance); keyFile.set_boolean ("Algorithms", "CACorrect", rtSettings.ca_autocorrect);//Emil's CA correction - + keyFile.set_boolean ("Algorithms", "HotDeadPixFilt", rtSettings.hotdeadpix_filt);//Emil's hot/dead pixel filter + keyFile.set_integer ("Algorithms", "LineDenoise", rtSettings.linenoise);//Emil's line denoise + keyFile.set_integer ("Crop Settings", "DPI", cropDPI); keyFile.set_string ("Color Management", "ICCDirectory", rtSettings.iccDirectory); @@ -422,11 +431,7 @@ void Options::load () { g_mkdir_with_parents (profdir.c_str(), 511); options.saveToFile (rtdir + "/options"); } -#ifdef _WIN32 cacheBaseDir = rtdir + "/cache"; -#else - cacheBaseDir = Glib::ustring(g_get_user_cache_dir()) + "/RawTherapee"; -#endif } Glib::ustring fname = argv0+"/languages/"; diff --git a/rtgui/preferences.cc b/rtgui/preferences.cc index 1a3ed53b0..2da24dfcf 100644 --- a/rtgui/preferences.cc +++ b/rtgui/preferences.cc @@ -288,12 +288,28 @@ Gtk::Widget* Preferences::getProcParamsPanel () { dcbEnhance = Gtk::manage(new Gtk::CheckButton((M("PREFERENCES_DCBENHANCE")))); caAutoCorrect = Gtk::manage(new Gtk::CheckButton((M("PREFERENCES_CACORRECTION"))));//Emil's CA correction - + HotDeadPixFilt = Gtk::manage(new Gtk::CheckButton((M("PREFERENCES_HOTDEADPIXFILT"))));//Emil's hot/dead pixel filter + + //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + //Emil's line denoise + LineDenoiseLabel = Gtk::manage(new Gtk::Label(M("PREFERENCES_LINEDENOISE")+":")); + LineDenoise = Gtk::manage(new Gtk::SpinButton ()); + LineDenoise->set_digits(0); + LineDenoise->set_increments(1, 10); + LineDenoise->set_range(0, 1000); + Gtk::HBox* hb14 = Gtk::manage(new Gtk::HBox()); + hb14->pack_start (*LineDenoiseLabel, Gtk::PACK_SHRINK, 4); + hb14->pack_start (*LineDenoise); + //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + fdb->pack_start (*hb11, Gtk::PACK_SHRINK, 4); fdb->pack_start (*hb12, Gtk::PACK_SHRINK, 4); fdb->pack_start (*hb13, Gtk::PACK_SHRINK, 4); fdb->pack_start (*dcbEnhance, Gtk::PACK_SHRINK, 4); fdb->pack_start (*caAutoCorrect, Gtk::PACK_SHRINK, 4);//Emil's CA correction + fdb->pack_start (*HotDeadPixFilt, Gtk::PACK_SHRINK, 4);//Emil's hot/dead pixel filter + fdb->pack_start (*hb14, Gtk::PACK_SHRINK, 4);//Emil's line denoise + mvbpp->pack_start (*fdem, Gtk::PACK_SHRINK, 4); mvbpp->set_border_width (4); // drlab->set_size_request (drimg->get_width(), -1); @@ -722,6 +738,9 @@ void Preferences::storePreferences () { moptions.rtSettings.dcb_iterations=(int)dcbIterations->get_value(); moptions.rtSettings.dcb_enhance=dcbEnhance->get_active(); moptions.rtSettings.ca_autocorrect=caAutoCorrect->get_active();//Emil's CA correction + moptions.rtSettings.hotdeadpix_filt=HotDeadPixFilt->get_active();//Emil's hot/dead pixel filter + moptions.rtSettings.linenoise=(int)LineDenoise->get_value();//Emil's line denoise + if (sdcurrent->get_active ()) moptions.startupDir = STARTUPDIR_CURRENT; @@ -821,6 +840,10 @@ void Preferences::fillPreferences () { dcbIterations->set_sensitive(moptions.rtSettings.demosaicMethod=="dcb"); dcbIterationsLabel->set_sensitive(moptions.rtSettings.demosaicMethod=="dcb"); caAutoCorrect->set_active(moptions.rtSettings.ca_autocorrect);//Emil's CA Auto Correction + HotDeadPixFilt->set_active(moptions.rtSettings.hotdeadpix_filt);//Emil's hot/dead pixel filter + LineDenoise->set_value(moptions.rtSettings.linenoise);//Emil's line denoise + + if (moptions.startupDir==STARTUPDIR_CURRENT) sdcurrent->set_active (); diff --git a/rtgui/preferences.h b/rtgui/preferences.h index b721cb01e..0335ff914 100644 --- a/rtgui/preferences.h +++ b/rtgui/preferences.h @@ -76,6 +76,10 @@ class Preferences : public Gtk::Dialog { Gtk::SpinButton* dcbIterations; Gtk::CheckButton* dcbEnhance; Gtk::CheckButton* caAutoCorrect;//Emil's CA correction + Gtk::CheckButton* HotDeadPixFilt;//Emil's hot/dead pixel filter + Gtk::Label* LineDenoiseLabel;//Emil's line denoise + Gtk::SpinButton* LineDenoise; + Gtk::FileChooserButton* iccDir; Gtk::FileChooserButton* monProfile;