X-Git-Url: https://git.pterodactylus.net/?a=blobdiff_plain;f=synfig-core%2Ftags%2Fstable%2Fsrc%2Fsynfig%2Fgamma.cpp;fp=synfig-core%2Ftags%2Fstable%2Fsrc%2Fsynfig%2Fgamma.cpp;h=f1d1add7959595358bd1f111d3bc5cbfe34ad2c8;hb=684cf1db661a9a5cbc142238cf05d6d2f7aa3f89;hp=0000000000000000000000000000000000000000;hpb=829dade3901a0f6e606075811b8b5c0d1bb5393e;p=synfig.git diff --git a/synfig-core/tags/stable/src/synfig/gamma.cpp b/synfig-core/tags/stable/src/synfig/gamma.cpp new file mode 100644 index 0000000..f1d1add --- /dev/null +++ b/synfig-core/tags/stable/src/synfig/gamma.cpp @@ -0,0 +1,193 @@ +/* === S Y N F I G ========================================================= */ +/*! \file gamma.cpp +** \brief Template File +** +** $Id$ +** +** \legal +** Copyright (c) 2002-2005 Robert B. Quattlebaum Jr., Adrian Bentley +** +** This package 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 2 of +** the License, or (at your option) any later version. +** +** This package 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. +** \endlegal +*/ +/* ========================================================================= */ + +/* === H E A D E R S ======================================================= */ + +#ifdef USING_PCH +# include "pch.h" +#else +#ifdef HAVE_CONFIG_H +# include +#endif + +#include "gamma.h" +#include +#include +#endif + +/* === U S I N G =========================================================== */ + +using namespace std; +//using namespace etl; +using namespace synfig; + +/* === M A C R O S ========================================================= */ + +/* === G L O B A L S ======================================================= */ + +/* === P R O C E D U R E S ================================================= */ + +/* === M E T H O D S ======================================================= */ + +void +Gamma::set_gamma(float x) +{ + gamma_r=gamma_g=gamma_b=x; + int i; + red_blue_level=1.0f; + for(i=0;i<65536;i++) + { + float f(float(i)/65536.0f); + f=pow(f,gamma_r); + table_r_U16_to_U8[i]=table_g_U16_to_U8[i]=table_b_U16_to_U8[i]=(unsigned char)(f*(255.0f-(black_level*255))+0.5f + black_level*255.0f); + } + + for(i=0;i<256;i++) + table_r_U8_to_F32[i]=table_g_U8_to_F32[i]=table_b_U8_to_F32[i]=pow((float(i)/255.0f)*(1.0f-black_level)+black_level,gamma_r); +} + + +void +Gamma::refresh_gamma_r() +{ + int i; +// const float scalar(min(red_blue_level,1.0f)); + const float scalar(1.0f); + for(i=0;i<65536;i++) + { + float f(float(i)/65536.0f); + f=pow(f,gamma_r)*scalar; + table_r_U16_to_U8[i]=(unsigned char)(f*(255.0f-(black_level*255))+0.5f + black_level*255.0f); + } + + for(i=0;i<256;i++) + table_r_U8_to_F32[i]=pow((float(i)/255.0f)*(1.0f-black_level)+black_level,gamma_r)*scalar; +} + +void +Gamma::refresh_gamma_g() +{ + int i; +// const float scalar(sqrt(min(red_blue_level,2.0f-red_blue_level))); + const float scalar(1.0f); + for(i=0;i<65536;i++) + { + float f(float(i)/65536.0f); + f=pow(f,gamma_g)*scalar; + table_g_U16_to_U8[i]=(unsigned char)(f*(255.0f-(black_level*255))+0.5f + black_level*255.0f); + } + for(i=0;i<256;i++) + table_g_U8_to_F32[i]=pow((float(i)/255.0f)*(1.0f-black_level)+black_level,gamma_g)*scalar; +} + +void +Gamma::refresh_gamma_b() +{ + int i; +// const float scalar(min(2.0f-red_blue_level,1.0f)); + const float scalar(1.0f); + for(i=0;i<65536;i++) + { + float f(float(i)/65536.0f); + f=pow(f,gamma_b)*scalar; + table_b_U16_to_U8[i]=(unsigned char)(f*(255.0f-(black_level*255))+0.5f + black_level*255.0f); + } + for(i=0;i<256;i++) + table_b_U8_to_F32[i]=pow((float(i)/255.0f)*(1.0f-black_level)+black_level,gamma_b)*scalar; +} + +void +Gamma::set_gamma_r(float x) +{ + // If the gamma hasn't changed, then don't recompute the tables + if(x==gamma_r) return; + + gamma_r=x; + refresh_gamma_r(); +} + +void +Gamma::set_gamma_g(float x) +{ + // If the gamma hasn't changed, then don't recompute the tables + if(x==gamma_g) return; + + gamma_g=x; + refresh_gamma_g(); +} + +void +Gamma::set_gamma_b(float x) +{ + // If the gamma hasn't changed, then don't recompute the tables + if(x==gamma_b) return; + + gamma_b=x; + refresh_gamma_b(); +} + +void +Gamma::set_black_level(float x) +{ + // If the black_level hasn't changed, then don't recompute the tables + if(x==black_level) return; + + black_level=x; + + // Rebuild tables + refresh_gamma_r(); + refresh_gamma_g(); + refresh_gamma_b(); +} + +void +Gamma::set_red_blue_level(float x) +{ + // If the black_level hasn't changed, then don't recompute the tables + if(x==red_blue_level) return; + + red_blue_level=x; + + // Rebuild tables + refresh_gamma_r(); + refresh_gamma_g(); + refresh_gamma_b(); +} + +void +Gamma::set_all(float r, float g, float b, float black, float red_blue) +{ + // If nothing has changed, then don't recompute the tables + if(gamma_r==r && gamma_g==g && gamma_b==b && black_level==black && red_blue_level==red_blue) + return; + + gamma_r=r; + gamma_g=g; + gamma_b=b; + black_level=black; + red_blue_level=red_blue; + + // Rebuild tables + refresh_gamma_r(); + refresh_gamma_g(); + refresh_gamma_b(); +}