//	K ENB Evolution    
//	Advanced K enbbloom.fx Shader v6.0
//	Multiple Anamorphic Lens Flare Passes
//	Additional effects and saturation settings per passes courtesy of Matso and Dirty Peasant
//	Basing on initial crazyness courtesy of Midhras, you crazy dutchman, you ! :P
//	Initial D-N-I Code courtesy of --JawZ--
//	Code extensive modifications by Kyo
//	Copyright (c) 2007-2013 Boris Vorontsov

//======================================================================================================================================================================================
// 	Effects options : 1 to enable, 0 to disable
//======================================================================================================================================================================================

/**
 *	* KYO ! : Let the following define enabled in my setup ! *   
 */
#define ENABLE_FLIP_DAY_NIGHT_FACTOR	1

//======================================================================================================================================================================================

#define USE_TINTING				1		// Comment it to disable tinting or (1 = fixed color tinting, 2 = texture sample tinting, 3 and 4 = add blending)
#define USE_PRIMARY_ANAMFLARE			1		// Set 0 to disable Primary anamorphic lens flare (ALF)
#define USE_SECONDARY_ANAMFLARE			1		// Set 0 to disable Secondary anamorphic lens flare (ALF_2)
#define USE_BLOOM_CONTRAST   			1		// Set 0 to disable postpass contrast fine-tuning control


//======================================================================================================================================================================================

// Anamorphic Lens Flare Types PRESETS (lenz effect based on light emitters, depending on their intensities, colours, setable for Days, Nights and Interiors)

/**
 *	KYO : Choose only * ONE * type per circumstance
 *	AMBIENT is discreet, set on light emitters colours
 *	KINEMATIC is a bit more noticeable, set on light emitters colours
 *	MOVIE is more noticeable, fixed to a single colour tint, mostly based on Violet a/o Cyan RGB formulas
 *	Mix and match below, and choose Horizontal or Vertical axis
 */

#define USE_AMBIENT_ALF_DAY		1
#define USE_MOVIE_ALF_DAY		0
#define USE_KINEMATIC_ALF_DAY		0

#define USE_AMBIENT_ALF_NIGHT		0
#define USE_MOVIE_ALF_NIGHT		0
#define USE_KINEMATIC_ALF_NIGHT		1

#define USE_AMBIENT_ALF_INT		1
#define USE_MOVIE_ALF_INT		0
#define USE_KINEMATIC_ALF_INT		0

/**
 *	KYO : The following will set Secondary ALF's behaviour
 */

#define USE_ENHANCE_PRIMARY		0
#define USE_COMPLEMENT_PRIMARY		1


//======================================================================================================================================================================================

// Bloom Colour Tinting parameters
#define TINT_COLOR_DAY			float3(0.55, 0.48, 0.61)	// fixed color R /G /B	
#define TINT_COLOR_NIGHT		float3(0.55, 0.48, 0.61)	// fixed color R /G /B		
#define TINT_COLOR_INTERIOR		float3(0.55, 0.48, 0.61)	// fixed color R /G /B		
	
#define TINT_TEXTURE	tex2D(SamplerBloom6, In.txcoord0.xy).rgb	// sampled color if using USE_TINTING == 2

// Tint Level parameters
#define TINT_LEVEL_DAY			0.55				// level of tint used in the process	//0.5525  <- [KYO : slightly more lighting in bloom]
#define TINT_LEVEL_NIGHT		0.55				// level of tint used in the process	//0.575 //0.565 <- [KYO : slightly more bloom and pizza]
#define TINT_LEVEL_INTERIOR		0.54925		//0.54875	// level of tint used in the process	//0.565 //0.55  <- [KYO : slightly more pizza]

// Tint Blending parameters for methods 3 and 4
#define TINT_BLEND_DAY			0.1111				// blend factor between fixed and sampled color tints	//[KYO : try 2.0 or more exagerated values yet]
#define TINT_BLEND_NIGHT		0.1111				// blend factor between fixed and sampled color tints
#define TINT_BLEND_INTERIOR		0.1111				// blend factor between fixed and sampled color tints

// Tinting Method Defines
#if USE_TINTING == 1							// definition of tint color
 #define TINT			TINT_COLOR
#elif USE_TINTING == 2
 #define TINT			TINT_TEXTURE
#elif USE_TINTING == 3
#define TINT			lerp(TINT_TEXTURE, TINT_COLOR, TINT_BLEND)
#elif USE_TINTING == 4
#define TINT			lerp(tex2D(SamplerBloom1, 0.5).rgb, TINT_COLOR, TINT_BLEND)	// sampled color if using USE_TINTING == 4
#endif


//======================================================================================================================================================================================

// Primary Anamorphic Lens Flare (lenz effect based on light emitters, depending on their intensities, colours, setable for Days, Nights and Interiors)

/**
 *	KYO : When fFlareTint RGB values are equal, the ALF will be the exact same colour as the light emitter it's generated by
 *	When values are different, ALF's colour will be fixed to the currently set RGB values
 *	By choosing 0 or 1 as the ALF's axis, you can set it horizontal *or* vertical depending on Days, Nights or Interiors circumstances
 */

/**
*	Primary Anamorphic flare parameters DAY
*/

#if (USE_AMBIENT_ALF_DAY == 1)
#define fFlareLuminance_Day 				0.333				// Threshold 
#define fFlareBlur_Day 					15.0	//14.0			// Size of the flare
#define fFlareIntensity_Day 				0.14 				// Intensity			
#define fFlareTint_Day					float3(0.32, 0.32, 0.32)	// Tint R-G-B //[KYO : densified opacity a bit : 0.27 low, 0.30 discreet, 0.35 strong]
#define fFlareAxis_Day					0	// Blur axis    	// [KYO : 0 is horizontal - 1 is vertical - Stackable -if using- with ALF from enbeffectprepass.fx]
#endif

#if (USE_KINEMATIC_ALF_DAY == 1)
#define fFlareLuminance_Day				0.233			
#define fFlareBlur_Day	 				16.0				// 15.0, 14.0		
#define fFlareIntensity_Day      			0.15				// 0.14					
#define fFlareTint_Day					float3(0.34, 0.34, 0.34)	
#define fFlareAxis_Day					0		
#endif

#if (USE_MOVIE_ALF_DAY == 1)
#define fFlareLuminance_Day				0.333				
#define fFlareBlur_Day	 				15.0				// 14.0			
#define fFlareIntensity_Day				0.44				// 0.68 MEB below		
//#define fFlareTint_Day				float3(0.012, 0.313, 0.588)	// Tint R-G-B	//[KYO : Medium Electric Blue]	
#define fFlareTint_Day					float3(0.000, 0.000, 1.000)	// Tint R-G-B	//[KYO : Blue]			
#define fFlareAxis_Day					0	
#endif

/**
*	Primary Anamorphic flare parameters NIGHT
*/

#if (USE_AMBIENT_ALF_NIGHT == 1)
#define fFlareLuminance_Night 				0.333				// Threshold 
#define fFlareBlur_Night 				15.0				// Size of the flare
#define fFlareIntensity_Night 				0.14				// Intensity			
#define fFlareTint_Night				float3(0.32, 0.32, 0.32)	// Tint R-G-B //[KYO : densified opacity a bit : 0.27 low, 0.30 discreet, 0.35 strong]
#define fFlareAxis_Night				0	// Blur axis  		// [KYO : 0 is horizontal - 1 is vertical]
#endif

#if (USE_KINEMATIC_ALF_NIGHT == 1)
#define fFlareLuminance_Night				0.333				// 0.233, 0.277				
#define fFlareBlur_Night	 			14.0				// 15.0, 18.0		
#define fFlareIntensity_Night    			0.155				// 0.14, 0.16						
#define fFlareTint_Night				float3(0.35, 0.35, 0.35)	
#define fFlareAxis_Night				0	
#endif

#if (USE_MOVIE_ALF_NIGHT == 1)
#define fFlareLuminance_Night				0.222				
#define fFlareBlur_Night 				15.0				// 14.0			
#define fFlareIntensity_Night				0.52				// 0.68 MEB below		
//#define fFlareTint_Night				float3(0.012, 0.313, 0.588)	// Tint R-G-B	//[KYO : Medium Electric Blue]	
#define fFlareTint_Night				float3(0.000, 0.000, 1.000)	// Tint R-G-B	//[KYO : Blue]			
#define fFlareAxis_Night				0	
#endif

/**
*	Primary Anamorphic flare parameters INTERIOR
*/

#if (USE_AMBIENT_ALF_INT == 1)
#define fFlareLuminance_Interior 			0.333				// Threshold 
#define fFlareBlur_Interior 				14.0	//15.0			// Size of the flare
#define fFlareIntensity_Interior 			0.16 	//0.14			// Intensity			
#define fFlareTint_Interior				float3(0.34, 0.34, 0.34)	// Tint R-G-B //[KYO : densified opacity a bit : 0.27 low, 0.30 discreet, 0.35 strong]
#define fFlareAxis_Interior				0 	// Blur axis 		// [KYO : 0 is horizontal - 1 is vertical] 
#endif

#if (USE_KINEMATIC_ALF_INT == 1)
#define fFlareLuminance_Interior 			0.233				
#define fFlareBlur_Interior 				14.0				// 15.0, 18.0		
#define fFlareIntensity_Interior 			0.16				// 0.14						
#define fFlareTint_Interior				float3(0.36, 0.36, 0.36)	
#define fFlareAxis_Interior				1	
#endif

#if (USE_MOVIE_ALF_INT == 1)
#define fFlareLuminance_Interior 			0.222				
#define fFlareBlur_Interior 				15.0				// 14.0			
#define fFlareIntensity_Interior 			0.62				// 0.50 Blue	//0.68 MEB below	
#define fFlareTint_Interior				float3(0.012, 0.313, 0.588)	// Tint R-G-B	//[KYO : Medium Electric Blue]	
//#define fFlareTint_Interior				float3(0.000, 0.000, 1.000)	// Tint R-G-B	//[KYO : Blue]			
#define fFlareAxis_Interior				0	
#endif

//======================================================================================================================================================================================

// Secondary Anamorphic Lens Flare (lenz effect based on light emitters, depending on their intensities, colours, setable for Days, Nights and Interiors)

/**
 *	KYO : When fFlareTint_Secondary RGB values are equal, the Secondary ALF will be the exact same colour as the light emitter it's generated by
 *	When values are different, Secondary ALF's colour will be fixed to the currently set RGB values
 *	By choosing 0 or 1 as the Secondary ALF's axis, you can set it horizontal *or* vertical depending on Days, Nights or Interiors circumstances
 */

#if (USE_ENHANCE_PRIMARY == 1)
/**
*	Secondary Anamorphic flare parameters DAY
*/

#define fFlareLuminance_Secondary_Day			3.333	// 0.888, 0.777		// Threshold // I'll set something rather high here, to better blend with Primary
#define fFlareBlur_Secondary_Day	 		8.0	// 15.0, 14.0		// Size of the flare
#define fFlareIntensity_Secondary_Day    		0.0022	// 0.15, 0.13, 0.07	// Intensity, 0.00 to disable, 0.0033 to enhance			
#define fFlareTint_Secondary_Day			float3(0.00, 0.00, 1.00)	// Tint R-G-B 
#define fFlareAxis_Secondary_Day			0	// Blur axis 		// [KYO : 0 is horizontal - 1 is vertical] 

/**
*	Secondary Anamorphic flare parameters NIGHT
*/

#define fFlareLuminance_Secondary_Night			0.333				
#define fFlareBlur_Secondary_Night	 		15.0				// 16.0, 14.0		
#define fFlareIntensity_Secondary_Night    		0.155				// 0.14, 0.16, 0.15						
#define fFlareTint_Secondary_Night			float3(0.012, 0.313, 0.588)	
#define fFlareAxis_Secondary_Night			1	

/**
*	Secondary Anamorphic flare parameters INTERIOR
*/

#define fFlareLuminance_Secondary_Interior		0.233				
#define fFlareBlur_Secondary_Interior	 		200.0				// 16.0, 15.0, 14.0	
#define fFlareIntensity_Secondary_Interior    		0.15				// 0.14, 0.16					
#define fFlareTint_Secondary_Interior			float3(0.00, 0.00, 1.00)	
#define fFlareAxis_Secondary_Interior			1 	

#endif


#if (USE_COMPLEMENT_PRIMARY == 1)
/**
*	Secondary Anamorphic flare parameters DAY
*/

#define fFlareLuminance_Secondary_Day			3.333	// 0.888, 0.777		// Threshold // I'll set something rather high here, to better blend with Primary
#define fFlareBlur_Secondary_Day	 		8.0	// 15.0, 14.0		// Size of the flare
#define fFlareIntensity_Secondary_Day    		0.0022	// 0.15, 0.13, 0.07	// Intensity, 0.00 to disable, 0.0033 to enhance			
#define fFlareTint_Secondary_Day			float3(0.012, 0.313, 0.588)	// Tint R-G-B 
#define fFlareAxis_Secondary_Day			1	// Blur axis 		// [KYO : 0 is horizontal - 1 is vertical] 

/**
*	Secondary Anamorphic flare parameters NIGHT
*/

#define fFlareLuminance_Secondary_Night			0.333				
#define fFlareBlur_Secondary_Night	 		15.0				// 16.0, 14.0		
#define fFlareIntensity_Secondary_Night    		0.155				// 0.14, 0.16, 0.15						
#define fFlareTint_Secondary_Night			float3(0.00, 0.00, 1.00)	
#define fFlareAxis_Secondary_Night			1	

/**
*	Secondary Anamorphic flare parameters INTERIOR
*/

#define fFlareLuminance_Secondary_Interior		0.233				
#define fFlareBlur_Secondary_Interior	 		200.0				// 16.0, 15.0, 14.0	
#define fFlareIntensity_Secondary_Interior    		0.18				// 0.14, 0.16, 0.15					
#define fFlareTint_Secondary_Interior			float3(0.012, 0.313, 0.588)	// (0.00, 0.00, 1.00)	
#define fFlareAxis_Secondary_Interior			1 	

#endif


//======================================================================================================================================================================================

// Additional Bloom Radii (radius indicates what area of the image will take part in bloom calculations according to single pixel)

/**
 *	KYO : Bloom radii shall be set below, NOT in enbseries.ini
 *	Values are based off Bokeh weighting - Try 0.122 - 0.282 - 0.524 - 1.122 - 1.282 - 1.524
 * 	Default values in Standard ENB Series Bloom can be considered as 0.122, 0.524, 1.282
 */

// Bloom Radii DAY
#define BloomRadius0_Day 0.282				// Input Texture is fullscreen
#define BloomRadius1_Day 0.524				// Bloom Texture 1 - FirstPass
#define BloomRadius2_Day 1.282				// Bloom Texture 2 - SecondPass

// Bloom Radii NIGHT
#define BloomRadius0_Night 0.282
#define BloomRadius1_Night 0.524
#define BloomRadius2_Night 1.282

// Bloom Radii NIGHT
#define BloomRadius0_Interior 0.282
#define BloomRadius1_Interior 0.524
#define BloomRadius2_Interior 1.282


//======================================================================================================================================================================================

// Bloom Exposure - Overall Saturation and Bleeding (exposure control before final mix in postpass : ZeroPassHQ is bloom prepass, 1st is bloom texture 1, 2nd is bloom texture 2)

/**
 *	KYO : Use Bokeh weights here, or choose another poison :P Feel free to experiment
 *	Classic values range as follows : 0.122, 0.282, 0.524, 1.122, 1.282, 1.524, and so on
 *	This ' knob ' will control overall bloom vibrance and bleeding, ZeroPassHQ being the most sensible (FullScreen texture)
 */

// Bloom Exposure DAY
#define BloomExposure_ZeroPassHQ_Day 		1.282		// FullScreen Texture - Bloom Prepass		
#define BloomExposure_FirstPass_Day 		1.524		// Bloom Texture 1
#define BloomExposure_SecondPass_Day 		1.524		// Bloom Texture 2

// Bloom Exposure NIGHT
#define BloomExposure_ZeroPassHQ_Night 		1.282		// 1.524	//1.423		
#define BloomExposure_FirstPass_Night 		1.524
#define BloomExposure_SecondPass_Night 		1.524

// Bloom Exposure INTERIOR
#define BloomExposure_ZeroPassHQ_Interior 	1.282		
#define BloomExposure_FirstPass_Interior 	1.524
#define BloomExposure_SecondPass_Interior 	1.524


//======================================================================================================================================================================================

// Additional Bloom Saturation (level of saturation added for each bloom pass : ZeroPassHQ is bloom prepass, 1st is bloom texture 1, 2nd is bloom texture 2, last is bloom postpass)

/**
 *	KYO : Can be set positive or negative
 */

// Bloom Saturation DAY
#define Saturation_ZeroPassHQ_Day 	0.425		// FullScreen Texture - Bloom Prepass		
#define Saturation_FirstPass_Day 	0.1		// Bloom Texture 1
#define Saturation_SecondPass_Day 	-0.25		// Bloom Texture 2
#define Saturation_LastPass_Day 	0.2		// Bloom PostPass - mixes several bloom textures

// Bloom Saturation NIGHT
#define Saturation_ZeroPassHQ_Night 	0.425		
#define Saturation_FirstPass_Night 	0.1
#define Saturation_SecondPass_Night 	-0.25
#define Saturation_LastPass_Night 	0.2

// Bloom Saturation INTERIOR
#define Saturation_ZeroPassHQ_Interior 	0.425		
#define Saturation_FirstPass_Interior 	0.1
#define Saturation_SecondPass_Interior 	-0.25
#define Saturation_LastPass_Interior 	0.2


//======================================================================================================================================================================================

// Additional MiddleGray Factors (compensation multiplier for saturation's middlegray : ZeroPassHQ is bloom prepass, 1st is bloom texture 1, 2nd is bloom texture 2, last is bloom postpass)

/**
 *	KYO : You can try 0.133 or even lower for blazing bloom - Thanx Midh ! :P  
 *	Multipliers allow for ' compensating ' bloom.r+bloom.g+bloom.b
 */

// Bloom MiddleGray Factors DAY
#define MiddleGrayFactor_ZeroPassHQ_Day 	0.533	// FullScreen Texture - Bloom Prepass		
#define MiddleGrayFactor_FirstPass_Day 		0.433	// Bloom Texture 1
#define MiddleGrayFactor_SecondPass_Day 	0.433	// Bloom Texture 2
#define MiddleGrayFactor_LastPass_Day 		0.333	// Bloom PostPass - mixes several bloom textures

// Bloom MiddleGray Factors NIGHT
#define MiddleGrayFactor_ZeroPassHQ_Night 	0.533		
#define MiddleGrayFactor_FirstPass_Night 	0.433
#define MiddleGrayFactor_SecondPass_Night 	0.433
#define MiddleGrayFactor_LastPass_Night 	0.333

// Bloom MiddleGray Factors INTERIOR
#define MiddleGrayFactor_ZeroPassHQ_Interior 	0.533		
#define MiddleGrayFactor_FirstPass_Interior 	0.433
#define MiddleGrayFactor_SecondPass_Interior 	0.433
#define MiddleGrayFactor_LastPass_Interior 	0.333


//======================================================================================================================================================================================

// Bloom Multipliers (ZeroPassHQ is bloom prepass, 1st is bloom texture 1, 2nd is bloom texture 2, last is bloom postpass)

// Bloom Multiplier DAY
#define BloomMultiplier_ZeroPassHQ_Day 		0.24041994	// FullScreen Texture - Bloom Prepass		
#define BloomMultiplier_FirstPass_Day 		0.102020997	// Bloom Texture 1
#define BloomMultiplier_SecondPass_Day 		0.075020997	// Bloom Texture 2
#define BloomMultiplier_LastPass_Day 		0.142857142	// Bloom PostPass - mixes several bloom textures

// Bloom Multiplier NIGHT
#define BloomMultiplier_ZeroPassHQ_Night 	0.24041994		
#define BloomMultiplier_FirstPass_Night 	0.102020997	// 0.082020997
#define BloomMultiplier_SecondPass_Night 	0.075020997	// 0.082020997 
#define BloomMultiplier_LastPass_Night 		0.142857142

// Bloom Multiplier INTERIOR
#define BloomMultiplier_ZeroPassHQ_Interior 	0.24041994		
#define BloomMultiplier_FirstPass_Interior 	0.102020997	// 0.082020997
#define BloomMultiplier_SecondPass_Interior 	0.075020997	// 0.082020997 
#define BloomMultiplier_LastPass_Interior 	0.142857142


//======================================================================================================================================================================================

// Bloom Spray (bloom intensity / level control knob for bloom prepass - ZeroPassHQ FullScreen Texture)

/**
 *	KYO : proceed via * very * small increments - Raising this value will make overall bloom ' brighter ' and wider
 *	Decreasing will ' tighten ' bloom and make it ' darker '
 *	usefull fine-tuning knob for interiors brightness and exposure once they're set in enbeffect.fx
 */

#define BloomSpray_Day 		0.075		// KYO : 0.0	
#define BloomSpray_Night 	0.075		// 0.7485		
#define BloomSpray_Interior 	0.075		


//======================================================================================================================================================================================

// Bloom Contrast (bloom intensity / level control knob for bloom postpass - mixes several bloom textures )
// Needs to be enabled via main defines - See above
// KYO : I'm using this to fine-tune the bloom's behaviour for bright spots and light emitters

/**
 *	KYO : proceed via * very * small increments for fine-tuning here - Set positive to limit, set negative to spray
 *	Decreasing will ' spray ' bloom wider and make it ' shinier ' and more saturated
 *	Increasing will act as a bloom limiter, darkening it and lowering its saturation
 *	Adviced values for fine-tuning range as follow : [KYO : add 0.1 to these to clearly notice the changes]
 *	-0.0524, -0.0433, -0.0333, -0.0282, -0.0233 -0.0133 -0.0122, -0.01, -0.0075, -0.0033 
 *	[0.0 (neutral)]
 *	0.0033, 0.0075, 0.01, 0.0122, 0.0133, 0.0233, 0.0282, 0.0333, 0.0433, 0.0524
 */

#define BloomContrast_Day 		-0.0524		// -0.0282	//-0.0524	//-0.0433	//KYO : 0.0 is neutral - Set -0.0122 to regain consistency	
#define BloomContrast_Night 		-0.0033		// KYO : 0.0 is neutral			
#define BloomContrast_Interior 		0.0		// KYO : 0.0 is neutral	


//======================================================================================================================================================================================
//[KYO : external parameters, do not modify unless you * EXACTLY * know what you're doing]
//======================================================================================================================================================================================

#if (ENABLE_FLIP_DAY_NIGHT_FACTOR == 0)
		1 - ENightDayFactor = ENightDayFactor;
#endif

//keyboard controlled temporary variables (in some versions exists in the config file). Press and hold key 1,2,3...8 together with PageUp or PageDown to modify. By default all set to 1.0
float4	tempF1; //0,1,2,3
float4	tempF2; //5,6,7,8
float4	tempF3; //9,0
//x=Width, y=1/Width, z=ScreenScaleY, w=1/ScreenScaleY
float4	ScreenSize;
//x=generic timer in range 0..1, period of 16777216 ms (4.6 hours), w=frame time elapsed (in seconds)
float4	Timer;
//additional info for computations
float4	TempParameters; 
//BloomRadius1, BloomRadius2, BloomBlueShiftAmount, BloomContrast
float4	BloomParameters;
//Additional Vars for D-N-I Separation
//changes in range 0..1, 0 means that night time, 1 - day time
float	ENightDayFactor;
//changes 0 or 1. 0 means that exterior, 1 - interior
float	EInteriorFactor;
//changes in range 0..1, 0 means full quality, 1 lowest dynamic quality (0.33, 0.66 are limits for quality levels)
float	EAdaptiveQualityFactor;
//fov in degrees
float	FieldOfView;

// Textures & samplers
texture2D texBloom1;
texture2D texBloom2;
texture2D texBloom3;
texture2D texBloom4;
texture2D texBloom5;
texture2D texBloom6;
texture2D texBloom7;//additional bloom tex
texture2D texBloom8;//additional bloom tex

sampler2D SamplerBloom1 = sampler_state
{
    Texture   = <texBloom1>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

sampler2D SamplerBloom2 = sampler_state
{
    Texture   = <texBloom2>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

sampler2D SamplerBloom3 = sampler_state
{
    Texture   = <texBloom3>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

sampler2D SamplerBloom4 = sampler_state
{
    Texture   = <texBloom4>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

sampler2D SamplerBloom5 = sampler_state
{
    Texture   = <texBloom5>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

sampler2D SamplerBloom6 = sampler_state
{
    Texture   = <texBloom6>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

sampler2D SamplerBloom7 = sampler_state
{
    Texture   = <texBloom7>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

sampler2D SamplerBloom8 = sampler_state
{
    Texture   = <texBloom8>;
	MinFilter = LINEAR;
	MagFilter = LINEAR;
	MipFilter = NONE;//NONE;
	AddressU  = Clamp;
	AddressV  = Clamp;
	SRGBTexture=FALSE;
	MaxMipLevel=0;
	MipMapLodBias=0;
};

// Shaders input/output structures
struct VS_OUTPUT_POST
{
	float4 vpos  : POSITION;
	float2 txcoord0 : TEXCOORD0;
};
struct VS_INPUT_POST
{
	float3 pos  : POSITION;
	float2 txcoord0 : TEXCOORD0;
};

/**
 * Bright pass - rescales sampled pixel to emboss bright enough value.
 */
float3 BrightPass(float2 tex)
{
float fFlareLuminance =lerp( lerp( fFlareLuminance_Day, fFlareLuminance_Night, 1 - ENightDayFactor ), fFlareLuminance_Interior, EInteriorFactor);

	float3 c = tex2D(SamplerBloom2, tex).rgb;
    float3 bC = max(c - float3(fFlareLuminance, fFlareLuminance, fFlareLuminance), 0.0);
    float bright = dot(bC, 1.0);
    bright = smoothstep(0.0f, 0.5, bright);
    return lerp(0.0, c, bright);
}

/**
 * Anamorphic sampling function - scales pixel coordinate
 * to stretch the image along one of the axels.
 * (http://en.wikipedia.org/wiki/Anamorphosis)
 */
float3 AnamorphicSample(int axis, float2 tex, float blur)
{
	tex = 2.0 * tex - 1.0;
	if (!axis) tex.x /= -blur;
	else tex.y /= -blur;
	tex = 0.5 * tex + 0.5;
	return BrightPass(tex);
}

/**
 * Converts pixel color to gray-scale.
 */
float GrayScale(float3 sample)
{
	return dot(sample, float3(0.3, 0.59, 0.11));
}

// Constants ///////////////////////////////////////////////////////////////
const float2 bloomOffset[8]=
{
	float2(0.707, 0.707),
	float2(0.707, -0.707),
	float2(-0.707, 0.707),
	float2(-0.707, -0.707),
	float2(0.0, 1.0),
	float2(0.0, -1.0),
	float2(1.0, 0.0),
	float2(-1.0, 0.0)
};

// [KYO : memo]
// Deepness, curvature, inverse size
const float3 offset[4]=
{
	float3(1.6, 4.0, 1.0),
	float3(0.7, 0.25, 2.0),
	float3(0.3, 1.5, 0.5),
	float3(-0.5, 1.0, 1.0)
};

// Color filter per reflection
const float3 factors[4]=
{
	float3(0.3, 0.4, 0.4),
	float3(0.2, 0.4, 0.5),
	float3(0.5, 0.3, 0.7),
	float3(0.1, 0.2, 0.7)
};

// Shaders //////////////////////////////////////////////////////////////////

// Vertex shader (screen-aligned mesh)
VS_OUTPUT_POST VS_Bloom(VS_INPUT_POST IN)
{
	VS_OUTPUT_POST OUT;
	OUT.vpos = float4(IN.pos.x, IN.pos.y, IN.pos.z, 1.0);
	OUT.txcoord0.xy = IN.txcoord0.xy + TempParameters.xy;

	return OUT;
}

// Primary Anamorphic lens flare pixel shader (Matso code)
float4 PS_ProcessPass_Anamorphic_Primary(VS_OUTPUT_POST IN, float2 vPos : VPOS, uniform int axis) : COLOR
{
float fFlareBlur =lerp( lerp( fFlareBlur_Day, fFlareBlur_Night, 1 - ENightDayFactor ), fFlareBlur_Interior, EInteriorFactor);
float3 fFlareTint =lerp( lerp( fFlareTint_Day, fFlareTint_Night, 1 - ENightDayFactor ), fFlareTint_Interior, EInteriorFactor);
float fFlareIntensity =lerp( lerp( fFlareIntensity_Day, fFlareIntensity_Night, 1 - ENightDayFactor ), fFlareIntensity_Interior, EInteriorFactor);
//[KYO : axis is separated below in pass p1]

	float4 res;
	float2 coord = IN.txcoord0.xy;
	float3 anamFlare = AnamorphicSample(axis, coord.xy, fFlareBlur) * fFlareTint;
	
	res.rgb = anamFlare * fFlareIntensity;
	res.a = 1.0;
	
	return res;
}

// Secondary Anamorphic lens flare pixel shader (Matso code)
float4 PS_ProcessPass_Anamorphic_Secondary(VS_OUTPUT_POST IN, float2 vPos : VPOS, uniform int axis) : COLOR
{
float fFlareBlur_Secondary =lerp( lerp( fFlareBlur_Secondary_Day, fFlareBlur_Secondary_Night, 1 - ENightDayFactor ), fFlareBlur_Secondary_Interior, EInteriorFactor);
float3 fFlareTint_Secondary =lerp( lerp( fFlareTint_Secondary_Day, fFlareTint_Secondary_Night, 1 - ENightDayFactor ), fFlareTint_Secondary_Interior, EInteriorFactor);
float fFlareIntensity_Secondary =lerp( lerp( fFlareIntensity_Secondary_Day, fFlareIntensity_Secondary_Night, 1 - ENightDayFactor ), fFlareIntensity_Secondary_Interior, EInteriorFactor);
//[KYO : I know, below is SO cheap... :P]
float fThreshold_Secondary_Day = (fFlareLuminance_Day * 0.0) + fFlareLuminance_Secondary_Day;
float fThreshold_Secondary_Night = (fFlareLuminance_Night * 0.0) + fFlareLuminance_Secondary_Night;
float fThreshold_Secondary_Interior = (fFlareLuminance_Interior * 0.0) + fFlareLuminance_Secondary_Interior;
//[KYO : axis is separated below in pass p2]

	float4 res;
	float2 coord = IN.txcoord0.xy;
	float3 anamFlare = AnamorphicSample(axis, coord.xy, fFlareBlur_Secondary) * fFlareTint_Secondary;
	
	res.rgb = anamFlare * fFlareIntensity_Secondary;
	res.a = 1.0;
	
	return res;
}

//zero pass HQ, input texture is fullscreen
//SamplerBloom1 - fullscreen texture
float4 PS_BloomPrePass(VS_OUTPUT_POST In) : COLOR
{
float BloomRadius0 =lerp( lerp( BloomRadius0_Day, BloomRadius0_Night, 1 - ENightDayFactor ), BloomRadius0_Interior, EInteriorFactor);
float BloomMultiplier_ZeroPassHQ=lerp( lerp( BloomMultiplier_ZeroPassHQ_Day, BloomMultiplier_ZeroPassHQ_Night, 1 - ENightDayFactor ), BloomMultiplier_ZeroPassHQ_Interior, EInteriorFactor);
float BloomSpray =lerp( lerp( BloomSpray_Day, BloomSpray_Night, 1 - ENightDayFactor ), BloomSpray_Interior, EInteriorFactor);
float BloomExposure_ZeroPassHQ =lerp( lerp( BloomExposure_ZeroPassHQ_Day, BloomExposure_ZeroPassHQ_Night, 1 - ENightDayFactor ), BloomExposure_ZeroPassHQ_Interior, EInteriorFactor);
	float4 bloomuv;
	float4 bloom = BloomSpray; 
	float2 screenfact = TempParameters.z;
	float4 srcbloom = bloom;
	
	screenfact.y *= ScreenSize.z;
	
	for (int i = 0; i < 4; i++)
	{
		bloomuv.xy = bloomOffset[i] * BloomRadius0;
		bloomuv.xy = (bloomuv.xy * screenfact.xy) + In.txcoord0.xy;		
		bloom.xyz += tex2D(SamplerBloom1, bloomuv.xy).xyz * BloomExposure_ZeroPassHQ;//1.282 //1.524 //1.423 [use bokeh weights here...]
	}
	bloom.xyz *= BloomMultiplier_ZeroPassHQ; 

	bloom.xyz = min(bloom.xyz, 32768.0);
	bloom.xyz = max(bloom.xyz, 0.0);
        float Saturation_ZeroPassHQ=lerp( lerp( Saturation_ZeroPassHQ_Day, Saturation_ZeroPassHQ_Night, 1 - ENightDayFactor ), Saturation_ZeroPassHQ_Interior, EInteriorFactor);
float MiddleGrayFactor_ZeroPassHQ=lerp( lerp( MiddleGrayFactor_ZeroPassHQ_Day, MiddleGrayFactor_ZeroPassHQ_Night, 1 - ENightDayFactor ), MiddleGrayFactor_ZeroPassHQ_Interior, EInteriorFactor);	
	float middlegray=(bloom.r+bloom.g+bloom.b)*MiddleGrayFactor_ZeroPassHQ; 
	float3 diffcolor=bloom.rgb-middlegray;
	bloom.rgb+=diffcolor*Saturation_ZeroPassHQ;
	bloom.rgb=max(bloom.rgb, 0.0); //output must be never negative.
	bloom.w = 1.0;
        return bloom;	
}

//first and second passes draw to every texture
//twice, after computations of these two passes,
//result is set as input to next cycle

//first pass
//SamplerBloom1 is result of prepass or second pass from cycle
float4 PS_BloomTexture1(VS_OUTPUT_POST In) : COLOR
{
float BloomRadius1 =lerp( lerp( BloomRadius1_Day, BloomRadius1_Night, 1 - ENightDayFactor ), BloomRadius1_Interior, EInteriorFactor);
float BloomMultiplier_FirstPass=lerp( lerp( BloomMultiplier_FirstPass_Day, BloomMultiplier_FirstPass_Night, 1 - ENightDayFactor ), BloomMultiplier_FirstPass_Interior, EInteriorFactor);
float BloomExposure_FirstPass =lerp( lerp( BloomExposure_FirstPass_Day, BloomExposure_FirstPass_Night, 1 - ENightDayFactor ), BloomExposure_FirstPass_Interior, EInteriorFactor);
	float4 bloomuv;
	float4 bloom = tex2D(SamplerBloom1, In.txcoord0);
	float2 screenfact = TempParameters.z;
	float4 srcbloom = bloom;
	float4 bloomadd = bloom;
	float step = BloomRadius1 * BloomParameters.x;
	
	screenfact.y *= ScreenSize.z;
	screenfact.xy *= step;

	for (int i = 0; i < 8; i++)
	{
		bloomuv.xy = bloomOffset[i];
		bloomuv.xy = (bloomuv.xy * screenfact.xy) + In.txcoord0.xy;
		bloom += tex2D(SamplerBloom1, bloomuv.xy) * BloomExposure_FirstPass;	//1.524
	}
	bloom *= BloomMultiplier_FirstPass;  

#ifdef USE_TINTING
/**
 *	D-N-I
 */
float TINT_LEVEL =lerp( lerp( TINT_LEVEL_DAY, TINT_LEVEL_NIGHT, 1 - ENightDayFactor ), TINT_LEVEL_INTERIOR, EInteriorFactor);
float3 TINT_COLOR =lerp( lerp( TINT_COLOR_DAY, TINT_COLOR_NIGHT, 1 - ENightDayFactor ), TINT_COLOR_INTERIOR, EInteriorFactor);
float TINT_BLEND =lerp( lerp( TINT_BLEND_DAY, TINT_BLEND_NIGHT, 1 - ENightDayFactor ), TINT_BLEND_INTERIOR, EInteriorFactor);

	float3 tint = TINT * TINT_LEVEL;
	float ttt = max(dot(bloom.xyz, 0.333) - dot(srcbloom.xyz, 0.111), 0.0);
	//float ttt = max(dot(bloom.xyz, 0.333) - dot(srcbloom.xyz, 0.333), 0.0);
	float gray = BloomParameters.z * ttt * 10.0;	
	float mixfact = (gray / (1.0 + gray));
	
	mixfact *= 1.0 - saturate((TempParameters.w - 1.0) * 0.2);
	tint.xy += saturate((TempParameters.w - 1.0) * 0.3);
	tint.xy = saturate(tint.xy);
	
	bloom.xyz *= lerp(1.0, tint.xyz, mixfact);
#endif

	float Saturation_FirstPass=lerp( lerp( Saturation_FirstPass_Day, Saturation_FirstPass_Night, 1 - ENightDayFactor ), Saturation_FirstPass_Interior, EInteriorFactor);
float MiddleGrayFactor_FirstPass=lerp( lerp( MiddleGrayFactor_FirstPass_Day, MiddleGrayFactor_FirstPass_Night, 1 - ENightDayFactor ), MiddleGrayFactor_FirstPass_Interior, EInteriorFactor);
	float middlegray=(bloom.r+bloom.g+bloom.b)*MiddleGrayFactor_FirstPass;
	float3 diffcolor=bloom.rgb-middlegray;
	bloom.rgb+=diffcolor*Saturation_FirstPass;
	bloom.rgb=max(bloom.rgb, 0.0); //output must be never negative.
	bloom.w = 1.0;
	
	return bloom;
}

//second pass
//SamplerBloom1 is result of first pass
float4 PS_BloomTexture2(VS_OUTPUT_POST In) : COLOR
{
float BloomRadius2 =lerp( lerp( BloomRadius2_Day, BloomRadius2_Night, 1 - ENightDayFactor ), BloomRadius2_Interior, EInteriorFactor);
float BloomMultiplier_SecondPass=lerp( lerp( BloomMultiplier_SecondPass_Day, BloomMultiplier_SecondPass_Night, 1 - ENightDayFactor ), BloomMultiplier_SecondPass_Interior, EInteriorFactor);
float BloomExposure_SecondPass =lerp( lerp( BloomExposure_SecondPass_Day, BloomExposure_SecondPass_Night, 1 - ENightDayFactor ), BloomExposure_SecondPass_Interior, EInteriorFactor);
	float4 bloomuv;
	float4 bloom = tex2D(SamplerBloom1, In.txcoord0);
	float2 screenfact = TempParameters.z;
	float4 srcbloom = bloom;
	float step = BloomRadius2 * BloomParameters.y;
	float4 rotvec = 0.0;
	
	screenfact.y *= ScreenSize.z;
	screenfact.xy *= step;
	sincos(0.3927, rotvec.x, rotvec.y);
	
	for (int i = 0; i < 8; i++)
	{
		bloomuv.xy = bloomOffset[i];
		bloomuv.xy = reflect(bloomuv.xy, rotvec.xy);///????????
		bloomuv.xy = (bloomuv.xy * screenfact.xy) + In.txcoord0.xy;
		bloom += tex2D(SamplerBloom1, bloomuv.xy) * BloomExposure_SecondPass;	//1.524
	}
	bloom *= BloomMultiplier_SecondPass; 
	float Saturation_SecondPass=lerp( lerp( Saturation_SecondPass_Day, Saturation_SecondPass_Night, 1 - ENightDayFactor ), Saturation_SecondPass_Interior, EInteriorFactor);
float MiddleGrayFactor_SecondPass=lerp( lerp( MiddleGrayFactor_SecondPass_Day, MiddleGrayFactor_SecondPass_Night, 1 - ENightDayFactor ), MiddleGrayFactor_SecondPass_Interior, EInteriorFactor);
	float middlegray=(bloom.r+bloom.g+bloom.b)*MiddleGrayFactor_SecondPass;
	float3 diffcolor=bloom.rgb-middlegray;
	bloom.rgb+=diffcolor*Saturation_SecondPass;
	bloom.rgb=max(bloom.rgb, 0.0); //output must be never negative.
	
	bloom.w = 1.0;
	return bloom;
}

//last pass, mix several bloom textures
//SamplerBloom5 is the result of prepass
//float4 PS_BloomPostPass(float2 vPos : VPOS ) : COLOR
float4 PS_BloomPostPass(VS_OUTPUT_POST In) : COLOR
{
float BloomMultiplier_LastPass=lerp( lerp( BloomMultiplier_LastPass_Day, BloomMultiplier_LastPass_Night, 1 - ENightDayFactor ), BloomMultiplier_LastPass_Interior, EInteriorFactor);
	float4 bloom;
	//v1
	bloom = tex2D(SamplerBloom1, In.txcoord0);
	bloom += tex2D(SamplerBloom2, In.txcoord0);
	bloom += tex2D(SamplerBloom3, In.txcoord0);
	bloom += tex2D(SamplerBloom4, In.txcoord0);
	bloom += tex2D(SamplerBloom7, In.txcoord0);
	bloom += tex2D(SamplerBloom8, In.txcoord0);
	bloom += tex2D(SamplerBloom5, In.txcoord0);
//	bloom += tex2D(SamplerBloom6, In.txcoord0);
	bloom *= BloomMultiplier_LastPass;

	float Saturation_LastPass=lerp( lerp( Saturation_LastPass_Day, Saturation_LastPass_Night, 1 - ENightDayFactor ), Saturation_LastPass_Interior, EInteriorFactor);
float MiddleGrayFactor_LastPass=lerp( lerp( MiddleGrayFactor_LastPass_Day, MiddleGrayFactor_LastPass_Night, 1 - ENightDayFactor ), MiddleGrayFactor_LastPass_Interior, EInteriorFactor);
	float middlegray=(bloom.r+bloom.g+bloom.b)*MiddleGrayFactor_LastPass;
	float3 diffcolor=bloom.rgb-middlegray;
	bloom.rgb+=diffcolor*Saturation_LastPass;
	bloom.rgb=max(bloom.rgb, 0.0); //output must be never negative.

#if (USE_BLOOM_CONTRAST == 1)
/**
 *	D-N-I
 */
float BloomContrast=lerp( lerp( BloomContrast_Day, BloomContrast_Night, 1 - ENightDayFactor ), BloomContrast_Interior, EInteriorFactor);

	float TBloomContrast= BloomContrast;	//KYO : Set above
	float maxb=max(bloom.x, max(bloom.y, bloom.z));
	float tempnorb=(maxb/(1.0+maxb));
	tempnorb=pow(tempnorb, TBloomContrast);
	bloom.xyz*=tempnorb;
#endif

	return bloom;
}

//---------------------------------------------------------------------------------

technique BloomPrePass
{
    pass p0
    {
		VertexShader = compile vs_3_0 VS_Bloom();
		PixelShader  = compile ps_3_0 PS_BloomPrePass();

		ColorWriteEnable = ALPHA|RED|GREEN|BLUE;
		CullMode = NONE;
		AlphaBlendEnable = FALSE;
		AlphaTestEnable = FALSE;
		SEPARATEALPHABLENDENABLE = FALSE;
		FogEnable = FALSE;
		SRGBWRITEENABLE = FALSE;
	}
}

technique BloomTexture1
{
    pass p0
    {
		VertexShader = compile vs_3_0 VS_Bloom();
		PixelShader  = compile ps_3_0 PS_BloomTexture1();

		ColorWriteEnable = ALPHA|RED|GREEN|BLUE;
		CullMode = NONE;
		AlphaBlendEnable = FALSE;
		AlphaTestEnable = FALSE;
		SEPARATEALPHABLENDENABLE = FALSE;
		FogEnable = FALSE;
		SRGBWRITEENABLE = FALSE;
	}
}


technique BloomTexture2
{
    pass p0
    {
		VertexShader = compile vs_3_0 VS_Bloom();
		PixelShader  = compile ps_3_0 PS_BloomTexture2();

		ColorWriteEnable = ALPHA|RED|GREEN|BLUE;
		CullMode = NONE;
		AlphaBlendEnable = FALSE;
		AlphaTestEnable = FALSE;
		SEPARATEALPHABLENDENABLE = FALSE;
		FogEnable = FALSE;
		SRGBWRITEENABLE = FALSE;
	}
}

technique BloomPostPass
{
    pass p0
    {
		VertexShader = compile vs_3_0 VS_Bloom();
		PixelShader  = compile ps_3_0 PS_BloomPostPass();

		ColorWriteEnable = ALPHA|RED|GREEN|BLUE;
		CullMode = NONE;
		AlphaBlendEnable = FALSE;
		AlphaTestEnable = FALSE;
		SEPARATEALPHABLENDENABLE = FALSE;
		FogEnable = FALSE;
		SRGBWRITEENABLE = FALSE;
	}
	
#if (USE_PRIMARY_ANAMFLARE == 1)
	pass p1
	{
		AlphaBlendEnable = true;
		SrcBlend = One;
		DestBlend = One;
			
		PixelShader = compile ps_3_0 PS_ProcessPass_Anamorphic_Primary(lerp( lerp( fFlareAxis_Day, fFlareAxis_Night, 1 - ENightDayFactor ), fFlareAxis_Interior, EInteriorFactor));
	}
#endif

#if (USE_SECONDARY_ANAMFLARE == 1)
	pass p2
	{
		AlphaBlendEnable = true;
		SrcBlend = One;
		DestBlend = One;
			
PixelShader = compile ps_3_0 PS_ProcessPass_Anamorphic_Secondary(lerp( lerp( fFlareAxis_Secondary_Day, fFlareAxis_Secondary_Night, 1 - ENightDayFactor ), fFlareAxis_Secondary_Interior, EInteriorFactor));
	}
#endif
}