initial commit
This commit is contained in:
5
lib/renderers/shaders/ShaderChunk/alphamap_fragment.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/alphamap_fragment.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_ALPHAMAP
|
||||
|
||||
diffuseColor.a *= texture2D( alphaMap, vUv ).g;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef USE_ALPHAMAP
|
||||
|
||||
uniform sampler2D alphaMap;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef ALPHATEST
|
||||
|
||||
if ( diffuseColor.a < ALPHATEST ) discard;
|
||||
|
||||
#endif
|
16
lib/renderers/shaders/ShaderChunk/aomap_fragment.glsl
Normal file
16
lib/renderers/shaders/ShaderChunk/aomap_fragment.glsl
Normal file
@ -0,0 +1,16 @@
|
||||
#ifdef USE_AOMAP
|
||||
|
||||
// reads channel R, compatible with a combined OcclusionRoughnessMetallic (RGB) texture
|
||||
float ambientOcclusion = ( texture2D( aoMap, vUv2 ).r - 1.0 ) * aoMapIntensity + 1.0;
|
||||
|
||||
reflectedLight.indirectDiffuse *= ambientOcclusion;
|
||||
|
||||
#if defined( USE_ENVMAP ) && defined( PHYSICAL )
|
||||
|
||||
float dotNV = saturate( dot( geometry.normal, geometry.viewDir ) );
|
||||
|
||||
reflectedLight.indirectSpecular *= computeSpecularOcclusion( dotNV, ambientOcclusion, material.specularRoughness );
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
@ -0,0 +1,6 @@
|
||||
#ifdef USE_AOMAP
|
||||
|
||||
uniform sampler2D aoMap;
|
||||
uniform float aoMapIntensity;
|
||||
|
||||
#endif
|
2
lib/renderers/shaders/ShaderChunk/begin_vertex.glsl
Normal file
2
lib/renderers/shaders/ShaderChunk/begin_vertex.glsl
Normal file
@ -0,0 +1,2 @@
|
||||
|
||||
vec3 transformed = vec3( position );
|
@ -0,0 +1,2 @@
|
||||
|
||||
vec3 objectNormal = vec3( normal );
|
295
lib/renderers/shaders/ShaderChunk/bsdfs.glsl
Normal file
295
lib/renderers/shaders/ShaderChunk/bsdfs.glsl
Normal file
@ -0,0 +1,295 @@
|
||||
float punctualLightIntensityToIrradianceFactor( const in float lightDistance, const in float cutoffDistance, const in float decayExponent ) {
|
||||
|
||||
#if defined ( PHYSICALLY_CORRECT_LIGHTS )
|
||||
|
||||
// based upon Frostbite 3 Moving to Physically-based Rendering
|
||||
// page 32, equation 26: E[window1]
|
||||
// https://seblagarde.files.wordpress.com/2015/07/course_notes_moving_frostbite_to_pbr_v32.pdf
|
||||
// this is intended to be used on spot and point lights who are represented as luminous intensity
|
||||
// but who must be converted to luminous irradiance for surface lighting calculation
|
||||
float distanceFalloff = 1.0 / max( pow( lightDistance, decayExponent ), 0.01 );
|
||||
|
||||
if( cutoffDistance > 0.0 ) {
|
||||
|
||||
distanceFalloff *= pow2( saturate( 1.0 - pow4( lightDistance / cutoffDistance ) ) );
|
||||
|
||||
}
|
||||
|
||||
return distanceFalloff;
|
||||
|
||||
#else
|
||||
|
||||
if( cutoffDistance > 0.0 && decayExponent > 0.0 ) {
|
||||
|
||||
return pow( saturate( -lightDistance / cutoffDistance + 1.0 ), decayExponent );
|
||||
|
||||
}
|
||||
|
||||
return 1.0;
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
vec3 BRDF_Diffuse_Lambert( const in vec3 diffuseColor ) {
|
||||
|
||||
return RECIPROCAL_PI * diffuseColor;
|
||||
|
||||
} // validated
|
||||
|
||||
vec3 F_Schlick( const in vec3 specularColor, const in float dotLH ) {
|
||||
|
||||
// Original approximation by Christophe Schlick '94
|
||||
// float fresnel = pow( 1.0 - dotLH, 5.0 );
|
||||
|
||||
// Optimized variant (presented by Epic at SIGGRAPH '13)
|
||||
// https://cdn2.unrealengine.com/Resources/files/2013SiggraphPresentationsNotes-26915738.pdf
|
||||
float fresnel = exp2( ( -5.55473 * dotLH - 6.98316 ) * dotLH );
|
||||
|
||||
return ( 1.0 - specularColor ) * fresnel + specularColor;
|
||||
|
||||
} // validated
|
||||
|
||||
// Microfacet Models for Refraction through Rough Surfaces - equation (34)
|
||||
// http://graphicrants.blogspot.com/2013/08/specular-brdf-reference.html
|
||||
// alpha is "roughness squared" in Disney’s reparameterization
|
||||
float G_GGX_Smith( const in float alpha, const in float dotNL, const in float dotNV ) {
|
||||
|
||||
// geometry term (normalized) = G(l)⋅G(v) / 4(n⋅l)(n⋅v)
|
||||
// also see #12151
|
||||
|
||||
float a2 = pow2( alpha );
|
||||
|
||||
float gl = dotNL + sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNL ) );
|
||||
float gv = dotNV + sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNV ) );
|
||||
|
||||
return 1.0 / ( gl * gv );
|
||||
|
||||
} // validated
|
||||
|
||||
// Moving Frostbite to Physically Based Rendering 3.0 - page 12, listing 2
|
||||
// https://seblagarde.files.wordpress.com/2015/07/course_notes_moving_frostbite_to_pbr_v32.pdf
|
||||
float G_GGX_SmithCorrelated( const in float alpha, const in float dotNL, const in float dotNV ) {
|
||||
|
||||
float a2 = pow2( alpha );
|
||||
|
||||
// dotNL and dotNV are explicitly swapped. This is not a mistake.
|
||||
float gv = dotNL * sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNV ) );
|
||||
float gl = dotNV * sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNL ) );
|
||||
|
||||
return 0.5 / max( gv + gl, EPSILON );
|
||||
|
||||
}
|
||||
|
||||
// Microfacet Models for Refraction through Rough Surfaces - equation (33)
|
||||
// http://graphicrants.blogspot.com/2013/08/specular-brdf-reference.html
|
||||
// alpha is "roughness squared" in Disney’s reparameterization
|
||||
float D_GGX( const in float alpha, const in float dotNH ) {
|
||||
|
||||
float a2 = pow2( alpha );
|
||||
|
||||
float denom = pow2( dotNH ) * ( a2 - 1.0 ) + 1.0; // avoid alpha = 0 with dotNH = 1
|
||||
|
||||
return RECIPROCAL_PI * a2 / pow2( denom );
|
||||
|
||||
}
|
||||
|
||||
// GGX Distribution, Schlick Fresnel, GGX-Smith Visibility
|
||||
vec3 BRDF_Specular_GGX( const in IncidentLight incidentLight, const in GeometricContext geometry, const in vec3 specularColor, const in float roughness ) {
|
||||
|
||||
float alpha = pow2( roughness ); // UE4's roughness
|
||||
|
||||
vec3 halfDir = normalize( incidentLight.direction + geometry.viewDir );
|
||||
|
||||
float dotNL = saturate( dot( geometry.normal, incidentLight.direction ) );
|
||||
float dotNV = saturate( dot( geometry.normal, geometry.viewDir ) );
|
||||
float dotNH = saturate( dot( geometry.normal, halfDir ) );
|
||||
float dotLH = saturate( dot( incidentLight.direction, halfDir ) );
|
||||
|
||||
vec3 F = F_Schlick( specularColor, dotLH );
|
||||
|
||||
float G = G_GGX_SmithCorrelated( alpha, dotNL, dotNV );
|
||||
|
||||
float D = D_GGX( alpha, dotNH );
|
||||
|
||||
return F * ( G * D );
|
||||
|
||||
} // validated
|
||||
|
||||
// Rect Area Light
|
||||
|
||||
// Real-Time Polygonal-Light Shading with Linearly Transformed Cosines
|
||||
// by Eric Heitz, Jonathan Dupuy, Stephen Hill and David Neubelt
|
||||
// code: https://github.com/selfshadow/ltc_code/
|
||||
|
||||
vec2 LTC_Uv( const in vec3 N, const in vec3 V, const in float roughness ) {
|
||||
|
||||
const float LUT_SIZE = 64.0;
|
||||
const float LUT_SCALE = ( LUT_SIZE - 1.0 ) / LUT_SIZE;
|
||||
const float LUT_BIAS = 0.5 / LUT_SIZE;
|
||||
|
||||
float dotNV = saturate( dot( N, V ) );
|
||||
|
||||
// texture parameterized by sqrt( GGX alpha ) and sqrt( 1 - cos( theta ) )
|
||||
vec2 uv = vec2( roughness, sqrt( 1.0 - dotNV ) );
|
||||
|
||||
uv = uv * LUT_SCALE + LUT_BIAS;
|
||||
|
||||
return uv;
|
||||
|
||||
}
|
||||
|
||||
float LTC_ClippedSphereFormFactor( const in vec3 f ) {
|
||||
|
||||
// Real-Time Area Lighting: a Journey from Research to Production (p.102)
|
||||
// An approximation of the form factor of a horizon-clipped rectangle.
|
||||
|
||||
float l = length( f );
|
||||
|
||||
return max( ( l * l + f.z ) / ( l + 1.0 ), 0.0 );
|
||||
|
||||
}
|
||||
|
||||
vec3 LTC_EdgeVectorFormFactor( const in vec3 v1, const in vec3 v2 ) {
|
||||
|
||||
float x = dot( v1, v2 );
|
||||
|
||||
float y = abs( x );
|
||||
|
||||
// rational polynomial approximation to theta / sin( theta ) / 2PI
|
||||
float a = 0.8543985 + ( 0.4965155 + 0.0145206 * y ) * y;
|
||||
float b = 3.4175940 + ( 4.1616724 + y ) * y;
|
||||
float v = a / b;
|
||||
|
||||
float theta_sintheta = ( x > 0.0 ) ? v : 0.5 * inversesqrt( max( 1.0 - x * x, 1e-7 ) ) - v;
|
||||
|
||||
return cross( v1, v2 ) * theta_sintheta;
|
||||
|
||||
}
|
||||
|
||||
vec3 LTC_Evaluate( const in vec3 N, const in vec3 V, const in vec3 P, const in mat3 mInv, const in vec3 rectCoords[ 4 ] ) {
|
||||
|
||||
// bail if point is on back side of plane of light
|
||||
// assumes ccw winding order of light vertices
|
||||
vec3 v1 = rectCoords[ 1 ] - rectCoords[ 0 ];
|
||||
vec3 v2 = rectCoords[ 3 ] - rectCoords[ 0 ];
|
||||
vec3 lightNormal = cross( v1, v2 );
|
||||
|
||||
if( dot( lightNormal, P - rectCoords[ 0 ] ) < 0.0 ) return vec3( 0.0 );
|
||||
|
||||
// construct orthonormal basis around N
|
||||
vec3 T1, T2;
|
||||
T1 = normalize( V - N * dot( V, N ) );
|
||||
T2 = - cross( N, T1 ); // negated from paper; possibly due to a different handedness of world coordinate system
|
||||
|
||||
// compute transform
|
||||
mat3 mat = mInv * transposeMat3( mat3( T1, T2, N ) );
|
||||
|
||||
// transform rect
|
||||
vec3 coords[ 4 ];
|
||||
coords[ 0 ] = mat * ( rectCoords[ 0 ] - P );
|
||||
coords[ 1 ] = mat * ( rectCoords[ 1 ] - P );
|
||||
coords[ 2 ] = mat * ( rectCoords[ 2 ] - P );
|
||||
coords[ 3 ] = mat * ( rectCoords[ 3 ] - P );
|
||||
|
||||
// project rect onto sphere
|
||||
coords[ 0 ] = normalize( coords[ 0 ] );
|
||||
coords[ 1 ] = normalize( coords[ 1 ] );
|
||||
coords[ 2 ] = normalize( coords[ 2 ] );
|
||||
coords[ 3 ] = normalize( coords[ 3 ] );
|
||||
|
||||
// calculate vector form factor
|
||||
vec3 vectorFormFactor = vec3( 0.0 );
|
||||
vectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 0 ], coords[ 1 ] );
|
||||
vectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 1 ], coords[ 2 ] );
|
||||
vectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 2 ], coords[ 3 ] );
|
||||
vectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 3 ], coords[ 0 ] );
|
||||
|
||||
// adjust for horizon clipping
|
||||
float result = LTC_ClippedSphereFormFactor( vectorFormFactor );
|
||||
|
||||
/*
|
||||
// alternate method of adjusting for horizon clipping (see referece)
|
||||
// refactoring required
|
||||
float len = length( vectorFormFactor );
|
||||
float z = vectorFormFactor.z / len;
|
||||
|
||||
const float LUT_SIZE = 64.0;
|
||||
const float LUT_SCALE = ( LUT_SIZE - 1.0 ) / LUT_SIZE;
|
||||
const float LUT_BIAS = 0.5 / LUT_SIZE;
|
||||
|
||||
// tabulated horizon-clipped sphere, apparently...
|
||||
vec2 uv = vec2( z * 0.5 + 0.5, len );
|
||||
uv = uv * LUT_SCALE + LUT_BIAS;
|
||||
|
||||
float scale = texture2D( ltc_2, uv ).w;
|
||||
|
||||
float result = len * scale;
|
||||
*/
|
||||
|
||||
return vec3( result );
|
||||
|
||||
}
|
||||
|
||||
// End Rect Area Light
|
||||
|
||||
// ref: https://www.unrealengine.com/blog/physically-based-shading-on-mobile - environmentBRDF for GGX on mobile
|
||||
vec3 BRDF_Specular_GGX_Environment( const in GeometricContext geometry, const in vec3 specularColor, const in float roughness ) {
|
||||
|
||||
float dotNV = saturate( dot( geometry.normal, geometry.viewDir ) );
|
||||
|
||||
const vec4 c0 = vec4( - 1, - 0.0275, - 0.572, 0.022 );
|
||||
|
||||
const vec4 c1 = vec4( 1, 0.0425, 1.04, - 0.04 );
|
||||
|
||||
vec4 r = roughness * c0 + c1;
|
||||
|
||||
float a004 = min( r.x * r.x, exp2( - 9.28 * dotNV ) ) * r.x + r.y;
|
||||
|
||||
vec2 AB = vec2( -1.04, 1.04 ) * a004 + r.zw;
|
||||
|
||||
return specularColor * AB.x + AB.y;
|
||||
|
||||
} // validated
|
||||
|
||||
|
||||
float G_BlinnPhong_Implicit( /* const in float dotNL, const in float dotNV */ ) {
|
||||
|
||||
// geometry term is (n dot l)(n dot v) / 4(n dot l)(n dot v)
|
||||
return 0.25;
|
||||
|
||||
}
|
||||
|
||||
float D_BlinnPhong( const in float shininess, const in float dotNH ) {
|
||||
|
||||
return RECIPROCAL_PI * ( shininess * 0.5 + 1.0 ) * pow( dotNH, shininess );
|
||||
|
||||
}
|
||||
|
||||
vec3 BRDF_Specular_BlinnPhong( const in IncidentLight incidentLight, const in GeometricContext geometry, const in vec3 specularColor, const in float shininess ) {
|
||||
|
||||
vec3 halfDir = normalize( incidentLight.direction + geometry.viewDir );
|
||||
|
||||
//float dotNL = saturate( dot( geometry.normal, incidentLight.direction ) );
|
||||
//float dotNV = saturate( dot( geometry.normal, geometry.viewDir ) );
|
||||
float dotNH = saturate( dot( geometry.normal, halfDir ) );
|
||||
float dotLH = saturate( dot( incidentLight.direction, halfDir ) );
|
||||
|
||||
vec3 F = F_Schlick( specularColor, dotLH );
|
||||
|
||||
float G = G_BlinnPhong_Implicit( /* dotNL, dotNV */ );
|
||||
|
||||
float D = D_BlinnPhong( shininess, dotNH );
|
||||
|
||||
return F * ( G * D );
|
||||
|
||||
} // validated
|
||||
|
||||
// source: http://simonstechblog.blogspot.ca/2011/12/microfacet-brdf.html
|
||||
float GGXRoughnessToBlinnExponent( const in float ggxRoughness ) {
|
||||
return ( 2.0 / pow2( ggxRoughness + 0.0001 ) - 2.0 );
|
||||
}
|
||||
|
||||
float BlinnExponentToGGXRoughness( const in float blinnExponent ) {
|
||||
return sqrt( 2.0 / ( blinnExponent + 2.0 ) );
|
||||
}
|
44
lib/renderers/shaders/ShaderChunk/bumpmap_pars_fragment.glsl
Normal file
44
lib/renderers/shaders/ShaderChunk/bumpmap_pars_fragment.glsl
Normal file
@ -0,0 +1,44 @@
|
||||
#ifdef USE_BUMPMAP
|
||||
|
||||
uniform sampler2D bumpMap;
|
||||
uniform float bumpScale;
|
||||
|
||||
// Bump Mapping Unparametrized Surfaces on the GPU by Morten S. Mikkelsen
|
||||
// http://api.unrealengine.com/attachments/Engine/Rendering/LightingAndShadows/BumpMappingWithoutTangentSpace/mm_sfgrad_bump.pdf
|
||||
|
||||
// Evaluate the derivative of the height w.r.t. screen-space using forward differencing (listing 2)
|
||||
|
||||
vec2 dHdxy_fwd() {
|
||||
|
||||
vec2 dSTdx = dFdx( vUv );
|
||||
vec2 dSTdy = dFdy( vUv );
|
||||
|
||||
float Hll = bumpScale * texture2D( bumpMap, vUv ).x;
|
||||
float dBx = bumpScale * texture2D( bumpMap, vUv + dSTdx ).x - Hll;
|
||||
float dBy = bumpScale * texture2D( bumpMap, vUv + dSTdy ).x - Hll;
|
||||
|
||||
return vec2( dBx, dBy );
|
||||
|
||||
}
|
||||
|
||||
vec3 perturbNormalArb( vec3 surf_pos, vec3 surf_norm, vec2 dHdxy ) {
|
||||
|
||||
// Workaround for Adreno 3XX dFd*( vec3 ) bug. See #9988
|
||||
|
||||
vec3 vSigmaX = vec3( dFdx( surf_pos.x ), dFdx( surf_pos.y ), dFdx( surf_pos.z ) );
|
||||
vec3 vSigmaY = vec3( dFdy( surf_pos.x ), dFdy( surf_pos.y ), dFdy( surf_pos.z ) );
|
||||
vec3 vN = surf_norm; // normalized
|
||||
|
||||
vec3 R1 = cross( vSigmaY, vN );
|
||||
vec3 R2 = cross( vN, vSigmaX );
|
||||
|
||||
float fDet = dot( vSigmaX, R1 );
|
||||
|
||||
fDet *= ( float( gl_FrontFacing ) * 2.0 - 1.0 );
|
||||
|
||||
vec3 vGrad = sign( fDet ) * ( dHdxy.x * R1 + dHdxy.y * R2 );
|
||||
return normalize( abs( fDet ) * surf_norm - vGrad );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
@ -0,0 +1,29 @@
|
||||
#if NUM_CLIPPING_PLANES > 0
|
||||
|
||||
vec4 plane;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < UNION_CLIPPING_PLANES; i ++ ) {
|
||||
|
||||
plane = clippingPlanes[ i ];
|
||||
if ( dot( vViewPosition, plane.xyz ) > plane.w ) discard;
|
||||
|
||||
}
|
||||
|
||||
#if UNION_CLIPPING_PLANES < NUM_CLIPPING_PLANES
|
||||
|
||||
bool clipped = true;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = UNION_CLIPPING_PLANES; i < NUM_CLIPPING_PLANES; i ++ ) {
|
||||
|
||||
plane = clippingPlanes[ i ];
|
||||
clipped = ( dot( vViewPosition, plane.xyz ) > plane.w ) && clipped;
|
||||
|
||||
}
|
||||
|
||||
if ( clipped ) discard;
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
@ -0,0 +1,9 @@
|
||||
#if NUM_CLIPPING_PLANES > 0
|
||||
|
||||
#if ! defined( PHYSICAL ) && ! defined( PHONG ) && ! defined( MATCAP )
|
||||
varying vec3 vViewPosition;
|
||||
#endif
|
||||
|
||||
uniform vec4 clippingPlanes[ NUM_CLIPPING_PLANES ];
|
||||
|
||||
#endif
|
@ -0,0 +1,3 @@
|
||||
#if NUM_CLIPPING_PLANES > 0 && ! defined( PHYSICAL ) && ! defined( PHONG ) && ! defined( MATCAP )
|
||||
varying vec3 vViewPosition;
|
||||
#endif
|
@ -0,0 +1,4 @@
|
||||
#if NUM_CLIPPING_PLANES > 0 && ! defined( PHYSICAL ) && ! defined( PHONG ) && ! defined( MATCAP )
|
||||
vViewPosition = - mvPosition.xyz;
|
||||
#endif
|
||||
|
5
lib/renderers/shaders/ShaderChunk/color_fragment.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/color_fragment.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_COLOR
|
||||
|
||||
diffuseColor.rgb *= vColor;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef USE_COLOR
|
||||
|
||||
varying vec3 vColor;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/color_pars_vertex.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/color_pars_vertex.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_COLOR
|
||||
|
||||
varying vec3 vColor;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/color_vertex.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/color_vertex.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_COLOR
|
||||
|
||||
vColor.xyz = color.xyz;
|
||||
|
||||
#endif
|
95
lib/renderers/shaders/ShaderChunk/common.glsl
Normal file
95
lib/renderers/shaders/ShaderChunk/common.glsl
Normal file
@ -0,0 +1,95 @@
|
||||
#define PI 3.14159265359
|
||||
#define PI2 6.28318530718
|
||||
#define PI_HALF 1.5707963267949
|
||||
#define RECIPROCAL_PI 0.31830988618
|
||||
#define RECIPROCAL_PI2 0.15915494
|
||||
#define LOG2 1.442695
|
||||
#define EPSILON 1e-6
|
||||
|
||||
#define saturate(a) clamp( a, 0.0, 1.0 )
|
||||
#define whiteCompliment(a) ( 1.0 - saturate( a ) )
|
||||
|
||||
float pow2( const in float x ) { return x*x; }
|
||||
float pow3( const in float x ) { return x*x*x; }
|
||||
float pow4( const in float x ) { float x2 = x*x; return x2*x2; }
|
||||
float average( const in vec3 color ) { return dot( color, vec3( 0.3333 ) ); }
|
||||
// expects values in the range of [0,1]x[0,1], returns values in the [0,1] range.
|
||||
// do not collapse into a single function per: http://byteblacksmith.com/improvements-to-the-canonical-one-liner-glsl-rand-for-opengl-es-2-0/
|
||||
highp float rand( const in vec2 uv ) {
|
||||
const highp float a = 12.9898, b = 78.233, c = 43758.5453;
|
||||
highp float dt = dot( uv.xy, vec2( a,b ) ), sn = mod( dt, PI );
|
||||
return fract(sin(sn) * c);
|
||||
}
|
||||
|
||||
struct IncidentLight {
|
||||
vec3 color;
|
||||
vec3 direction;
|
||||
bool visible;
|
||||
};
|
||||
|
||||
struct ReflectedLight {
|
||||
vec3 directDiffuse;
|
||||
vec3 directSpecular;
|
||||
vec3 indirectDiffuse;
|
||||
vec3 indirectSpecular;
|
||||
};
|
||||
|
||||
struct GeometricContext {
|
||||
vec3 position;
|
||||
vec3 normal;
|
||||
vec3 viewDir;
|
||||
};
|
||||
|
||||
vec3 transformDirection( in vec3 dir, in mat4 matrix ) {
|
||||
|
||||
return normalize( ( matrix * vec4( dir, 0.0 ) ).xyz );
|
||||
|
||||
}
|
||||
|
||||
// http://en.wikibooks.org/wiki/GLSL_Programming/Applying_Matrix_Transformations
|
||||
vec3 inverseTransformDirection( in vec3 dir, in mat4 matrix ) {
|
||||
|
||||
return normalize( ( vec4( dir, 0.0 ) * matrix ).xyz );
|
||||
|
||||
}
|
||||
|
||||
vec3 projectOnPlane(in vec3 point, in vec3 pointOnPlane, in vec3 planeNormal ) {
|
||||
|
||||
float distance = dot( planeNormal, point - pointOnPlane );
|
||||
|
||||
return - distance * planeNormal + point;
|
||||
|
||||
}
|
||||
|
||||
float sideOfPlane( in vec3 point, in vec3 pointOnPlane, in vec3 planeNormal ) {
|
||||
|
||||
return sign( dot( point - pointOnPlane, planeNormal ) );
|
||||
|
||||
}
|
||||
|
||||
vec3 linePlaneIntersect( in vec3 pointOnLine, in vec3 lineDirection, in vec3 pointOnPlane, in vec3 planeNormal ) {
|
||||
|
||||
return lineDirection * ( dot( planeNormal, pointOnPlane - pointOnLine ) / dot( planeNormal, lineDirection ) ) + pointOnLine;
|
||||
|
||||
}
|
||||
|
||||
mat3 transposeMat3( const in mat3 m ) {
|
||||
|
||||
mat3 tmp;
|
||||
|
||||
tmp[ 0 ] = vec3( m[ 0 ].x, m[ 1 ].x, m[ 2 ].x );
|
||||
tmp[ 1 ] = vec3( m[ 0 ].y, m[ 1 ].y, m[ 2 ].y );
|
||||
tmp[ 2 ] = vec3( m[ 0 ].z, m[ 1 ].z, m[ 2 ].z );
|
||||
|
||||
return tmp;
|
||||
|
||||
}
|
||||
|
||||
// https://en.wikipedia.org/wiki/Relative_luminance
|
||||
float linearToRelativeLuminance( const in vec3 color ) {
|
||||
|
||||
vec3 weights = vec3( 0.2126, 0.7152, 0.0722 );
|
||||
|
||||
return dot( weights, color.rgb );
|
||||
|
||||
}
|
@ -0,0 +1,128 @@
|
||||
#ifdef ENVMAP_TYPE_CUBE_UV
|
||||
|
||||
#define cubeUV_textureSize (1024.0)
|
||||
|
||||
int getFaceFromDirection(vec3 direction) {
|
||||
vec3 absDirection = abs(direction);
|
||||
int face = -1;
|
||||
if( absDirection.x > absDirection.z ) {
|
||||
if(absDirection.x > absDirection.y )
|
||||
face = direction.x > 0.0 ? 0 : 3;
|
||||
else
|
||||
face = direction.y > 0.0 ? 1 : 4;
|
||||
}
|
||||
else {
|
||||
if(absDirection.z > absDirection.y )
|
||||
face = direction.z > 0.0 ? 2 : 5;
|
||||
else
|
||||
face = direction.y > 0.0 ? 1 : 4;
|
||||
}
|
||||
return face;
|
||||
}
|
||||
#define cubeUV_maxLods1 (log2(cubeUV_textureSize*0.25) - 1.0)
|
||||
#define cubeUV_rangeClamp (exp2((6.0 - 1.0) * 2.0))
|
||||
|
||||
vec2 MipLevelInfo( vec3 vec, float roughnessLevel, float roughness ) {
|
||||
float scale = exp2(cubeUV_maxLods1 - roughnessLevel);
|
||||
float dxRoughness = dFdx(roughness);
|
||||
float dyRoughness = dFdy(roughness);
|
||||
vec3 dx = dFdx( vec * scale * dxRoughness );
|
||||
vec3 dy = dFdy( vec * scale * dyRoughness );
|
||||
float d = max( dot( dx, dx ), dot( dy, dy ) );
|
||||
// Clamp the value to the max mip level counts. hard coded to 6 mips
|
||||
d = clamp(d, 1.0, cubeUV_rangeClamp);
|
||||
float mipLevel = 0.5 * log2(d);
|
||||
return vec2(floor(mipLevel), fract(mipLevel));
|
||||
}
|
||||
|
||||
#define cubeUV_maxLods2 (log2(cubeUV_textureSize*0.25) - 2.0)
|
||||
#define cubeUV_rcpTextureSize (1.0 / cubeUV_textureSize)
|
||||
|
||||
vec2 getCubeUV(vec3 direction, float roughnessLevel, float mipLevel) {
|
||||
mipLevel = roughnessLevel > cubeUV_maxLods2 - 3.0 ? 0.0 : mipLevel;
|
||||
float a = 16.0 * cubeUV_rcpTextureSize;
|
||||
|
||||
vec2 exp2_packed = exp2( vec2( roughnessLevel, mipLevel ) );
|
||||
vec2 rcp_exp2_packed = vec2( 1.0 ) / exp2_packed;
|
||||
// float powScale = exp2(roughnessLevel + mipLevel);
|
||||
float powScale = exp2_packed.x * exp2_packed.y;
|
||||
// float scale = 1.0 / exp2(roughnessLevel + 2.0 + mipLevel);
|
||||
float scale = rcp_exp2_packed.x * rcp_exp2_packed.y * 0.25;
|
||||
// float mipOffset = 0.75*(1.0 - 1.0/exp2(mipLevel))/exp2(roughnessLevel);
|
||||
float mipOffset = 0.75*(1.0 - rcp_exp2_packed.y) * rcp_exp2_packed.x;
|
||||
|
||||
bool bRes = mipLevel == 0.0;
|
||||
scale = bRes && (scale < a) ? a : scale;
|
||||
|
||||
vec3 r;
|
||||
vec2 offset;
|
||||
int face = getFaceFromDirection(direction);
|
||||
|
||||
float rcpPowScale = 1.0 / powScale;
|
||||
|
||||
if( face == 0) {
|
||||
r = vec3(direction.x, -direction.z, direction.y);
|
||||
offset = vec2(0.0+mipOffset,0.75 * rcpPowScale);
|
||||
offset.y = bRes && (offset.y < 2.0*a) ? a : offset.y;
|
||||
}
|
||||
else if( face == 1) {
|
||||
r = vec3(direction.y, direction.x, direction.z);
|
||||
offset = vec2(scale+mipOffset, 0.75 * rcpPowScale);
|
||||
offset.y = bRes && (offset.y < 2.0*a) ? a : offset.y;
|
||||
}
|
||||
else if( face == 2) {
|
||||
r = vec3(direction.z, direction.x, direction.y);
|
||||
offset = vec2(2.0*scale+mipOffset, 0.75 * rcpPowScale);
|
||||
offset.y = bRes && (offset.y < 2.0*a) ? a : offset.y;
|
||||
}
|
||||
else if( face == 3) {
|
||||
r = vec3(direction.x, direction.z, direction.y);
|
||||
offset = vec2(0.0+mipOffset,0.5 * rcpPowScale);
|
||||
offset.y = bRes && (offset.y < 2.0*a) ? 0.0 : offset.y;
|
||||
}
|
||||
else if( face == 4) {
|
||||
r = vec3(direction.y, direction.x, -direction.z);
|
||||
offset = vec2(scale+mipOffset, 0.5 * rcpPowScale);
|
||||
offset.y = bRes && (offset.y < 2.0*a) ? 0.0 : offset.y;
|
||||
}
|
||||
else {
|
||||
r = vec3(direction.z, -direction.x, direction.y);
|
||||
offset = vec2(2.0*scale+mipOffset, 0.5 * rcpPowScale);
|
||||
offset.y = bRes && (offset.y < 2.0*a) ? 0.0 : offset.y;
|
||||
}
|
||||
r = normalize(r);
|
||||
float texelOffset = 0.5 * cubeUV_rcpTextureSize;
|
||||
vec2 s = ( r.yz / abs( r.x ) + vec2( 1.0 ) ) * 0.5;
|
||||
vec2 base = offset + vec2( texelOffset );
|
||||
return base + s * ( scale - 2.0 * texelOffset );
|
||||
}
|
||||
|
||||
#define cubeUV_maxLods3 (log2(cubeUV_textureSize*0.25) - 3.0)
|
||||
|
||||
vec4 textureCubeUV( sampler2D envMap, vec3 reflectedDirection, float roughness ) {
|
||||
float roughnessVal = roughness* cubeUV_maxLods3;
|
||||
float r1 = floor(roughnessVal);
|
||||
float r2 = r1 + 1.0;
|
||||
float t = fract(roughnessVal);
|
||||
vec2 mipInfo = MipLevelInfo(reflectedDirection, r1, roughness);
|
||||
float s = mipInfo.y;
|
||||
float level0 = mipInfo.x;
|
||||
float level1 = level0 + 1.0;
|
||||
level1 = level1 > 5.0 ? 5.0 : level1;
|
||||
|
||||
// round to nearest mipmap if we are not interpolating.
|
||||
level0 += min( floor( s + 0.5 ), 5.0 );
|
||||
|
||||
// Tri linear interpolation.
|
||||
vec2 uv_10 = getCubeUV(reflectedDirection, r1, level0);
|
||||
vec4 color10 = envMapTexelToLinear(texture2D(envMap, uv_10));
|
||||
|
||||
vec2 uv_20 = getCubeUV(reflectedDirection, r2, level0);
|
||||
vec4 color20 = envMapTexelToLinear(texture2D(envMap, uv_20));
|
||||
|
||||
vec4 result = mix(color10, color20, t);
|
||||
|
||||
return vec4(result.rgb, 1.0);
|
||||
}
|
||||
|
||||
#endif
|
@ -0,0 +1,7 @@
|
||||
vec3 transformedNormal = normalMatrix * objectNormal;
|
||||
|
||||
#ifdef FLIP_SIDED
|
||||
|
||||
transformedNormal = - transformedNormal;
|
||||
|
||||
#endif
|
@ -0,0 +1,7 @@
|
||||
#ifdef USE_DISPLACEMENTMAP
|
||||
|
||||
uniform sampler2D displacementMap;
|
||||
uniform float displacementScale;
|
||||
uniform float displacementBias;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef USE_DISPLACEMENTMAP
|
||||
|
||||
transformed += normalize( objectNormal ) * ( texture2D( displacementMap, uv ).x * displacementScale + displacementBias );
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#if defined( DITHERING )
|
||||
|
||||
gl_FragColor.rgb = dithering( gl_FragColor.rgb );
|
||||
|
||||
#endif
|
@ -0,0 +1,18 @@
|
||||
#if defined( DITHERING )
|
||||
|
||||
// based on https://www.shadertoy.com/view/MslGR8
|
||||
vec3 dithering( vec3 color ) {
|
||||
//Calculate grid position
|
||||
float grid_position = rand( gl_FragCoord.xy );
|
||||
|
||||
//Shift the individual colors differently, thus making it even harder to see the dithering pattern
|
||||
vec3 dither_shift_RGB = vec3( 0.25 / 255.0, -0.25 / 255.0, 0.25 / 255.0 );
|
||||
|
||||
//modify shift acording to grid position.
|
||||
dither_shift_RGB = mix( 2.0 * dither_shift_RGB, -2.0 * dither_shift_RGB, grid_position );
|
||||
|
||||
//shift the color by dither_shift
|
||||
return color + dither_shift_RGB;
|
||||
}
|
||||
|
||||
#endif
|
@ -0,0 +1,9 @@
|
||||
#ifdef USE_EMISSIVEMAP
|
||||
|
||||
vec4 emissiveColor = texture2D( emissiveMap, vUv );
|
||||
|
||||
emissiveColor.rgb = emissiveMapTexelToLinear( emissiveColor ).rgb;
|
||||
|
||||
totalEmissiveRadiance *= emissiveColor.rgb;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef USE_EMISSIVEMAP
|
||||
|
||||
uniform sampler2D emissiveMap;
|
||||
|
||||
#endif
|
@ -0,0 +1 @@
|
||||
gl_FragColor = linearToOutputTexel( gl_FragColor );
|
@ -0,0 +1,83 @@
|
||||
// For a discussion of what this is, please read this: http://lousodrome.net/blog/light/2013/05/26/gamma-correct-and-hdr-rendering-in-a-32-bits-buffer/
|
||||
|
||||
vec4 LinearToLinear( in vec4 value ) {
|
||||
return value;
|
||||
}
|
||||
|
||||
vec4 GammaToLinear( in vec4 value, in float gammaFactor ) {
|
||||
return vec4( pow( value.rgb, vec3( gammaFactor ) ), value.a );
|
||||
}
|
||||
|
||||
vec4 LinearToGamma( in vec4 value, in float gammaFactor ) {
|
||||
return vec4( pow( value.rgb, vec3( 1.0 / gammaFactor ) ), value.a );
|
||||
}
|
||||
|
||||
vec4 sRGBToLinear( in vec4 value ) {
|
||||
return vec4( mix( pow( value.rgb * 0.9478672986 + vec3( 0.0521327014 ), vec3( 2.4 ) ), value.rgb * 0.0773993808, vec3( lessThanEqual( value.rgb, vec3( 0.04045 ) ) ) ), value.a );
|
||||
}
|
||||
|
||||
vec4 LinearTosRGB( in vec4 value ) {
|
||||
return vec4( mix( pow( value.rgb, vec3( 0.41666 ) ) * 1.055 - vec3( 0.055 ), value.rgb * 12.92, vec3( lessThanEqual( value.rgb, vec3( 0.0031308 ) ) ) ), value.a );
|
||||
}
|
||||
|
||||
vec4 RGBEToLinear( in vec4 value ) {
|
||||
return vec4( value.rgb * exp2( value.a * 255.0 - 128.0 ), 1.0 );
|
||||
}
|
||||
|
||||
vec4 LinearToRGBE( in vec4 value ) {
|
||||
float maxComponent = max( max( value.r, value.g ), value.b );
|
||||
float fExp = clamp( ceil( log2( maxComponent ) ), -128.0, 127.0 );
|
||||
return vec4( value.rgb / exp2( fExp ), ( fExp + 128.0 ) / 255.0 );
|
||||
// return vec4( value.brg, ( 3.0 + 128.0 ) / 256.0 );
|
||||
}
|
||||
|
||||
// reference: http://iwasbeingirony.blogspot.ca/2010/06/difference-between-rgbm-and-rgbd.html
|
||||
vec4 RGBMToLinear( in vec4 value, in float maxRange ) {
|
||||
return vec4( value.rgb * value.a * maxRange, 1.0 );
|
||||
}
|
||||
|
||||
vec4 LinearToRGBM( in vec4 value, in float maxRange ) {
|
||||
float maxRGB = max( value.r, max( value.g, value.b ) );
|
||||
float M = clamp( maxRGB / maxRange, 0.0, 1.0 );
|
||||
M = ceil( M * 255.0 ) / 255.0;
|
||||
return vec4( value.rgb / ( M * maxRange ), M );
|
||||
}
|
||||
|
||||
// reference: http://iwasbeingirony.blogspot.ca/2010/06/difference-between-rgbm-and-rgbd.html
|
||||
vec4 RGBDToLinear( in vec4 value, in float maxRange ) {
|
||||
return vec4( value.rgb * ( ( maxRange / 255.0 ) / value.a ), 1.0 );
|
||||
}
|
||||
|
||||
vec4 LinearToRGBD( in vec4 value, in float maxRange ) {
|
||||
float maxRGB = max( value.r, max( value.g, value.b ) );
|
||||
float D = max( maxRange / maxRGB, 1.0 );
|
||||
D = min( floor( D ) / 255.0, 1.0 );
|
||||
return vec4( value.rgb * ( D * ( 255.0 / maxRange ) ), D );
|
||||
}
|
||||
|
||||
// LogLuv reference: http://graphicrants.blogspot.ca/2009/04/rgbm-color-encoding.html
|
||||
|
||||
// M matrix, for encoding
|
||||
const mat3 cLogLuvM = mat3( 0.2209, 0.3390, 0.4184, 0.1138, 0.6780, 0.7319, 0.0102, 0.1130, 0.2969 );
|
||||
vec4 LinearToLogLuv( in vec4 value ) {
|
||||
vec3 Xp_Y_XYZp = value.rgb * cLogLuvM;
|
||||
Xp_Y_XYZp = max( Xp_Y_XYZp, vec3( 1e-6, 1e-6, 1e-6 ) );
|
||||
vec4 vResult;
|
||||
vResult.xy = Xp_Y_XYZp.xy / Xp_Y_XYZp.z;
|
||||
float Le = 2.0 * log2(Xp_Y_XYZp.y) + 127.0;
|
||||
vResult.w = fract( Le );
|
||||
vResult.z = ( Le - ( floor( vResult.w * 255.0 ) ) / 255.0 ) / 255.0;
|
||||
return vResult;
|
||||
}
|
||||
|
||||
// Inverse M matrix, for decoding
|
||||
const mat3 cLogLuvInverseM = mat3( 6.0014, -2.7008, -1.7996, -1.3320, 3.1029, -5.7721, 0.3008, -1.0882, 5.6268 );
|
||||
vec4 LogLuvToLinear( in vec4 value ) {
|
||||
float Le = value.z * 255.0 + value.w;
|
||||
vec3 Xp_Y_XYZp;
|
||||
Xp_Y_XYZp.y = exp2( ( Le - 127.0 ) / 2.0 );
|
||||
Xp_Y_XYZp.z = Xp_Y_XYZp.y / value.y;
|
||||
Xp_Y_XYZp.x = value.x * Xp_Y_XYZp.z;
|
||||
vec3 vRGB = Xp_Y_XYZp.rgb * cLogLuvInverseM;
|
||||
return vec4( max( vRGB, 0.0 ), 1.0 );
|
||||
}
|
72
lib/renderers/shaders/ShaderChunk/envmap_fragment.glsl
Normal file
72
lib/renderers/shaders/ShaderChunk/envmap_fragment.glsl
Normal file
@ -0,0 +1,72 @@
|
||||
#ifdef USE_ENVMAP
|
||||
|
||||
#if defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( PHONG )
|
||||
|
||||
vec3 cameraToVertex = normalize( vWorldPosition - cameraPosition );
|
||||
|
||||
// Transforming Normal Vectors with the Inverse Transformation
|
||||
vec3 worldNormal = inverseTransformDirection( normal, viewMatrix );
|
||||
|
||||
#ifdef ENVMAP_MODE_REFLECTION
|
||||
|
||||
vec3 reflectVec = reflect( cameraToVertex, worldNormal );
|
||||
|
||||
#else
|
||||
|
||||
vec3 reflectVec = refract( cameraToVertex, worldNormal, refractionRatio );
|
||||
|
||||
#endif
|
||||
|
||||
#else
|
||||
|
||||
vec3 reflectVec = vReflect;
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef ENVMAP_TYPE_CUBE
|
||||
|
||||
vec4 envColor = textureCube( envMap, vec3( flipEnvMap * reflectVec.x, reflectVec.yz ) );
|
||||
|
||||
#elif defined( ENVMAP_TYPE_EQUIREC )
|
||||
|
||||
vec2 sampleUV;
|
||||
|
||||
reflectVec = normalize( reflectVec );
|
||||
|
||||
sampleUV.y = asin( clamp( reflectVec.y, - 1.0, 1.0 ) ) * RECIPROCAL_PI + 0.5;
|
||||
|
||||
sampleUV.x = atan( reflectVec.z, reflectVec.x ) * RECIPROCAL_PI2 + 0.5;
|
||||
|
||||
vec4 envColor = texture2D( envMap, sampleUV );
|
||||
|
||||
#elif defined( ENVMAP_TYPE_SPHERE )
|
||||
|
||||
reflectVec = normalize( reflectVec );
|
||||
|
||||
vec3 reflectView = normalize( ( viewMatrix * vec4( reflectVec, 0.0 ) ).xyz + vec3( 0.0, 0.0, 1.0 ) );
|
||||
|
||||
vec4 envColor = texture2D( envMap, reflectView.xy * 0.5 + 0.5 );
|
||||
|
||||
#else
|
||||
|
||||
vec4 envColor = vec4( 0.0 );
|
||||
|
||||
#endif
|
||||
|
||||
envColor = envMapTexelToLinear( envColor );
|
||||
|
||||
#ifdef ENVMAP_BLENDING_MULTIPLY
|
||||
|
||||
outgoingLight = mix( outgoingLight, outgoingLight * envColor.xyz, specularStrength * reflectivity );
|
||||
|
||||
#elif defined( ENVMAP_BLENDING_MIX )
|
||||
|
||||
outgoingLight = mix( outgoingLight, envColor.xyz, specularStrength * reflectivity );
|
||||
|
||||
#elif defined( ENVMAP_BLENDING_ADD )
|
||||
|
||||
outgoingLight += envColor.xyz * specularStrength * reflectivity;
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
26
lib/renderers/shaders/ShaderChunk/envmap_pars_fragment.glsl
Normal file
26
lib/renderers/shaders/ShaderChunk/envmap_pars_fragment.glsl
Normal file
@ -0,0 +1,26 @@
|
||||
#if defined( USE_ENVMAP ) || defined( PHYSICAL )
|
||||
uniform float reflectivity;
|
||||
uniform float envMapIntensity;
|
||||
#endif
|
||||
|
||||
#ifdef USE_ENVMAP
|
||||
|
||||
#if ! defined( PHYSICAL ) && ( defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( PHONG ) )
|
||||
varying vec3 vWorldPosition;
|
||||
#endif
|
||||
|
||||
#ifdef ENVMAP_TYPE_CUBE
|
||||
uniform samplerCube envMap;
|
||||
#else
|
||||
uniform sampler2D envMap;
|
||||
#endif
|
||||
uniform float flipEnvMap;
|
||||
uniform int maxMipLevel;
|
||||
|
||||
#if defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( PHONG ) || defined( PHYSICAL )
|
||||
uniform float refractionRatio;
|
||||
#else
|
||||
varying vec3 vReflect;
|
||||
#endif
|
||||
|
||||
#endif
|
13
lib/renderers/shaders/ShaderChunk/envmap_pars_vertex.glsl
Normal file
13
lib/renderers/shaders/ShaderChunk/envmap_pars_vertex.glsl
Normal file
@ -0,0 +1,13 @@
|
||||
#ifdef USE_ENVMAP
|
||||
|
||||
#if defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( PHONG )
|
||||
varying vec3 vWorldPosition;
|
||||
|
||||
#else
|
||||
|
||||
varying vec3 vReflect;
|
||||
uniform float refractionRatio;
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
@ -0,0 +1,133 @@
|
||||
#if defined( USE_ENVMAP ) && defined( PHYSICAL )
|
||||
|
||||
vec3 getLightProbeIndirectIrradiance( /*const in SpecularLightProbe specularLightProbe,*/ const in GeometricContext geometry, const in int maxMIPLevel ) {
|
||||
|
||||
vec3 worldNormal = inverseTransformDirection( geometry.normal, viewMatrix );
|
||||
|
||||
#ifdef ENVMAP_TYPE_CUBE
|
||||
|
||||
vec3 queryVec = vec3( flipEnvMap * worldNormal.x, worldNormal.yz );
|
||||
|
||||
// TODO: replace with properly filtered cubemaps and access the irradiance LOD level, be it the last LOD level
|
||||
// of a specular cubemap, or just the default level of a specially created irradiance cubemap.
|
||||
|
||||
#ifdef TEXTURE_LOD_EXT
|
||||
|
||||
vec4 envMapColor = textureCubeLodEXT( envMap, queryVec, float( maxMIPLevel ) );
|
||||
|
||||
#else
|
||||
|
||||
// force the bias high to get the last LOD level as it is the most blurred.
|
||||
vec4 envMapColor = textureCube( envMap, queryVec, float( maxMIPLevel ) );
|
||||
|
||||
#endif
|
||||
|
||||
envMapColor.rgb = envMapTexelToLinear( envMapColor ).rgb;
|
||||
|
||||
#elif defined( ENVMAP_TYPE_CUBE_UV )
|
||||
|
||||
vec3 queryVec = vec3( flipEnvMap * worldNormal.x, worldNormal.yz );
|
||||
vec4 envMapColor = textureCubeUV( envMap, queryVec, 1.0 );
|
||||
|
||||
#else
|
||||
|
||||
vec4 envMapColor = vec4( 0.0 );
|
||||
|
||||
#endif
|
||||
|
||||
return PI * envMapColor.rgb * envMapIntensity;
|
||||
|
||||
}
|
||||
|
||||
// taken from here: http://casual-effects.blogspot.ca/2011/08/plausible-environment-lighting-in-two.html
|
||||
float getSpecularMIPLevel( const in float blinnShininessExponent, const in int maxMIPLevel ) {
|
||||
|
||||
//float envMapWidth = pow( 2.0, maxMIPLevelScalar );
|
||||
//float desiredMIPLevel = log2( envMapWidth * sqrt( 3.0 ) ) - 0.5 * log2( pow2( blinnShininessExponent ) + 1.0 );
|
||||
|
||||
float maxMIPLevelScalar = float( maxMIPLevel );
|
||||
float desiredMIPLevel = maxMIPLevelScalar + 0.79248 - 0.5 * log2( pow2( blinnShininessExponent ) + 1.0 );
|
||||
|
||||
// clamp to allowable LOD ranges.
|
||||
return clamp( desiredMIPLevel, 0.0, maxMIPLevelScalar );
|
||||
|
||||
}
|
||||
|
||||
vec3 getLightProbeIndirectRadiance( /*const in SpecularLightProbe specularLightProbe,*/ const in GeometricContext geometry, const in float blinnShininessExponent, const in int maxMIPLevel ) {
|
||||
|
||||
#ifdef ENVMAP_MODE_REFLECTION
|
||||
|
||||
vec3 reflectVec = reflect( -geometry.viewDir, geometry.normal );
|
||||
|
||||
#else
|
||||
|
||||
vec3 reflectVec = refract( -geometry.viewDir, geometry.normal, refractionRatio );
|
||||
|
||||
#endif
|
||||
|
||||
reflectVec = inverseTransformDirection( reflectVec, viewMatrix );
|
||||
|
||||
float specularMIPLevel = getSpecularMIPLevel( blinnShininessExponent, maxMIPLevel );
|
||||
|
||||
#ifdef ENVMAP_TYPE_CUBE
|
||||
|
||||
vec3 queryReflectVec = vec3( flipEnvMap * reflectVec.x, reflectVec.yz );
|
||||
|
||||
#ifdef TEXTURE_LOD_EXT
|
||||
|
||||
vec4 envMapColor = textureCubeLodEXT( envMap, queryReflectVec, specularMIPLevel );
|
||||
|
||||
#else
|
||||
|
||||
vec4 envMapColor = textureCube( envMap, queryReflectVec, specularMIPLevel );
|
||||
|
||||
#endif
|
||||
|
||||
envMapColor.rgb = envMapTexelToLinear( envMapColor ).rgb;
|
||||
|
||||
#elif defined( ENVMAP_TYPE_CUBE_UV )
|
||||
|
||||
vec3 queryReflectVec = vec3( flipEnvMap * reflectVec.x, reflectVec.yz );
|
||||
vec4 envMapColor = textureCubeUV( envMap, queryReflectVec, BlinnExponentToGGXRoughness(blinnShininessExponent ));
|
||||
|
||||
#elif defined( ENVMAP_TYPE_EQUIREC )
|
||||
|
||||
vec2 sampleUV;
|
||||
sampleUV.y = asin( clamp( reflectVec.y, - 1.0, 1.0 ) ) * RECIPROCAL_PI + 0.5;
|
||||
sampleUV.x = atan( reflectVec.z, reflectVec.x ) * RECIPROCAL_PI2 + 0.5;
|
||||
|
||||
#ifdef TEXTURE_LOD_EXT
|
||||
|
||||
vec4 envMapColor = texture2DLodEXT( envMap, sampleUV, specularMIPLevel );
|
||||
|
||||
#else
|
||||
|
||||
vec4 envMapColor = texture2D( envMap, sampleUV, specularMIPLevel );
|
||||
|
||||
#endif
|
||||
|
||||
envMapColor.rgb = envMapTexelToLinear( envMapColor ).rgb;
|
||||
|
||||
#elif defined( ENVMAP_TYPE_SPHERE )
|
||||
|
||||
vec3 reflectView = normalize( ( viewMatrix * vec4( reflectVec, 0.0 ) ).xyz + vec3( 0.0,0.0,1.0 ) );
|
||||
|
||||
#ifdef TEXTURE_LOD_EXT
|
||||
|
||||
vec4 envMapColor = texture2DLodEXT( envMap, reflectView.xy * 0.5 + 0.5, specularMIPLevel );
|
||||
|
||||
#else
|
||||
|
||||
vec4 envMapColor = texture2D( envMap, reflectView.xy * 0.5 + 0.5, specularMIPLevel );
|
||||
|
||||
#endif
|
||||
|
||||
envMapColor.rgb = envMapTexelToLinear( envMapColor ).rgb;
|
||||
|
||||
#endif
|
||||
|
||||
return envMapColor.rgb * envMapIntensity;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
25
lib/renderers/shaders/ShaderChunk/envmap_vertex.glsl
Normal file
25
lib/renderers/shaders/ShaderChunk/envmap_vertex.glsl
Normal file
@ -0,0 +1,25 @@
|
||||
#ifdef USE_ENVMAP
|
||||
|
||||
#if defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( PHONG )
|
||||
|
||||
vWorldPosition = worldPosition.xyz;
|
||||
|
||||
#else
|
||||
|
||||
vec3 cameraToVertex = normalize( worldPosition.xyz - cameraPosition );
|
||||
|
||||
vec3 worldNormal = inverseTransformDirection( transformedNormal, viewMatrix );
|
||||
|
||||
#ifdef ENVMAP_MODE_REFLECTION
|
||||
|
||||
vReflect = reflect( cameraToVertex, worldNormal );
|
||||
|
||||
#else
|
||||
|
||||
vReflect = refract( cameraToVertex, worldNormal, refractionRatio );
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
15
lib/renderers/shaders/ShaderChunk/fog_fragment.glsl
Normal file
15
lib/renderers/shaders/ShaderChunk/fog_fragment.glsl
Normal file
@ -0,0 +1,15 @@
|
||||
#ifdef USE_FOG
|
||||
|
||||
#ifdef FOG_EXP2
|
||||
|
||||
float fogFactor = whiteCompliment( exp2( - fogDensity * fogDensity * fogDepth * fogDepth * LOG2 ) );
|
||||
|
||||
#else
|
||||
|
||||
float fogFactor = smoothstep( fogNear, fogFar, fogDepth );
|
||||
|
||||
#endif
|
||||
|
||||
gl_FragColor.rgb = mix( gl_FragColor.rgb, fogColor, fogFactor );
|
||||
|
||||
#endif
|
17
lib/renderers/shaders/ShaderChunk/fog_pars_fragment.glsl
Normal file
17
lib/renderers/shaders/ShaderChunk/fog_pars_fragment.glsl
Normal file
@ -0,0 +1,17 @@
|
||||
#ifdef USE_FOG
|
||||
|
||||
uniform vec3 fogColor;
|
||||
varying float fogDepth;
|
||||
|
||||
#ifdef FOG_EXP2
|
||||
|
||||
uniform float fogDensity;
|
||||
|
||||
#else
|
||||
|
||||
uniform float fogNear;
|
||||
uniform float fogFar;
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/fog_pars_vertex.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/fog_pars_vertex.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_FOG
|
||||
|
||||
varying float fogDepth;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/fog_vertex.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/fog_vertex.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_FOG
|
||||
|
||||
fogDepth = -mvPosition.z;
|
||||
|
||||
#endif
|
@ -0,0 +1,24 @@
|
||||
#ifdef TOON
|
||||
|
||||
uniform sampler2D gradientMap;
|
||||
|
||||
vec3 getGradientIrradiance( vec3 normal, vec3 lightDirection ) {
|
||||
|
||||
// dotNL will be from -1.0 to 1.0
|
||||
float dotNL = dot( normal, lightDirection );
|
||||
vec2 coord = vec2( dotNL * 0.5 + 0.5, 0.0 );
|
||||
|
||||
#ifdef USE_GRADIENTMAP
|
||||
|
||||
return texture2D( gradientMap, coord ).rgb;
|
||||
|
||||
#else
|
||||
|
||||
return ( coord.x < 0.7 ) ? vec3( 0.7 ) : vec3( 1.0 );
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
}
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/lightmap_fragment.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/lightmap_fragment.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_LIGHTMAP
|
||||
|
||||
reflectedLight.indirectDiffuse += PI * texture2D( lightMap, vUv2 ).xyz * lightMapIntensity; // factor of PI should not be present; included here to prevent breakage
|
||||
|
||||
#endif
|
@ -0,0 +1,6 @@
|
||||
#ifdef USE_LIGHTMAP
|
||||
|
||||
uniform sampler2D lightMap;
|
||||
uniform float lightMapIntensity;
|
||||
|
||||
#endif
|
123
lib/renderers/shaders/ShaderChunk/lights_fragment_begin.glsl
Normal file
123
lib/renderers/shaders/ShaderChunk/lights_fragment_begin.glsl
Normal file
@ -0,0 +1,123 @@
|
||||
/**
|
||||
* This is a template that can be used to light a material, it uses pluggable
|
||||
* RenderEquations (RE)for specific lighting scenarios.
|
||||
*
|
||||
* Instructions for use:
|
||||
* - Ensure that both RE_Direct, RE_IndirectDiffuse and RE_IndirectSpecular are defined
|
||||
* - If you have defined an RE_IndirectSpecular, you need to also provide a Material_LightProbeLOD. <---- ???
|
||||
* - Create a material parameter that is to be passed as the third parameter to your lighting functions.
|
||||
*
|
||||
* TODO:
|
||||
* - Add area light support.
|
||||
* - Add sphere light support.
|
||||
* - Add diffuse light probe (irradiance cubemap) support.
|
||||
*/
|
||||
|
||||
GeometricContext geometry;
|
||||
|
||||
geometry.position = - vViewPosition;
|
||||
geometry.normal = normal;
|
||||
geometry.viewDir = normalize( vViewPosition );
|
||||
|
||||
IncidentLight directLight;
|
||||
|
||||
#if ( NUM_POINT_LIGHTS > 0 ) && defined( RE_Direct )
|
||||
|
||||
PointLight pointLight;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_POINT_LIGHTS; i ++ ) {
|
||||
|
||||
pointLight = pointLights[ i ];
|
||||
|
||||
getPointDirectLightIrradiance( pointLight, geometry, directLight );
|
||||
|
||||
#ifdef USE_SHADOWMAP
|
||||
directLight.color *= all( bvec2( pointLight.shadow, directLight.visible ) ) ? getPointShadow( pointShadowMap[ i ], pointLight.shadowMapSize, pointLight.shadowBias, pointLight.shadowRadius, vPointShadowCoord[ i ], pointLight.shadowCameraNear, pointLight.shadowCameraFar ) : 1.0;
|
||||
#endif
|
||||
|
||||
RE_Direct( directLight, geometry, material, reflectedLight );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if ( NUM_SPOT_LIGHTS > 0 ) && defined( RE_Direct )
|
||||
|
||||
SpotLight spotLight;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_SPOT_LIGHTS; i ++ ) {
|
||||
|
||||
spotLight = spotLights[ i ];
|
||||
|
||||
getSpotDirectLightIrradiance( spotLight, geometry, directLight );
|
||||
|
||||
#ifdef USE_SHADOWMAP
|
||||
directLight.color *= all( bvec2( spotLight.shadow, directLight.visible ) ) ? getShadow( spotShadowMap[ i ], spotLight.shadowMapSize, spotLight.shadowBias, spotLight.shadowRadius, vSpotShadowCoord[ i ] ) : 1.0;
|
||||
#endif
|
||||
|
||||
RE_Direct( directLight, geometry, material, reflectedLight );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if ( NUM_DIR_LIGHTS > 0 ) && defined( RE_Direct )
|
||||
|
||||
DirectionalLight directionalLight;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_DIR_LIGHTS; i ++ ) {
|
||||
|
||||
directionalLight = directionalLights[ i ];
|
||||
|
||||
getDirectionalDirectLightIrradiance( directionalLight, geometry, directLight );
|
||||
|
||||
#ifdef USE_SHADOWMAP
|
||||
directLight.color *= all( bvec2( directionalLight.shadow, directLight.visible ) ) ? getShadow( directionalShadowMap[ i ], directionalLight.shadowMapSize, directionalLight.shadowBias, directionalLight.shadowRadius, vDirectionalShadowCoord[ i ] ) : 1.0;
|
||||
#endif
|
||||
|
||||
RE_Direct( directLight, geometry, material, reflectedLight );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if ( NUM_RECT_AREA_LIGHTS > 0 ) && defined( RE_Direct_RectArea )
|
||||
|
||||
RectAreaLight rectAreaLight;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_RECT_AREA_LIGHTS; i ++ ) {
|
||||
|
||||
rectAreaLight = rectAreaLights[ i ];
|
||||
RE_Direct_RectArea( rectAreaLight, geometry, material, reflectedLight );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if defined( RE_IndirectDiffuse )
|
||||
|
||||
vec3 irradiance = getAmbientLightIrradiance( ambientLightColor );
|
||||
|
||||
#if ( NUM_HEMI_LIGHTS > 0 )
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_HEMI_LIGHTS; i ++ ) {
|
||||
|
||||
irradiance += getHemisphereLightIrradiance( hemisphereLights[ i ], geometry );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
#if defined( RE_IndirectSpecular )
|
||||
|
||||
vec3 radiance = vec3( 0.0 );
|
||||
vec3 clearCoatRadiance = vec3( 0.0 );
|
||||
|
||||
#endif
|
11
lib/renderers/shaders/ShaderChunk/lights_fragment_end.glsl
Normal file
11
lib/renderers/shaders/ShaderChunk/lights_fragment_end.glsl
Normal file
@ -0,0 +1,11 @@
|
||||
#if defined( RE_IndirectDiffuse )
|
||||
|
||||
RE_IndirectDiffuse( irradiance, geometry, material, reflectedLight );
|
||||
|
||||
#endif
|
||||
|
||||
#if defined( RE_IndirectSpecular )
|
||||
|
||||
RE_IndirectSpecular( radiance, clearCoatRadiance, geometry, material, reflectedLight );
|
||||
|
||||
#endif
|
33
lib/renderers/shaders/ShaderChunk/lights_fragment_maps.glsl
Normal file
33
lib/renderers/shaders/ShaderChunk/lights_fragment_maps.glsl
Normal file
@ -0,0 +1,33 @@
|
||||
#if defined( RE_IndirectDiffuse )
|
||||
|
||||
#ifdef USE_LIGHTMAP
|
||||
|
||||
vec3 lightMapIrradiance = texture2D( lightMap, vUv2 ).xyz * lightMapIntensity;
|
||||
|
||||
#ifndef PHYSICALLY_CORRECT_LIGHTS
|
||||
|
||||
lightMapIrradiance *= PI; // factor of PI should not be present; included here to prevent breakage
|
||||
|
||||
#endif
|
||||
|
||||
irradiance += lightMapIrradiance;
|
||||
|
||||
#endif
|
||||
|
||||
#if defined( USE_ENVMAP ) && defined( PHYSICAL ) && defined( ENVMAP_TYPE_CUBE_UV )
|
||||
|
||||
irradiance += getLightProbeIndirectIrradiance( /*lightProbe,*/ geometry, maxMipLevel );
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
#if defined( USE_ENVMAP ) && defined( RE_IndirectSpecular )
|
||||
|
||||
radiance += getLightProbeIndirectRadiance( /*specularLightProbe,*/ geometry, Material_BlinnShininessExponent( material ), maxMipLevel );
|
||||
|
||||
#ifndef STANDARD
|
||||
clearCoatRadiance += getLightProbeIndirectRadiance( /*specularLightProbe,*/ geometry, Material_ClearCoat_BlinnShininessExponent( material ), maxMipLevel );
|
||||
#endif
|
||||
|
||||
#endif
|
115
lib/renderers/shaders/ShaderChunk/lights_lambert_vertex.glsl
Normal file
115
lib/renderers/shaders/ShaderChunk/lights_lambert_vertex.glsl
Normal file
@ -0,0 +1,115 @@
|
||||
vec3 diffuse = vec3( 1.0 );
|
||||
|
||||
GeometricContext geometry;
|
||||
geometry.position = mvPosition.xyz;
|
||||
geometry.normal = normalize( transformedNormal );
|
||||
geometry.viewDir = normalize( -mvPosition.xyz );
|
||||
|
||||
GeometricContext backGeometry;
|
||||
backGeometry.position = geometry.position;
|
||||
backGeometry.normal = -geometry.normal;
|
||||
backGeometry.viewDir = geometry.viewDir;
|
||||
|
||||
vLightFront = vec3( 0.0 );
|
||||
|
||||
#ifdef DOUBLE_SIDED
|
||||
vLightBack = vec3( 0.0 );
|
||||
#endif
|
||||
|
||||
IncidentLight directLight;
|
||||
float dotNL;
|
||||
vec3 directLightColor_Diffuse;
|
||||
|
||||
#if NUM_POINT_LIGHTS > 0
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_POINT_LIGHTS; i ++ ) {
|
||||
|
||||
getPointDirectLightIrradiance( pointLights[ i ], geometry, directLight );
|
||||
|
||||
dotNL = dot( geometry.normal, directLight.direction );
|
||||
directLightColor_Diffuse = PI * directLight.color;
|
||||
|
||||
vLightFront += saturate( dotNL ) * directLightColor_Diffuse;
|
||||
|
||||
#ifdef DOUBLE_SIDED
|
||||
|
||||
vLightBack += saturate( -dotNL ) * directLightColor_Diffuse;
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_SPOT_LIGHTS > 0
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_SPOT_LIGHTS; i ++ ) {
|
||||
|
||||
getSpotDirectLightIrradiance( spotLights[ i ], geometry, directLight );
|
||||
|
||||
dotNL = dot( geometry.normal, directLight.direction );
|
||||
directLightColor_Diffuse = PI * directLight.color;
|
||||
|
||||
vLightFront += saturate( dotNL ) * directLightColor_Diffuse;
|
||||
|
||||
#ifdef DOUBLE_SIDED
|
||||
|
||||
vLightBack += saturate( -dotNL ) * directLightColor_Diffuse;
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
#if NUM_RECT_AREA_LIGHTS > 0
|
||||
|
||||
for ( int i = 0; i < NUM_RECT_AREA_LIGHTS; i ++ ) {
|
||||
|
||||
// TODO (abelnation): implement
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
*/
|
||||
|
||||
#if NUM_DIR_LIGHTS > 0
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_DIR_LIGHTS; i ++ ) {
|
||||
|
||||
getDirectionalDirectLightIrradiance( directionalLights[ i ], geometry, directLight );
|
||||
|
||||
dotNL = dot( geometry.normal, directLight.direction );
|
||||
directLightColor_Diffuse = PI * directLight.color;
|
||||
|
||||
vLightFront += saturate( dotNL ) * directLightColor_Diffuse;
|
||||
|
||||
#ifdef DOUBLE_SIDED
|
||||
|
||||
vLightBack += saturate( -dotNL ) * directLightColor_Diffuse;
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_HEMI_LIGHTS > 0
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_HEMI_LIGHTS; i ++ ) {
|
||||
|
||||
vLightFront += getHemisphereLightIrradiance( hemisphereLights[ i ], geometry );
|
||||
|
||||
#ifdef DOUBLE_SIDED
|
||||
|
||||
vLightBack += getHemisphereLightIrradiance( hemisphereLights[ i ], backGeometry );
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
#endif
|
170
lib/renderers/shaders/ShaderChunk/lights_pars_begin.glsl
Normal file
170
lib/renderers/shaders/ShaderChunk/lights_pars_begin.glsl
Normal file
@ -0,0 +1,170 @@
|
||||
uniform vec3 ambientLightColor;
|
||||
|
||||
vec3 getAmbientLightIrradiance( const in vec3 ambientLightColor ) {
|
||||
|
||||
vec3 irradiance = ambientLightColor;
|
||||
|
||||
#ifndef PHYSICALLY_CORRECT_LIGHTS
|
||||
|
||||
irradiance *= PI;
|
||||
|
||||
#endif
|
||||
|
||||
return irradiance;
|
||||
|
||||
}
|
||||
|
||||
#if NUM_DIR_LIGHTS > 0
|
||||
|
||||
struct DirectionalLight {
|
||||
vec3 direction;
|
||||
vec3 color;
|
||||
|
||||
int shadow;
|
||||
float shadowBias;
|
||||
float shadowRadius;
|
||||
vec2 shadowMapSize;
|
||||
};
|
||||
|
||||
uniform DirectionalLight directionalLights[ NUM_DIR_LIGHTS ];
|
||||
|
||||
void getDirectionalDirectLightIrradiance( const in DirectionalLight directionalLight, const in GeometricContext geometry, out IncidentLight directLight ) {
|
||||
|
||||
directLight.color = directionalLight.color;
|
||||
directLight.direction = directionalLight.direction;
|
||||
directLight.visible = true;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#if NUM_POINT_LIGHTS > 0
|
||||
|
||||
struct PointLight {
|
||||
vec3 position;
|
||||
vec3 color;
|
||||
float distance;
|
||||
float decay;
|
||||
|
||||
int shadow;
|
||||
float shadowBias;
|
||||
float shadowRadius;
|
||||
vec2 shadowMapSize;
|
||||
float shadowCameraNear;
|
||||
float shadowCameraFar;
|
||||
};
|
||||
|
||||
uniform PointLight pointLights[ NUM_POINT_LIGHTS ];
|
||||
|
||||
// directLight is an out parameter as having it as a return value caused compiler errors on some devices
|
||||
void getPointDirectLightIrradiance( const in PointLight pointLight, const in GeometricContext geometry, out IncidentLight directLight ) {
|
||||
|
||||
vec3 lVector = pointLight.position - geometry.position;
|
||||
directLight.direction = normalize( lVector );
|
||||
|
||||
float lightDistance = length( lVector );
|
||||
|
||||
directLight.color = pointLight.color;
|
||||
directLight.color *= punctualLightIntensityToIrradianceFactor( lightDistance, pointLight.distance, pointLight.decay );
|
||||
directLight.visible = ( directLight.color != vec3( 0.0 ) );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#if NUM_SPOT_LIGHTS > 0
|
||||
|
||||
struct SpotLight {
|
||||
vec3 position;
|
||||
vec3 direction;
|
||||
vec3 color;
|
||||
float distance;
|
||||
float decay;
|
||||
float coneCos;
|
||||
float penumbraCos;
|
||||
|
||||
int shadow;
|
||||
float shadowBias;
|
||||
float shadowRadius;
|
||||
vec2 shadowMapSize;
|
||||
};
|
||||
|
||||
uniform SpotLight spotLights[ NUM_SPOT_LIGHTS ];
|
||||
|
||||
// directLight is an out parameter as having it as a return value caused compiler errors on some devices
|
||||
void getSpotDirectLightIrradiance( const in SpotLight spotLight, const in GeometricContext geometry, out IncidentLight directLight ) {
|
||||
|
||||
vec3 lVector = spotLight.position - geometry.position;
|
||||
directLight.direction = normalize( lVector );
|
||||
|
||||
float lightDistance = length( lVector );
|
||||
float angleCos = dot( directLight.direction, spotLight.direction );
|
||||
|
||||
if ( angleCos > spotLight.coneCos ) {
|
||||
|
||||
float spotEffect = smoothstep( spotLight.coneCos, spotLight.penumbraCos, angleCos );
|
||||
|
||||
directLight.color = spotLight.color;
|
||||
directLight.color *= spotEffect * punctualLightIntensityToIrradianceFactor( lightDistance, spotLight.distance, spotLight.decay );
|
||||
directLight.visible = true;
|
||||
|
||||
} else {
|
||||
|
||||
directLight.color = vec3( 0.0 );
|
||||
directLight.visible = false;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#if NUM_RECT_AREA_LIGHTS > 0
|
||||
|
||||
struct RectAreaLight {
|
||||
vec3 color;
|
||||
vec3 position;
|
||||
vec3 halfWidth;
|
||||
vec3 halfHeight;
|
||||
};
|
||||
|
||||
// Pre-computed values of LinearTransformedCosine approximation of BRDF
|
||||
// BRDF approximation Texture is 64x64
|
||||
uniform sampler2D ltc_1; // RGBA Float
|
||||
uniform sampler2D ltc_2; // RGBA Float
|
||||
|
||||
uniform RectAreaLight rectAreaLights[ NUM_RECT_AREA_LIGHTS ];
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#if NUM_HEMI_LIGHTS > 0
|
||||
|
||||
struct HemisphereLight {
|
||||
vec3 direction;
|
||||
vec3 skyColor;
|
||||
vec3 groundColor;
|
||||
};
|
||||
|
||||
uniform HemisphereLight hemisphereLights[ NUM_HEMI_LIGHTS ];
|
||||
|
||||
vec3 getHemisphereLightIrradiance( const in HemisphereLight hemiLight, const in GeometricContext geometry ) {
|
||||
|
||||
float dotNL = dot( geometry.normal, hemiLight.direction );
|
||||
float hemiDiffuseWeight = 0.5 * dotNL + 0.5;
|
||||
|
||||
vec3 irradiance = mix( hemiLight.groundColor, hemiLight.skyColor, hemiDiffuseWeight );
|
||||
|
||||
#ifndef PHYSICALLY_CORRECT_LIGHTS
|
||||
|
||||
irradiance *= PI;
|
||||
|
||||
#endif
|
||||
|
||||
return irradiance;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
BlinnPhongMaterial material;
|
||||
material.diffuseColor = diffuseColor.rgb;
|
||||
material.specularColor = specular;
|
||||
material.specularShininess = shininess;
|
||||
material.specularStrength = specularStrength;
|
@ -0,0 +1,53 @@
|
||||
varying vec3 vViewPosition;
|
||||
|
||||
#ifndef FLAT_SHADED
|
||||
|
||||
varying vec3 vNormal;
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
struct BlinnPhongMaterial {
|
||||
|
||||
vec3 diffuseColor;
|
||||
vec3 specularColor;
|
||||
float specularShininess;
|
||||
float specularStrength;
|
||||
|
||||
};
|
||||
|
||||
void RE_Direct_BlinnPhong( const in IncidentLight directLight, const in GeometricContext geometry, const in BlinnPhongMaterial material, inout ReflectedLight reflectedLight ) {
|
||||
|
||||
#ifdef TOON
|
||||
|
||||
vec3 irradiance = getGradientIrradiance( geometry.normal, directLight.direction ) * directLight.color;
|
||||
|
||||
#else
|
||||
|
||||
float dotNL = saturate( dot( geometry.normal, directLight.direction ) );
|
||||
vec3 irradiance = dotNL * directLight.color;
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef PHYSICALLY_CORRECT_LIGHTS
|
||||
|
||||
irradiance *= PI; // punctual light
|
||||
|
||||
#endif
|
||||
|
||||
reflectedLight.directDiffuse += irradiance * BRDF_Diffuse_Lambert( material.diffuseColor );
|
||||
|
||||
reflectedLight.directSpecular += irradiance * BRDF_Specular_BlinnPhong( directLight, geometry, material.specularColor, material.specularShininess ) * material.specularStrength;
|
||||
|
||||
}
|
||||
|
||||
void RE_IndirectDiffuse_BlinnPhong( const in vec3 irradiance, const in GeometricContext geometry, const in BlinnPhongMaterial material, inout ReflectedLight reflectedLight ) {
|
||||
|
||||
reflectedLight.indirectDiffuse += irradiance * BRDF_Diffuse_Lambert( material.diffuseColor );
|
||||
|
||||
}
|
||||
|
||||
#define RE_Direct RE_Direct_BlinnPhong
|
||||
#define RE_IndirectDiffuse RE_IndirectDiffuse_BlinnPhong
|
||||
|
||||
#define Material_LightProbeLOD( material ) (0)
|
@ -0,0 +1,10 @@
|
||||
PhysicalMaterial material;
|
||||
material.diffuseColor = diffuseColor.rgb * ( 1.0 - metalnessFactor );
|
||||
material.specularRoughness = clamp( roughnessFactor, 0.04, 1.0 );
|
||||
#ifdef STANDARD
|
||||
material.specularColor = mix( vec3( DEFAULT_SPECULAR_COEFFICIENT ), diffuseColor.rgb, metalnessFactor );
|
||||
#else
|
||||
material.specularColor = mix( vec3( MAXIMUM_SPECULAR_COEFFICIENT * pow2( reflectivity ) ), diffuseColor.rgb, metalnessFactor );
|
||||
material.clearCoat = saturate( clearCoat ); // Burley clearcoat model
|
||||
material.clearCoatRoughness = clamp( clearCoatRoughness, 0.04, 1.0 );
|
||||
#endif
|
@ -0,0 +1,135 @@
|
||||
struct PhysicalMaterial {
|
||||
|
||||
vec3 diffuseColor;
|
||||
float specularRoughness;
|
||||
vec3 specularColor;
|
||||
|
||||
#ifndef STANDARD
|
||||
float clearCoat;
|
||||
float clearCoatRoughness;
|
||||
#endif
|
||||
|
||||
};
|
||||
|
||||
#define MAXIMUM_SPECULAR_COEFFICIENT 0.16
|
||||
#define DEFAULT_SPECULAR_COEFFICIENT 0.04
|
||||
|
||||
// Clear coat directional hemishperical reflectance (this approximation should be improved)
|
||||
float clearCoatDHRApprox( const in float roughness, const in float dotNL ) {
|
||||
|
||||
return DEFAULT_SPECULAR_COEFFICIENT + ( 1.0 - DEFAULT_SPECULAR_COEFFICIENT ) * ( pow( 1.0 - dotNL, 5.0 ) * pow( 1.0 - roughness, 2.0 ) );
|
||||
|
||||
}
|
||||
|
||||
#if NUM_RECT_AREA_LIGHTS > 0
|
||||
|
||||
void RE_Direct_RectArea_Physical( const in RectAreaLight rectAreaLight, const in GeometricContext geometry, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {
|
||||
|
||||
vec3 normal = geometry.normal;
|
||||
vec3 viewDir = geometry.viewDir;
|
||||
vec3 position = geometry.position;
|
||||
vec3 lightPos = rectAreaLight.position;
|
||||
vec3 halfWidth = rectAreaLight.halfWidth;
|
||||
vec3 halfHeight = rectAreaLight.halfHeight;
|
||||
vec3 lightColor = rectAreaLight.color;
|
||||
float roughness = material.specularRoughness;
|
||||
|
||||
vec3 rectCoords[ 4 ];
|
||||
rectCoords[ 0 ] = lightPos - halfWidth - halfHeight; // counterclockwise
|
||||
rectCoords[ 1 ] = lightPos + halfWidth - halfHeight;
|
||||
rectCoords[ 2 ] = lightPos + halfWidth + halfHeight;
|
||||
rectCoords[ 3 ] = lightPos - halfWidth + halfHeight;
|
||||
|
||||
vec2 uv = LTC_Uv( normal, viewDir, roughness );
|
||||
|
||||
vec4 t1 = texture2D( ltc_1, uv );
|
||||
vec4 t2 = texture2D( ltc_2, uv );
|
||||
|
||||
mat3 mInv = mat3(
|
||||
vec3( t1.x, 0, t1.y ),
|
||||
vec3( 0, 1, 0 ),
|
||||
vec3( t1.z, 0, t1.w )
|
||||
);
|
||||
|
||||
// LTC Fresnel Approximation by Stephen Hill
|
||||
// http://blog.selfshadow.com/publications/s2016-advances/s2016_ltc_fresnel.pdf
|
||||
vec3 fresnel = ( material.specularColor * t2.x + ( vec3( 1.0 ) - material.specularColor ) * t2.y );
|
||||
|
||||
reflectedLight.directSpecular += lightColor * fresnel * LTC_Evaluate( normal, viewDir, position, mInv, rectCoords );
|
||||
|
||||
reflectedLight.directDiffuse += lightColor * material.diffuseColor * LTC_Evaluate( normal, viewDir, position, mat3( 1.0 ), rectCoords );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
void RE_Direct_Physical( const in IncidentLight directLight, const in GeometricContext geometry, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {
|
||||
|
||||
float dotNL = saturate( dot( geometry.normal, directLight.direction ) );
|
||||
|
||||
vec3 irradiance = dotNL * directLight.color;
|
||||
|
||||
#ifndef PHYSICALLY_CORRECT_LIGHTS
|
||||
|
||||
irradiance *= PI; // punctual light
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef STANDARD
|
||||
float clearCoatDHR = material.clearCoat * clearCoatDHRApprox( material.clearCoatRoughness, dotNL );
|
||||
#else
|
||||
float clearCoatDHR = 0.0;
|
||||
#endif
|
||||
|
||||
reflectedLight.directSpecular += ( 1.0 - clearCoatDHR ) * irradiance * BRDF_Specular_GGX( directLight, geometry, material.specularColor, material.specularRoughness );
|
||||
|
||||
reflectedLight.directDiffuse += ( 1.0 - clearCoatDHR ) * irradiance * BRDF_Diffuse_Lambert( material.diffuseColor );
|
||||
|
||||
#ifndef STANDARD
|
||||
|
||||
reflectedLight.directSpecular += irradiance * material.clearCoat * BRDF_Specular_GGX( directLight, geometry, vec3( DEFAULT_SPECULAR_COEFFICIENT ), material.clearCoatRoughness );
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
void RE_IndirectDiffuse_Physical( const in vec3 irradiance, const in GeometricContext geometry, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {
|
||||
|
||||
reflectedLight.indirectDiffuse += irradiance * BRDF_Diffuse_Lambert( material.diffuseColor );
|
||||
|
||||
}
|
||||
|
||||
void RE_IndirectSpecular_Physical( const in vec3 radiance, const in vec3 clearCoatRadiance, const in GeometricContext geometry, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {
|
||||
|
||||
#ifndef STANDARD
|
||||
float dotNV = saturate( dot( geometry.normal, geometry.viewDir ) );
|
||||
float dotNL = dotNV;
|
||||
float clearCoatDHR = material.clearCoat * clearCoatDHRApprox( material.clearCoatRoughness, dotNL );
|
||||
#else
|
||||
float clearCoatDHR = 0.0;
|
||||
#endif
|
||||
|
||||
reflectedLight.indirectSpecular += ( 1.0 - clearCoatDHR ) * radiance * BRDF_Specular_GGX_Environment( geometry, material.specularColor, material.specularRoughness );
|
||||
|
||||
#ifndef STANDARD
|
||||
|
||||
reflectedLight.indirectSpecular += clearCoatRadiance * material.clearCoat * BRDF_Specular_GGX_Environment( geometry, vec3( DEFAULT_SPECULAR_COEFFICIENT ), material.clearCoatRoughness );
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
#define RE_Direct RE_Direct_Physical
|
||||
#define RE_Direct_RectArea RE_Direct_RectArea_Physical
|
||||
#define RE_IndirectDiffuse RE_IndirectDiffuse_Physical
|
||||
#define RE_IndirectSpecular RE_IndirectSpecular_Physical
|
||||
|
||||
#define Material_BlinnShininessExponent( material ) GGXRoughnessToBlinnExponent( material.specularRoughness )
|
||||
#define Material_ClearCoat_BlinnShininessExponent( material ) GGXRoughnessToBlinnExponent( material.clearCoatRoughness )
|
||||
|
||||
// ref: https://seblagarde.files.wordpress.com/2015/07/course_notes_moving_frostbite_to_pbr_v32.pdf
|
||||
float computeSpecularOcclusion( const in float dotNV, const in float ambientOcclusion, const in float roughness ) {
|
||||
|
||||
return saturate( pow( dotNV + ambientOcclusion, exp2( - 16.0 * roughness - 1.0 ) ) - 1.0 + ambientOcclusion );
|
||||
|
||||
}
|
@ -0,0 +1,5 @@
|
||||
#if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )
|
||||
|
||||
gl_FragDepthEXT = log2( vFragDepth ) * logDepthBufFC * 0.5;
|
||||
|
||||
#endif
|
@ -0,0 +1,6 @@
|
||||
#if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )
|
||||
|
||||
uniform float logDepthBufFC;
|
||||
varying float vFragDepth;
|
||||
|
||||
#endif
|
@ -0,0 +1,13 @@
|
||||
#ifdef USE_LOGDEPTHBUF
|
||||
|
||||
#ifdef USE_LOGDEPTHBUF_EXT
|
||||
|
||||
varying float vFragDepth;
|
||||
|
||||
#else
|
||||
|
||||
uniform float logDepthBufFC;
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
15
lib/renderers/shaders/ShaderChunk/logdepthbuf_vertex.glsl
Normal file
15
lib/renderers/shaders/ShaderChunk/logdepthbuf_vertex.glsl
Normal file
@ -0,0 +1,15 @@
|
||||
#ifdef USE_LOGDEPTHBUF
|
||||
|
||||
#ifdef USE_LOGDEPTHBUF_EXT
|
||||
|
||||
vFragDepth = 1.0 + gl_Position.w;
|
||||
|
||||
#else
|
||||
|
||||
gl_Position.z = log2( max( EPSILON, gl_Position.w + 1.0 ) ) * logDepthBufFC - 1.0;
|
||||
|
||||
gl_Position.z *= gl_Position.w;
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
8
lib/renderers/shaders/ShaderChunk/map_fragment.glsl
Normal file
8
lib/renderers/shaders/ShaderChunk/map_fragment.glsl
Normal file
@ -0,0 +1,8 @@
|
||||
#ifdef USE_MAP
|
||||
|
||||
vec4 texelColor = texture2D( map, vUv );
|
||||
|
||||
texelColor = mapTexelToLinear( texelColor );
|
||||
diffuseColor *= texelColor;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/map_pars_fragment.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/map_pars_fragment.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#ifdef USE_MAP
|
||||
|
||||
uniform sampler2D map;
|
||||
|
||||
#endif
|
@ -0,0 +1,7 @@
|
||||
#ifdef USE_MAP
|
||||
|
||||
vec2 uv = ( uvTransform * vec3( gl_PointCoord.x, 1.0 - gl_PointCoord.y, 1 ) ).xy;
|
||||
vec4 mapTexel = texture2D( map, uv );
|
||||
diffuseColor *= mapTexelToLinear( mapTexel );
|
||||
|
||||
#endif
|
@ -0,0 +1,6 @@
|
||||
#ifdef USE_MAP
|
||||
|
||||
uniform mat3 uvTransform;
|
||||
uniform sampler2D map;
|
||||
|
||||
#endif
|
10
lib/renderers/shaders/ShaderChunk/metalnessmap_fragment.glsl
Normal file
10
lib/renderers/shaders/ShaderChunk/metalnessmap_fragment.glsl
Normal file
@ -0,0 +1,10 @@
|
||||
float metalnessFactor = metalness;
|
||||
|
||||
#ifdef USE_METALNESSMAP
|
||||
|
||||
vec4 texelMetalness = texture2D( metalnessMap, vUv );
|
||||
|
||||
// reads channel B, compatible with a combined OcclusionRoughnessMetallic (RGB) texture
|
||||
metalnessFactor *= texelMetalness.b;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef USE_METALNESSMAP
|
||||
|
||||
uniform sampler2D metalnessMap;
|
||||
|
||||
#endif
|
@ -0,0 +1,8 @@
|
||||
#ifdef USE_MORPHNORMALS
|
||||
|
||||
objectNormal += ( morphNormal0 - normal ) * morphTargetInfluences[ 0 ];
|
||||
objectNormal += ( morphNormal1 - normal ) * morphTargetInfluences[ 1 ];
|
||||
objectNormal += ( morphNormal2 - normal ) * morphTargetInfluences[ 2 ];
|
||||
objectNormal += ( morphNormal3 - normal ) * morphTargetInfluences[ 3 ];
|
||||
|
||||
#endif
|
@ -0,0 +1,13 @@
|
||||
#ifdef USE_MORPHTARGETS
|
||||
|
||||
#ifndef USE_MORPHNORMALS
|
||||
|
||||
uniform float morphTargetInfluences[ 8 ];
|
||||
|
||||
#else
|
||||
|
||||
uniform float morphTargetInfluences[ 4 ];
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
17
lib/renderers/shaders/ShaderChunk/morphtarget_vertex.glsl
Normal file
17
lib/renderers/shaders/ShaderChunk/morphtarget_vertex.glsl
Normal file
@ -0,0 +1,17 @@
|
||||
#ifdef USE_MORPHTARGETS
|
||||
|
||||
transformed += ( morphTarget0 - position ) * morphTargetInfluences[ 0 ];
|
||||
transformed += ( morphTarget1 - position ) * morphTargetInfluences[ 1 ];
|
||||
transformed += ( morphTarget2 - position ) * morphTargetInfluences[ 2 ];
|
||||
transformed += ( morphTarget3 - position ) * morphTargetInfluences[ 3 ];
|
||||
|
||||
#ifndef USE_MORPHNORMALS
|
||||
|
||||
transformed += ( morphTarget4 - position ) * morphTargetInfluences[ 4 ];
|
||||
transformed += ( morphTarget5 - position ) * morphTargetInfluences[ 5 ];
|
||||
transformed += ( morphTarget6 - position ) * morphTargetInfluences[ 6 ];
|
||||
transformed += ( morphTarget7 - position ) * morphTargetInfluences[ 7 ];
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
19
lib/renderers/shaders/ShaderChunk/normal_fragment_begin.glsl
Normal file
19
lib/renderers/shaders/ShaderChunk/normal_fragment_begin.glsl
Normal file
@ -0,0 +1,19 @@
|
||||
#ifdef FLAT_SHADED
|
||||
|
||||
// Workaround for Adreno/Nexus5 not able able to do dFdx( vViewPosition ) ...
|
||||
|
||||
vec3 fdx = vec3( dFdx( vViewPosition.x ), dFdx( vViewPosition.y ), dFdx( vViewPosition.z ) );
|
||||
vec3 fdy = vec3( dFdy( vViewPosition.x ), dFdy( vViewPosition.y ), dFdy( vViewPosition.z ) );
|
||||
vec3 normal = normalize( cross( fdx, fdy ) );
|
||||
|
||||
#else
|
||||
|
||||
vec3 normal = normalize( vNormal );
|
||||
|
||||
#ifdef DOUBLE_SIDED
|
||||
|
||||
normal = normal * ( float( gl_FrontFacing ) * 2.0 - 1.0 );
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
31
lib/renderers/shaders/ShaderChunk/normal_fragment_maps.glsl
Normal file
31
lib/renderers/shaders/ShaderChunk/normal_fragment_maps.glsl
Normal file
@ -0,0 +1,31 @@
|
||||
#ifdef USE_NORMALMAP
|
||||
|
||||
#ifdef OBJECTSPACE_NORMALMAP
|
||||
|
||||
normal = texture2D( normalMap, vUv ).xyz * 2.0 - 1.0; // overrides both flatShading and attribute normals
|
||||
|
||||
#ifdef FLIP_SIDED
|
||||
|
||||
normal = - normal;
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef DOUBLE_SIDED
|
||||
|
||||
normal = normal * ( float( gl_FrontFacing ) * 2.0 - 1.0 );
|
||||
|
||||
#endif
|
||||
|
||||
normal = normalize( normalMatrix * normal );
|
||||
|
||||
#else // tangent-space normal map
|
||||
|
||||
normal = perturbNormal2Arb( -vViewPosition, normal );
|
||||
|
||||
#endif
|
||||
|
||||
#elif defined( USE_BUMPMAP )
|
||||
|
||||
normal = perturbNormalArb( -vViewPosition, normal, dHdxy_fwd() );
|
||||
|
||||
#endif
|
@ -0,0 +1,42 @@
|
||||
#ifdef USE_NORMALMAP
|
||||
|
||||
uniform sampler2D normalMap;
|
||||
uniform vec2 normalScale;
|
||||
|
||||
#ifdef OBJECTSPACE_NORMALMAP
|
||||
|
||||
uniform mat3 normalMatrix;
|
||||
|
||||
#else
|
||||
|
||||
// Per-Pixel Tangent Space Normal Mapping
|
||||
// http://hacksoflife.blogspot.ch/2009/11/per-pixel-tangent-space-normal-mapping.html
|
||||
|
||||
vec3 perturbNormal2Arb( vec3 eye_pos, vec3 surf_norm ) {
|
||||
|
||||
// Workaround for Adreno 3XX dFd*( vec3 ) bug. See #9988
|
||||
|
||||
vec3 q0 = vec3( dFdx( eye_pos.x ), dFdx( eye_pos.y ), dFdx( eye_pos.z ) );
|
||||
vec3 q1 = vec3( dFdy( eye_pos.x ), dFdy( eye_pos.y ), dFdy( eye_pos.z ) );
|
||||
vec2 st0 = dFdx( vUv.st );
|
||||
vec2 st1 = dFdy( vUv.st );
|
||||
|
||||
float scale = sign( st1.t * st0.s - st0.t * st1.s ); // we do not care about the magnitude
|
||||
|
||||
vec3 S = normalize( ( q0 * st1.t - q1 * st0.t ) * scale );
|
||||
vec3 T = normalize( ( - q0 * st1.s + q1 * st0.s ) * scale );
|
||||
vec3 N = normalize( surf_norm );
|
||||
mat3 tsn = mat3( S, T, N );
|
||||
|
||||
vec3 mapN = texture2D( normalMap, vUv ).xyz * 2.0 - 1.0;
|
||||
|
||||
mapN.xy *= normalScale;
|
||||
mapN.xy *= ( float( gl_FrontFacing ) * 2.0 - 1.0 );
|
||||
|
||||
return normalize( tsn * mapN );
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
41
lib/renderers/shaders/ShaderChunk/packing.glsl
Normal file
41
lib/renderers/shaders/ShaderChunk/packing.glsl
Normal file
@ -0,0 +1,41 @@
|
||||
vec3 packNormalToRGB( const in vec3 normal ) {
|
||||
return normalize( normal ) * 0.5 + 0.5;
|
||||
}
|
||||
|
||||
vec3 unpackRGBToNormal( const in vec3 rgb ) {
|
||||
return 2.0 * rgb.xyz - 1.0;
|
||||
}
|
||||
|
||||
const float PackUpscale = 256. / 255.; // fraction -> 0..1 (including 1)
|
||||
const float UnpackDownscale = 255. / 256.; // 0..1 -> fraction (excluding 1)
|
||||
|
||||
const vec3 PackFactors = vec3( 256. * 256. * 256., 256. * 256., 256. );
|
||||
const vec4 UnpackFactors = UnpackDownscale / vec4( PackFactors, 1. );
|
||||
|
||||
const float ShiftRight8 = 1. / 256.;
|
||||
|
||||
vec4 packDepthToRGBA( const in float v ) {
|
||||
vec4 r = vec4( fract( v * PackFactors ), v );
|
||||
r.yzw -= r.xyz * ShiftRight8; // tidy overflow
|
||||
return r * PackUpscale;
|
||||
}
|
||||
|
||||
float unpackRGBAToDepth( const in vec4 v ) {
|
||||
return dot( v, UnpackFactors );
|
||||
}
|
||||
|
||||
// NOTE: viewZ/eyeZ is < 0 when in front of the camera per OpenGL conventions
|
||||
|
||||
float viewZToOrthographicDepth( const in float viewZ, const in float near, const in float far ) {
|
||||
return ( viewZ + near ) / ( near - far );
|
||||
}
|
||||
float orthographicDepthToViewZ( const in float linearClipZ, const in float near, const in float far ) {
|
||||
return linearClipZ * ( near - far ) - near;
|
||||
}
|
||||
|
||||
float viewZToPerspectiveDepth( const in float viewZ, const in float near, const in float far ) {
|
||||
return (( near + viewZ ) * far ) / (( far - near ) * viewZ );
|
||||
}
|
||||
float perspectiveDepthToViewZ( const in float invClipZ, const in float near, const in float far ) {
|
||||
return ( near * far ) / ( ( far - near ) * invClipZ - far );
|
||||
}
|
@ -0,0 +1,6 @@
|
||||
#ifdef PREMULTIPLIED_ALPHA
|
||||
|
||||
// Get get normal blending with premultipled, use with CustomBlending, OneFactor, OneMinusSrcAlphaFactor, AddEquation.
|
||||
gl_FragColor.rgb *= gl_FragColor.a;
|
||||
|
||||
#endif
|
3
lib/renderers/shaders/ShaderChunk/project_vertex.glsl
Normal file
3
lib/renderers/shaders/ShaderChunk/project_vertex.glsl
Normal file
@ -0,0 +1,3 @@
|
||||
vec4 mvPosition = modelViewMatrix * vec4( transformed, 1.0 );
|
||||
|
||||
gl_Position = projectionMatrix * mvPosition;
|
10
lib/renderers/shaders/ShaderChunk/roughnessmap_fragment.glsl
Normal file
10
lib/renderers/shaders/ShaderChunk/roughnessmap_fragment.glsl
Normal file
@ -0,0 +1,10 @@
|
||||
float roughnessFactor = roughness;
|
||||
|
||||
#ifdef USE_ROUGHNESSMAP
|
||||
|
||||
vec4 texelRoughness = texture2D( roughnessMap, vUv );
|
||||
|
||||
// reads channel G, compatible with a combined OcclusionRoughnessMetallic (RGB) texture
|
||||
roughnessFactor *= texelRoughness.g;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef USE_ROUGHNESSMAP
|
||||
|
||||
uniform sampler2D roughnessMap;
|
||||
|
||||
#endif
|
243
lib/renderers/shaders/ShaderChunk/shadowmap_pars_fragment.glsl
Normal file
243
lib/renderers/shaders/ShaderChunk/shadowmap_pars_fragment.glsl
Normal file
@ -0,0 +1,243 @@
|
||||
#ifdef USE_SHADOWMAP
|
||||
|
||||
#if NUM_DIR_LIGHTS > 0
|
||||
|
||||
uniform sampler2D directionalShadowMap[ NUM_DIR_LIGHTS ];
|
||||
varying vec4 vDirectionalShadowCoord[ NUM_DIR_LIGHTS ];
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_SPOT_LIGHTS > 0
|
||||
|
||||
uniform sampler2D spotShadowMap[ NUM_SPOT_LIGHTS ];
|
||||
varying vec4 vSpotShadowCoord[ NUM_SPOT_LIGHTS ];
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_POINT_LIGHTS > 0
|
||||
|
||||
uniform sampler2D pointShadowMap[ NUM_POINT_LIGHTS ];
|
||||
varying vec4 vPointShadowCoord[ NUM_POINT_LIGHTS ];
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
#if NUM_RECT_AREA_LIGHTS > 0
|
||||
|
||||
// TODO (abelnation): create uniforms for area light shadows
|
||||
|
||||
#endif
|
||||
*/
|
||||
|
||||
float texture2DCompare( sampler2D depths, vec2 uv, float compare ) {
|
||||
|
||||
return step( compare, unpackRGBAToDepth( texture2D( depths, uv ) ) );
|
||||
|
||||
}
|
||||
|
||||
float texture2DShadowLerp( sampler2D depths, vec2 size, vec2 uv, float compare ) {
|
||||
|
||||
const vec2 offset = vec2( 0.0, 1.0 );
|
||||
|
||||
vec2 texelSize = vec2( 1.0 ) / size;
|
||||
vec2 centroidUV = floor( uv * size + 0.5 ) / size;
|
||||
|
||||
float lb = texture2DCompare( depths, centroidUV + texelSize * offset.xx, compare );
|
||||
float lt = texture2DCompare( depths, centroidUV + texelSize * offset.xy, compare );
|
||||
float rb = texture2DCompare( depths, centroidUV + texelSize * offset.yx, compare );
|
||||
float rt = texture2DCompare( depths, centroidUV + texelSize * offset.yy, compare );
|
||||
|
||||
vec2 f = fract( uv * size + 0.5 );
|
||||
|
||||
float a = mix( lb, lt, f.y );
|
||||
float b = mix( rb, rt, f.y );
|
||||
float c = mix( a, b, f.x );
|
||||
|
||||
return c;
|
||||
|
||||
}
|
||||
|
||||
float getShadow( sampler2D shadowMap, vec2 shadowMapSize, float shadowBias, float shadowRadius, vec4 shadowCoord ) {
|
||||
|
||||
float shadow = 1.0;
|
||||
|
||||
shadowCoord.xyz /= shadowCoord.w;
|
||||
shadowCoord.z += shadowBias;
|
||||
|
||||
// if ( something && something ) breaks ATI OpenGL shader compiler
|
||||
// if ( all( something, something ) ) using this instead
|
||||
|
||||
bvec4 inFrustumVec = bvec4 ( shadowCoord.x >= 0.0, shadowCoord.x <= 1.0, shadowCoord.y >= 0.0, shadowCoord.y <= 1.0 );
|
||||
bool inFrustum = all( inFrustumVec );
|
||||
|
||||
bvec2 frustumTestVec = bvec2( inFrustum, shadowCoord.z <= 1.0 );
|
||||
|
||||
bool frustumTest = all( frustumTestVec );
|
||||
|
||||
if ( frustumTest ) {
|
||||
|
||||
#if defined( SHADOWMAP_TYPE_PCF )
|
||||
|
||||
vec2 texelSize = vec2( 1.0 ) / shadowMapSize;
|
||||
|
||||
float dx0 = - texelSize.x * shadowRadius;
|
||||
float dy0 = - texelSize.y * shadowRadius;
|
||||
float dx1 = + texelSize.x * shadowRadius;
|
||||
float dy1 = + texelSize.y * shadowRadius;
|
||||
|
||||
shadow = (
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( dx0, dy0 ), shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( 0.0, dy0 ), shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( dx1, dy0 ), shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( dx0, 0.0 ), shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy, shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( dx1, 0.0 ), shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( dx0, dy1 ), shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( 0.0, dy1 ), shadowCoord.z ) +
|
||||
texture2DCompare( shadowMap, shadowCoord.xy + vec2( dx1, dy1 ), shadowCoord.z )
|
||||
) * ( 1.0 / 9.0 );
|
||||
|
||||
#elif defined( SHADOWMAP_TYPE_PCF_SOFT )
|
||||
|
||||
vec2 texelSize = vec2( 1.0 ) / shadowMapSize;
|
||||
|
||||
float dx0 = - texelSize.x * shadowRadius;
|
||||
float dy0 = - texelSize.y * shadowRadius;
|
||||
float dx1 = + texelSize.x * shadowRadius;
|
||||
float dy1 = + texelSize.y * shadowRadius;
|
||||
|
||||
shadow = (
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( dx0, dy0 ), shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( 0.0, dy0 ), shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( dx1, dy0 ), shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( dx0, 0.0 ), shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy, shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( dx1, 0.0 ), shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( dx0, dy1 ), shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( 0.0, dy1 ), shadowCoord.z ) +
|
||||
texture2DShadowLerp( shadowMap, shadowMapSize, shadowCoord.xy + vec2( dx1, dy1 ), shadowCoord.z )
|
||||
) * ( 1.0 / 9.0 );
|
||||
|
||||
#else // no percentage-closer filtering:
|
||||
|
||||
shadow = texture2DCompare( shadowMap, shadowCoord.xy, shadowCoord.z );
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
return shadow;
|
||||
|
||||
}
|
||||
|
||||
// cubeToUV() maps a 3D direction vector suitable for cube texture mapping to a 2D
|
||||
// vector suitable for 2D texture mapping. This code uses the following layout for the
|
||||
// 2D texture:
|
||||
//
|
||||
// xzXZ
|
||||
// y Y
|
||||
//
|
||||
// Y - Positive y direction
|
||||
// y - Negative y direction
|
||||
// X - Positive x direction
|
||||
// x - Negative x direction
|
||||
// Z - Positive z direction
|
||||
// z - Negative z direction
|
||||
//
|
||||
// Source and test bed:
|
||||
// https://gist.github.com/tschw/da10c43c467ce8afd0c4
|
||||
|
||||
vec2 cubeToUV( vec3 v, float texelSizeY ) {
|
||||
|
||||
// Number of texels to avoid at the edge of each square
|
||||
|
||||
vec3 absV = abs( v );
|
||||
|
||||
// Intersect unit cube
|
||||
|
||||
float scaleToCube = 1.0 / max( absV.x, max( absV.y, absV.z ) );
|
||||
absV *= scaleToCube;
|
||||
|
||||
// Apply scale to avoid seams
|
||||
|
||||
// two texels less per square (one texel will do for NEAREST)
|
||||
v *= scaleToCube * ( 1.0 - 2.0 * texelSizeY );
|
||||
|
||||
// Unwrap
|
||||
|
||||
// space: -1 ... 1 range for each square
|
||||
//
|
||||
// #X## dim := ( 4 , 2 )
|
||||
// # # center := ( 1 , 1 )
|
||||
|
||||
vec2 planar = v.xy;
|
||||
|
||||
float almostATexel = 1.5 * texelSizeY;
|
||||
float almostOne = 1.0 - almostATexel;
|
||||
|
||||
if ( absV.z >= almostOne ) {
|
||||
|
||||
if ( v.z > 0.0 )
|
||||
planar.x = 4.0 - v.x;
|
||||
|
||||
} else if ( absV.x >= almostOne ) {
|
||||
|
||||
float signX = sign( v.x );
|
||||
planar.x = v.z * signX + 2.0 * signX;
|
||||
|
||||
} else if ( absV.y >= almostOne ) {
|
||||
|
||||
float signY = sign( v.y );
|
||||
planar.x = v.x + 2.0 * signY + 2.0;
|
||||
planar.y = v.z * signY - 2.0;
|
||||
|
||||
}
|
||||
|
||||
// Transform to UV space
|
||||
|
||||
// scale := 0.5 / dim
|
||||
// translate := ( center + 0.5 ) / dim
|
||||
return vec2( 0.125, 0.25 ) * planar + vec2( 0.375, 0.75 );
|
||||
|
||||
}
|
||||
|
||||
float getPointShadow( sampler2D shadowMap, vec2 shadowMapSize, float shadowBias, float shadowRadius, vec4 shadowCoord, float shadowCameraNear, float shadowCameraFar ) {
|
||||
|
||||
vec2 texelSize = vec2( 1.0 ) / ( shadowMapSize * vec2( 4.0, 2.0 ) );
|
||||
|
||||
// for point lights, the uniform @vShadowCoord is re-purposed to hold
|
||||
// the vector from the light to the world-space position of the fragment.
|
||||
vec3 lightToPosition = shadowCoord.xyz;
|
||||
|
||||
// dp = normalized distance from light to fragment position
|
||||
float dp = ( length( lightToPosition ) - shadowCameraNear ) / ( shadowCameraFar - shadowCameraNear ); // need to clamp?
|
||||
dp += shadowBias;
|
||||
|
||||
// bd3D = base direction 3D
|
||||
vec3 bd3D = normalize( lightToPosition );
|
||||
|
||||
#if defined( SHADOWMAP_TYPE_PCF ) || defined( SHADOWMAP_TYPE_PCF_SOFT )
|
||||
|
||||
vec2 offset = vec2( - 1, 1 ) * shadowRadius * texelSize.y;
|
||||
|
||||
return (
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.xyy, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.yyy, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.xyx, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.yyx, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.xxy, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.yxy, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.xxx, texelSize.y ), dp ) +
|
||||
texture2DCompare( shadowMap, cubeToUV( bd3D + offset.yxx, texelSize.y ), dp )
|
||||
) * ( 1.0 / 9.0 );
|
||||
|
||||
#else // no percentage-closer filtering
|
||||
|
||||
return texture2DCompare( shadowMap, cubeToUV( bd3D, texelSize.y ), dp );
|
||||
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
#endif
|
32
lib/renderers/shaders/ShaderChunk/shadowmap_pars_vertex.glsl
Normal file
32
lib/renderers/shaders/ShaderChunk/shadowmap_pars_vertex.glsl
Normal file
@ -0,0 +1,32 @@
|
||||
#ifdef USE_SHADOWMAP
|
||||
|
||||
#if NUM_DIR_LIGHTS > 0
|
||||
|
||||
uniform mat4 directionalShadowMatrix[ NUM_DIR_LIGHTS ];
|
||||
varying vec4 vDirectionalShadowCoord[ NUM_DIR_LIGHTS ];
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_SPOT_LIGHTS > 0
|
||||
|
||||
uniform mat4 spotShadowMatrix[ NUM_SPOT_LIGHTS ];
|
||||
varying vec4 vSpotShadowCoord[ NUM_SPOT_LIGHTS ];
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_POINT_LIGHTS > 0
|
||||
|
||||
uniform mat4 pointShadowMatrix[ NUM_POINT_LIGHTS ];
|
||||
varying vec4 vPointShadowCoord[ NUM_POINT_LIGHTS ];
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
#if NUM_RECT_AREA_LIGHTS > 0
|
||||
|
||||
// TODO (abelnation): uniforms for area light shadows
|
||||
|
||||
#endif
|
||||
*/
|
||||
|
||||
#endif
|
44
lib/renderers/shaders/ShaderChunk/shadowmap_vertex.glsl
Normal file
44
lib/renderers/shaders/ShaderChunk/shadowmap_vertex.glsl
Normal file
@ -0,0 +1,44 @@
|
||||
#ifdef USE_SHADOWMAP
|
||||
|
||||
#if NUM_DIR_LIGHTS > 0
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_DIR_LIGHTS; i ++ ) {
|
||||
|
||||
vDirectionalShadowCoord[ i ] = directionalShadowMatrix[ i ] * worldPosition;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_SPOT_LIGHTS > 0
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_SPOT_LIGHTS; i ++ ) {
|
||||
|
||||
vSpotShadowCoord[ i ] = spotShadowMatrix[ i ] * worldPosition;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_POINT_LIGHTS > 0
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_POINT_LIGHTS; i ++ ) {
|
||||
|
||||
vPointShadowCoord[ i ] = pointShadowMatrix[ i ] * worldPosition;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
#if NUM_RECT_AREA_LIGHTS > 0
|
||||
|
||||
// TODO (abelnation): update vAreaShadowCoord with area light info
|
||||
|
||||
#endif
|
||||
*/
|
||||
|
||||
#endif
|
@ -0,0 +1,61 @@
|
||||
float getShadowMask() {
|
||||
|
||||
float shadow = 1.0;
|
||||
|
||||
#ifdef USE_SHADOWMAP
|
||||
|
||||
#if NUM_DIR_LIGHTS > 0
|
||||
|
||||
DirectionalLight directionalLight;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_DIR_LIGHTS; i ++ ) {
|
||||
|
||||
directionalLight = directionalLights[ i ];
|
||||
shadow *= bool( directionalLight.shadow ) ? getShadow( directionalShadowMap[ i ], directionalLight.shadowMapSize, directionalLight.shadowBias, directionalLight.shadowRadius, vDirectionalShadowCoord[ i ] ) : 1.0;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_SPOT_LIGHTS > 0
|
||||
|
||||
SpotLight spotLight;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_SPOT_LIGHTS; i ++ ) {
|
||||
|
||||
spotLight = spotLights[ i ];
|
||||
shadow *= bool( spotLight.shadow ) ? getShadow( spotShadowMap[ i ], spotLight.shadowMapSize, spotLight.shadowBias, spotLight.shadowRadius, vSpotShadowCoord[ i ] ) : 1.0;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if NUM_POINT_LIGHTS > 0
|
||||
|
||||
PointLight pointLight;
|
||||
|
||||
#pragma unroll_loop
|
||||
for ( int i = 0; i < NUM_POINT_LIGHTS; i ++ ) {
|
||||
|
||||
pointLight = pointLights[ i ];
|
||||
shadow *= bool( pointLight.shadow ) ? getPointShadow( pointShadowMap[ i ], pointLight.shadowMapSize, pointLight.shadowBias, pointLight.shadowRadius, vPointShadowCoord[ i ], pointLight.shadowCameraNear, pointLight.shadowCameraFar ) : 1.0;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
#if NUM_RECT_AREA_LIGHTS > 0
|
||||
|
||||
// TODO (abelnation): update shadow for Area light
|
||||
|
||||
#endif
|
||||
*/
|
||||
|
||||
#endif
|
||||
|
||||
return shadow;
|
||||
|
||||
}
|
8
lib/renderers/shaders/ShaderChunk/skinbase_vertex.glsl
Normal file
8
lib/renderers/shaders/ShaderChunk/skinbase_vertex.glsl
Normal file
@ -0,0 +1,8 @@
|
||||
#ifdef USE_SKINNING
|
||||
|
||||
mat4 boneMatX = getBoneMatrix( skinIndex.x );
|
||||
mat4 boneMatY = getBoneMatrix( skinIndex.y );
|
||||
mat4 boneMatZ = getBoneMatrix( skinIndex.z );
|
||||
mat4 boneMatW = getBoneMatrix( skinIndex.w );
|
||||
|
||||
#endif
|
46
lib/renderers/shaders/ShaderChunk/skinning_pars_vertex.glsl
Normal file
46
lib/renderers/shaders/ShaderChunk/skinning_pars_vertex.glsl
Normal file
@ -0,0 +1,46 @@
|
||||
#ifdef USE_SKINNING
|
||||
|
||||
uniform mat4 bindMatrix;
|
||||
uniform mat4 bindMatrixInverse;
|
||||
|
||||
#ifdef BONE_TEXTURE
|
||||
|
||||
uniform sampler2D boneTexture;
|
||||
uniform int boneTextureSize;
|
||||
|
||||
mat4 getBoneMatrix( const in float i ) {
|
||||
|
||||
float j = i * 4.0;
|
||||
float x = mod( j, float( boneTextureSize ) );
|
||||
float y = floor( j / float( boneTextureSize ) );
|
||||
|
||||
float dx = 1.0 / float( boneTextureSize );
|
||||
float dy = 1.0 / float( boneTextureSize );
|
||||
|
||||
y = dy * ( y + 0.5 );
|
||||
|
||||
vec4 v1 = texture2D( boneTexture, vec2( dx * ( x + 0.5 ), y ) );
|
||||
vec4 v2 = texture2D( boneTexture, vec2( dx * ( x + 1.5 ), y ) );
|
||||
vec4 v3 = texture2D( boneTexture, vec2( dx * ( x + 2.5 ), y ) );
|
||||
vec4 v4 = texture2D( boneTexture, vec2( dx * ( x + 3.5 ), y ) );
|
||||
|
||||
mat4 bone = mat4( v1, v2, v3, v4 );
|
||||
|
||||
return bone;
|
||||
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
uniform mat4 boneMatrices[ MAX_BONES ];
|
||||
|
||||
mat4 getBoneMatrix( const in float i ) {
|
||||
|
||||
mat4 bone = boneMatrices[ int(i) ];
|
||||
return bone;
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#endif
|
13
lib/renderers/shaders/ShaderChunk/skinning_vertex.glsl
Normal file
13
lib/renderers/shaders/ShaderChunk/skinning_vertex.glsl
Normal file
@ -0,0 +1,13 @@
|
||||
#ifdef USE_SKINNING
|
||||
|
||||
vec4 skinVertex = bindMatrix * vec4( transformed, 1.0 );
|
||||
|
||||
vec4 skinned = vec4( 0.0 );
|
||||
skinned += boneMatX * skinVertex * skinWeight.x;
|
||||
skinned += boneMatY * skinVertex * skinWeight.y;
|
||||
skinned += boneMatZ * skinVertex * skinWeight.z;
|
||||
skinned += boneMatW * skinVertex * skinWeight.w;
|
||||
|
||||
transformed = ( bindMatrixInverse * skinned ).xyz;
|
||||
|
||||
#endif
|
12
lib/renderers/shaders/ShaderChunk/skinnormal_vertex.glsl
Normal file
12
lib/renderers/shaders/ShaderChunk/skinnormal_vertex.glsl
Normal file
@ -0,0 +1,12 @@
|
||||
#ifdef USE_SKINNING
|
||||
|
||||
mat4 skinMatrix = mat4( 0.0 );
|
||||
skinMatrix += skinWeight.x * boneMatX;
|
||||
skinMatrix += skinWeight.y * boneMatY;
|
||||
skinMatrix += skinWeight.z * boneMatZ;
|
||||
skinMatrix += skinWeight.w * boneMatW;
|
||||
skinMatrix = bindMatrixInverse * skinMatrix * bindMatrix;
|
||||
|
||||
objectNormal = vec4( skinMatrix * vec4( objectNormal, 0.0 ) ).xyz;
|
||||
|
||||
#endif
|
12
lib/renderers/shaders/ShaderChunk/specularmap_fragment.glsl
Normal file
12
lib/renderers/shaders/ShaderChunk/specularmap_fragment.glsl
Normal file
@ -0,0 +1,12 @@
|
||||
float specularStrength;
|
||||
|
||||
#ifdef USE_SPECULARMAP
|
||||
|
||||
vec4 texelSpecular = texture2D( specularMap, vUv );
|
||||
specularStrength = texelSpecular.r;
|
||||
|
||||
#else
|
||||
|
||||
specularStrength = 1.0;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#ifdef USE_SPECULARMAP
|
||||
|
||||
uniform sampler2D specularMap;
|
||||
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#if defined( TONE_MAPPING )
|
||||
|
||||
gl_FragColor.rgb = toneMapping( gl_FragColor.rgb );
|
||||
|
||||
#endif
|
@ -0,0 +1,41 @@
|
||||
#ifndef saturate
|
||||
#define saturate(a) clamp( a, 0.0, 1.0 )
|
||||
#endif
|
||||
|
||||
uniform float toneMappingExposure;
|
||||
uniform float toneMappingWhitePoint;
|
||||
|
||||
// exposure only
|
||||
vec3 LinearToneMapping( vec3 color ) {
|
||||
|
||||
return toneMappingExposure * color;
|
||||
|
||||
}
|
||||
|
||||
// source: https://www.cs.utah.edu/~reinhard/cdrom/
|
||||
vec3 ReinhardToneMapping( vec3 color ) {
|
||||
|
||||
color *= toneMappingExposure;
|
||||
return saturate( color / ( vec3( 1.0 ) + color ) );
|
||||
|
||||
}
|
||||
|
||||
// source: http://filmicgames.com/archives/75
|
||||
#define Uncharted2Helper( x ) max( ( ( x * ( 0.15 * x + 0.10 * 0.50 ) + 0.20 * 0.02 ) / ( x * ( 0.15 * x + 0.50 ) + 0.20 * 0.30 ) ) - 0.02 / 0.30, vec3( 0.0 ) )
|
||||
vec3 Uncharted2ToneMapping( vec3 color ) {
|
||||
|
||||
// John Hable's filmic operator from Uncharted 2 video game
|
||||
color *= toneMappingExposure;
|
||||
return saturate( Uncharted2Helper( color ) / Uncharted2Helper( vec3( toneMappingWhitePoint ) ) );
|
||||
|
||||
}
|
||||
|
||||
// source: http://filmicgames.com/archives/75
|
||||
vec3 OptimizedCineonToneMapping( vec3 color ) {
|
||||
|
||||
// optimized filmic operator by Jim Hejl and Richard Burgess-Dawson
|
||||
color *= toneMappingExposure;
|
||||
color = max( vec3( 0.0 ), color - 0.004 );
|
||||
return pow( ( color * ( 6.2 * color + 0.5 ) ) / ( color * ( 6.2 * color + 1.7 ) + 0.06 ), vec3( 2.2 ) );
|
||||
|
||||
}
|
5
lib/renderers/shaders/ShaderChunk/uv2_pars_fragment.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/uv2_pars_fragment.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#if defined( USE_LIGHTMAP ) || defined( USE_AOMAP )
|
||||
|
||||
varying vec2 vUv2;
|
||||
|
||||
#endif
|
6
lib/renderers/shaders/ShaderChunk/uv2_pars_vertex.glsl
Normal file
6
lib/renderers/shaders/ShaderChunk/uv2_pars_vertex.glsl
Normal file
@ -0,0 +1,6 @@
|
||||
#if defined( USE_LIGHTMAP ) || defined( USE_AOMAP )
|
||||
|
||||
attribute vec2 uv2;
|
||||
varying vec2 vUv2;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/uv2_vertex.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/uv2_vertex.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#if defined( USE_LIGHTMAP ) || defined( USE_AOMAP )
|
||||
|
||||
vUv2 = uv2;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/uv_pars_fragment.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/uv_pars_fragment.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#if defined( USE_MAP ) || defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( USE_SPECULARMAP ) || defined( USE_ALPHAMAP ) || defined( USE_EMISSIVEMAP ) || defined( USE_ROUGHNESSMAP ) || defined( USE_METALNESSMAP )
|
||||
|
||||
varying vec2 vUv;
|
||||
|
||||
#endif
|
6
lib/renderers/shaders/ShaderChunk/uv_pars_vertex.glsl
Normal file
6
lib/renderers/shaders/ShaderChunk/uv_pars_vertex.glsl
Normal file
@ -0,0 +1,6 @@
|
||||
#if defined( USE_MAP ) || defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( USE_SPECULARMAP ) || defined( USE_ALPHAMAP ) || defined( USE_EMISSIVEMAP ) || defined( USE_ROUGHNESSMAP ) || defined( USE_METALNESSMAP )
|
||||
|
||||
varying vec2 vUv;
|
||||
uniform mat3 uvTransform;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/uv_vertex.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/uv_vertex.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#if defined( USE_MAP ) || defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( USE_SPECULARMAP ) || defined( USE_ALPHAMAP ) || defined( USE_EMISSIVEMAP ) || defined( USE_ROUGHNESSMAP ) || defined( USE_METALNESSMAP )
|
||||
|
||||
vUv = ( uvTransform * vec3( uv, 1 ) ).xy;
|
||||
|
||||
#endif
|
5
lib/renderers/shaders/ShaderChunk/worldpos_vertex.glsl
Normal file
5
lib/renderers/shaders/ShaderChunk/worldpos_vertex.glsl
Normal file
@ -0,0 +1,5 @@
|
||||
#if defined( USE_ENVMAP ) || defined( DISTANCE ) || defined ( USE_SHADOWMAP )
|
||||
|
||||
vec4 worldPosition = modelMatrix * vec4( transformed, 1.0 );
|
||||
|
||||
#endif
|
Reference in New Issue
Block a user