X-Git-Url: http://git.cinelerra-gg.org/git/?p=goodguy%2Fhistory.git;a=blobdiff_plain;f=cinelerra-5.1%2Fplugins%2FC41%2Fc41.C;h=b7160b75c79cdd233c25a7c3c2d3956a8e405844;hp=6a3829354c49b3930bf846d0d542784f8cd3e9a4;hb=7b05ad287956f8bd00836d9b5fb39f899a5fb641;hpb=e9a3c57c8d3bb4d79e76a4c3942f86a66d3c267e;ds=sidebyside diff --git a/cinelerra-5.1/plugins/C41/c41.C b/cinelerra-5.1/plugins/C41/c41.C index 6a382935..b7160b75 100644 --- a/cinelerra-5.1/plugins/C41/c41.C +++ b/cinelerra-5.1/plugins/C41/c41.C @@ -165,7 +165,7 @@ int C41Button::handle_event() C41BoxButton::C41BoxButton(C41Effect *plugin, C41Window *window, int x, int y) - : BC_GenericButton(x, y, _("Apply box")) + : BC_GenericButton(x, y, _("Apply default box")) { this->plugin = plugin; this->window = window; @@ -267,11 +267,11 @@ C41Window::C41Window(C41Effect *plugin) add_subwindow(gamma_b = new BC_Title(x + 80, y, "0.0000")); y += 30; - add_subwindow(new BC_Title(x, y, _("Coef 1:"))); + add_subwindow(new BC_Title(x, y, _("Contrast:"))); add_subwindow(coef1 = new BC_Title(x + 80, y, "0.0000")); y += 30; - add_subwindow(new BC_Title(x, y, _("Coef 2:"))); + add_subwindow(new BC_Title(x, y, _("Brightness:"))); add_subwindow(coef2 = new BC_Title(x + 80, y, "0.0000")); y += 30; @@ -334,12 +334,12 @@ C41Window::C41Window(C41Effect *plugin) &plugin->config.fix_gamma_b, x + 80, y)); y += 30; - add_subwindow(new BC_Title(x, y, _("Coef 1:"))); + add_subwindow(new BC_Title(x, y, _("Contrast:"))); add_subwindow(fix_coef1 = new C41TextBox(plugin, &plugin->config.fix_coef1, x + 80, y)); y += 30; - add_subwindow(new BC_Title(x, y, _("Coef 2:"))); + add_subwindow(new BC_Title(x, y, _("Brightness:"))); add_subwindow(fix_coef2 = new C41TextBox(plugin, &plugin->config.fix_coef2, x + 80, y)); y += 30; @@ -545,6 +545,21 @@ float C41Effect::myPow(float a, float b) #endif +void C41Effect::pix_fix(float &pix, float min, float gamma) +{ + float val = pix; + if( val >= 1e-3 ) { + val = min / val; + if( gamma != 1 ) val = POWF(val, gamma); + bclamp(val -= config.fix_light, 0, pix_max); + if( config.postproc ) + val = config.fix_coef1 * val + config.fix_coef2; + } + else + val = 1; + pix = val; +} + int C41Effect::process_realtime(VFrame *input, VFrame *output) { load_configuration(); @@ -599,9 +614,9 @@ int C41Effect::process_realtime(VFrame *input, VFrame *output) for( int i=0; i=0; row+=pix_len ) { - *tmp++ = fix_exepts(row[0]); - *tmp++ = fix_exepts(row[1]); - *tmp++ = fix_exepts(row[2]); + *tmp++ = bclip(row[0], 0, pix_max); + *tmp++ = bclip(row[1], 0, pix_max); + *tmp++ = bclip(row[2], 0, pix_max); } } @@ -731,92 +746,91 @@ int C41Effect::process_realtime(VFrame *input, VFrame *output) send_render_gui(&values); } + if( config.compute_magic ) { + float minima_r = 50., minima_g = 50., minima_b = 50.; + float maxima_r = 0., maxima_g = 0., maxima_b = 0.; + + for( int i = min_row; i < max_row; i++ ) { + float *row = (float*)frame->get_rows()[i]; + row += 3 * shave_min_col; + for( int j = min_col; j < max_col; j++, row += 3 ) { + if( row[0] < minima_r ) minima_r = row[0]; + if( row[0] > maxima_r ) maxima_r = row[0]; + + if( row[1] < minima_g ) minima_g = row[1]; + if( row[1] > maxima_g ) maxima_g = row[1]; + + if( row[2] < minima_b ) minima_b = row[2]; + if( row[2] > maxima_b ) maxima_b = row[2]; + } + } + + // Calculate postprocessing coeficents + values.coef2 = minima_r; + if( minima_g < values.coef2 ) values.coef2 = minima_g; + if( minima_b < values.coef2 ) values.coef2 = minima_b; + values.coef1 = maxima_r; + if( maxima_g > values.coef1 ) values.coef1 = maxima_g; + if( maxima_b > values.coef1 ) values.coef1 = maxima_b; + // Try not to overflow RGB601 (235 - 16) / 256 * 0.9 + float den = values.coef1 - values.coef2; + if( fabs(den) < 1e-6 ) den = 1e-6; + values.coef1 = 0.770 / den; + values.coef2 = 0.065 - values.coef2 * values.coef1; + send_render_gui(&values); + } + // Apply the transformation if( config.active ) { for( int i = 0; i < frame_h; i++ ) { float *row = (float*)frame->get_rows()[i]; for( int j = 0; j < frame_w; j++, row += pix_len ) { - float r0 = row[0] >= 1e-6 ? row[0] : 1e-6; - float v0 = config.fix_min_r / r0 - config.fix_light; - row[0] = normalize_pixel(v0 - config.fix_light); - float r1 = row[1] >= 1e-6 ? row[1] : 1e-6; - float v1 = POWF((config.fix_min_g / r1), config.fix_gamma_g); - row[1] = normalize_pixel(v1 - config.fix_light); - float r2 = row[2] >= 1e-6 ? row[2] : 1e-6; - float v2 = POWF((config.fix_min_b / r2), config.fix_gamma_b); - row[2] = normalize_pixel(v2 - config.fix_light); - } - } - if( config.compute_magic && !config.postproc ) { - float minima_r = 50., minima_g = 50., minima_b = 50.; - float maxima_r = 0., maxima_g = 0., maxima_b = 0.; - - for( int i = min_row; i < max_row; i++ ) { - float *row = (float*)frame->get_rows()[i]; - row += 3 * shave_min_col; - for( int j = min_col; j < max_col; j++, row += 3 ) { - if( row[0] < minima_r ) minima_r = row[0]; - if( row[0] > maxima_r ) maxima_r = row[0]; - - if( row[1] < minima_g ) minima_g = row[1]; - if( row[1] > maxima_g ) maxima_g = row[1]; - - if( row[2] < minima_b ) minima_b = row[2]; - if( row[2] > maxima_b ) maxima_b = row[2]; - } + pix_fix(row[0], config.fix_min_r, 1); + pix_fix(row[1], config.fix_min_g, config.fix_gamma_g); + pix_fix(row[2], config.fix_min_b, config.fix_gamma_b); } - - // Calculate postprocessing coeficents - values.coef2 = minima_r; - if( minima_g < values.coef2 ) values.coef2 = minima_g; - if( minima_b < values.coef2 ) values.coef2 = minima_b; - values.coef1 = maxima_r; - if( maxima_g > values.coef1 ) values.coef1 = maxima_g; - if( maxima_b > values.coef1 ) values.coef1 = maxima_b; - // Try not to overflow RGB601 (235 - 16) / 256 * 0.9 - float den = values.coef1 - values.coef2; - if( fabs(den) < 1e-6 ) den = 1e-6; - values.coef1 = 0.770 / den; - values.coef2 = 0.065 - values.coef2 * values.coef1; - send_render_gui(&values); } } if( config.show_box ) { - float **rows = (float **)frame->get_rows(); - if( min_row < max_row - 1 ) { - float *row1 = (float *)rows[min_row]; - float *row2 = (float *)rows[max_row - 1]; - - for( int i = 0; i < frame_w; i++ ) { - for( int j = 0; j < 3; j++ ) { - row1[j] = pix_max - row1[j]; - row2[j] = pix_max - row2[j]; - } - if( has_alpha ) { - row1[3] = pix_max; - row2[3] = pix_max; + EDLSession *session = get_edlsession(); + int line_w = bmax(session->output_w,session->output_h) / 600 + 1; + for( int j=0; jget_rows(); + if( min_row < max_row - 1 ) { + float *row1 = (float *)rows[min_row+j]; + float *row2 = (float *)rows[max_row-j - 1]; + + for( int i = 0; i < frame_w; i++ ) { + for( int j = 0; j < 3; j++ ) { + row1[j] = pix_max - row1[j]; + row2[j] = pix_max - row2[j]; + } + if( has_alpha ) { + row1[3] = pix_max; + row2[3] = pix_max; + } + row1 += pix_len; + row2 += pix_len; } - row1 += pix_len; - row2 += pix_len; } - } - - if( min_col < max_col - 1 ) { - int pix1 = pix_len * min_col; - int pix2 = pix_len * (max_col - 1); - - for( int i = 0; i < frame_h; i++ ) { - float *row1 = rows[i] + pix1; - float *row2 = rows[i] + pix2; - for( int j = 0; j < 3; j++ ) { - row1[j] = pix_max - row1[j]; - row2[j] = pix_max - row2[j]; - } - if( has_alpha ) { - row1[3] = pix_max; - row2[3] = pix_max; + if( min_col < max_col - 1 ) { + int pix1 = pix_len * min_col+j; + int pix2 = pix_len * (max_col-j - 1); + + for( int i = 0; i < frame_h; i++ ) { + float *row1 = rows[i] + pix1; + float *row2 = rows[i] + pix2; + + for( int j = 0; j < 3; j++ ) { + row1[j] = pix_max - row1[j]; + row2[j] = pix_max - row2[j]; + } + if( has_alpha ) { + row1[3] = pix_max; + row2[3] = pix_max; + } } } } @@ -830,24 +844,3 @@ int C41Effect::process_realtime(VFrame *input, VFrame *output) return 0; } -float C41Effect::normalize_pixel(float ival) -{ - float val = fix_exepts(ival); - - if( config.postproc ) - val = config.fix_coef1 * val + config.fix_coef2; - - CLAMP(val, 0., pix_max); - return val; -} - -float C41Effect::fix_exepts(float ival) -{ - switch( fpclassify(ival) ) { - case FP_NAN: - case FP_SUBNORMAL: return 0; - case FP_INFINITE: return ival < 0 ? 0 : pix_max; - } - return ival; -} -