Files
martinfencl.eu/locenice/js/legacy-shaders.js
T
2026-10-22 01:22:01 +02:00

34 lines
3.4 KiB
JavaScript

// Retained offline fallback shaders from the supplied prototype.
const vs = `#version 300 es
precision highp float;
layout(location=0) in vec3 position;
layout(location=1) in vec3 normal;
layout(location=2) in vec2 texCoord;
layout(location=3) in vec4 tangent;
uniform mat4 uVP; uniform mat4 uLightVP; uniform vec2 uUvScale;
out vec3 vNormal; out vec3 vWorld; out vec4 vShadow; out vec2 vUv; out vec4 vTangent;
void main(){vUv=texCoord*uUvScale;vTangent=tangent;vWorld=position;vNormal=normal;vShadow=uLightVP*vec4(position,1.);gl_Position=uVP*vec4(position,1.);}`;
const fs = `#version 300 es
precision highp float;
in vec3 vNormal; in vec3 vWorld; in vec4 vShadow; in vec2 vUv; in vec4 vTangent;
uniform vec4 uColor; uniform vec3 uEye; uniform vec3 uLight;
uniform float uInteriorMaterial; uniform float uInteriorFill; uniform float uInteriorStyle;
uniform float uSurfaceKind; uniform sampler2D uBaseMap; uniform sampler2D uNormalMap; uniform float uNormalScale;
uniform sampler2D uShadow; uniform float uGlass; uniform float uMetal; uniform float uRoughness;
uniform vec3 uAmbient; uniform vec3 uSunColor; uniform float uDirect; uniform float uSkyDay; uniform float uShadows;
out vec4 outColor;
vec3 srgbToLinear(vec3 c){return mix(c/12.92,pow((c+.055)/1.055,vec3(2.4)),step(vec3(.04045),c));}
float shade(vec3 n){if(uShadows<.5||uDirect<.001)return 1.;vec3 p=vShadow.xyz/vShadow.w*.5+.5;if(p.x<0.||p.x>1.||p.y<0.||p.y>1.||p.z>1.||p.z<0.)return 1.;float bias=max(.00045*(1.-max(dot(n,uLight),0.)),.00014);vec2 grad=vec2(0.);if(uSurfaceKind>.5){vec3 dx=dFdx(p),dy=dFdy(p);float det=dx.x*dy.y-dx.y*dy.x;if(abs(det)>1e-12)grad=vec2(dx.z*dy.y-dy.z*dx.y,dx.x*dy.z-dy.x*dx.z)/det;}float s=0.;for(int x=-1;x<=1;x++)for(int y=-1;y<=1;y++){vec2 uv=p.xy+vec2(float(x),float(y))/2048.;float d=texture(uShadow,uv).r;vec2 center=(floor(uv*2048.)+.5)/2048.;float receiver=p.z+dot(grad,center-p.xy);s+=receiver-bias<=d?1.:0.;}return s/9.;}
void main(){vec3 n=normalize(vNormal);if(!gl_FrontFacing)n=-n;vec3 gn=n;
if(uSurfaceKind>.5&&uSurfaceKind<1.5){vec3 t=normalize(vTangent.xyz-n*dot(n,vTangent.xyz));vec3 bt=normalize(cross(n,t))*vTangent.w;vec3 mn=texture(uNormalMap,vUv).xyz*2.-1.;mn.xy*=uNormalScale;n=normalize(mat3(t,bt,n)*mn);}
vec3 view=normalize(uEye-vWorld);float ndl=max(dot(n,uLight),0.);float sh=shade(gn);vec3 base=uSurfaceKind>.5?uColor.rgb:pow(uColor.rgb,vec3(2.2));
if((uSurfaceKind>.5&&uSurfaceKind<1.5)||uSurfaceKind>2.5)base*=srgbToLinear(texture(uBaseMap,vUv).rgb);vec3 ambient=uAmbient*(.84+.16*n.y)+vec3(uInteriorMaterial*uInteriorFill);vec3 col=base*(ambient+uSunColor*ndl*sh*uDirect);vec3 halfway=normalize(uLight+view);float spec=pow(max(dot(n,halfway),0.),mix(90.,8.,uRoughness));col+=uSunColor*spec*sh*(.018+uMetal*.15)*uDirect;
if(uGlass>.5){vec3 reflected=reflect(-view,n);float fres=pow(1.-max(dot(n,view),0.),4.);vec3 skycol=mix(vec3(.19,.26,.26),vec3(.50,.60,.64),smoothstep(-.25,.8,reflected.y));skycol*=mix(.035,1.,uSkyDay);col=mix(base*(ambient*.75),skycol,.32+fres*.48);col+=uSunColor*.14*pow(max(dot(n,halfway),0.),100.)*sh*uDirect;}
if(uInteriorStyle>.5)col=max(col,base*.85);
col=pow(max(col,vec3(0.)),vec3(1./2.2));outColor=vec4(clamp(col,0.,1.),uColor.a);}`;
const depthvs = `#version 300 es
precision highp float;layout(location=0) in vec3 position;uniform mat4 uVP;void main(){gl_Position=uVP*vec4(position,1.);}`;
const depthfs = `#version 300 es
precision highp float;void main(){}`;
export {vs, fs, depthvs, depthfs};