Skip to content

Material Effect Shaders

Special effect shaders for stylized and dynamic materials including toon shading, holograms, dissolve transitions, and more.

import {
toonVertexShader,
toonFragmentShader,
hologramVertexShader,
hologramFragmentShader,
dissolveVertexShader,
dissolveFragmentShader,
forcefieldVertexShader,
forcefieldFragmentShader,
glitchVertexShader,
glitchFragmentShader,
} from '@strata-game-library/shaders';

Cel-shading with customizable color bands:

UniformTypeDescription
uColorvec3Base color
uLightDirectionvec3Light direction
uBandsintNumber of shade bands
uOutlineWidthfloatOutline thickness
uOutlineColorvec3Outline color
import { toonVertexShader, toonFragmentShader } from '@strata-game-library/shaders';
const toonMaterial = new THREE.ShaderMaterial({
vertexShader: toonVertexShader,
fragmentShader: toonFragmentShader,
uniforms: {
uColor: { value: new THREE.Color(0xff6b6b) },
uLightDirection: { value: new THREE.Vector3(1, 1, 1).normalize() },
uBands: { value: 4 },
uOutlineWidth: { value: 0.03 },
uOutlineColor: { value: new THREE.Color(0x000000) },
},
});

Sci-fi holographic effect with scanlines and flicker:

UniformTypeDescription
uTimefloatAnimation time
uColorvec3Hologram color
uOpacityfloatBase opacity
uScanlineSpeedfloatScanline movement
uScanlineCountfloatNumber of scanlines
uFlickerSpeedfloatFlicker frequency
uRimPowerfloatRim light intensity
import { hologramVertexShader, hologramFragmentShader } from '@strata-game-library/shaders';
const hologramMaterial = new THREE.ShaderMaterial({
vertexShader: hologramVertexShader,
fragmentShader: hologramFragmentShader,
uniforms: {
uTime: { value: 0 },
uColor: { value: new THREE.Color(0x00ffff) },
uOpacity: { value: 0.5 },
uScanlineSpeed: { value: 2 },
uScanlineCount: { value: 100 },
uFlickerSpeed: { value: 10 },
uRimPower: { value: 2 },
},
transparent: true,
side: THREE.DoubleSide,
});

Noise-based dissolve transition effect:

UniformTypeDescription
uProgressfloatDissolve progress (0-1)
uNoiseTexturesampler2DNoise pattern
uEdgeColorvec3Dissolve edge color
uEdgeWidthfloatEdge glow width
uBaseTexturesampler2DObject texture
import { dissolveVertexShader, dissolveFragmentShader } from '@strata-game-library/shaders';
const dissolveMaterial = new THREE.ShaderMaterial({
vertexShader: dissolveVertexShader,
fragmentShader: dissolveFragmentShader,
uniforms: {
uProgress: { value: 0 },
uNoiseTexture: { value: noiseTexture },
uEdgeColor: { value: new THREE.Color(0xff4400) },
uEdgeWidth: { value: 0.1 },
uBaseTexture: { value: objectTexture },
},
transparent: true,
});
// Animate dissolve
gsap.to(dissolveMaterial.uniforms.uProgress, {
value: 1,
duration: 2,
ease: 'power2.out',
});

Energy shield / forcefield effect:

UniformTypeDescription
uTimefloatAnimation time
uColorvec3Shield color
uOpacityfloatBase opacity
uFresnelPowerfloatEdge glow falloff
uPulseSpeedfloatPulse animation speed
uHexScalefloatHexagon pattern scale
uImpactPointvec3Impact location
uImpactStrengthfloatImpact ripple strength
uImpactTimefloatTime since impact
import { forcefieldVertexShader, forcefieldFragmentShader } from '@strata-game-library/shaders';
const forcefieldMaterial = new THREE.ShaderMaterial({
vertexShader: forcefieldVertexShader,
fragmentShader: forcefieldFragmentShader,
uniforms: {
uTime: { value: 0 },
uColor: { value: new THREE.Color(0x00aaff) },
uOpacity: { value: 0.3 },
uFresnelPower: { value: 3 },
uPulseSpeed: { value: 2 },
uHexScale: { value: 10 },
uImpactPoint: { value: new THREE.Vector3(0, 0, 1) },
uImpactStrength: { value: 0 },
uImpactTime: { value: 0 },
},
transparent: true,
side: THREE.DoubleSide,
depthWrite: false,
});

Digital glitch / corruption effect:

UniformTypeDescription
uTimefloatAnimation time
uIntensityfloatGlitch intensity
uBlockSizefloatGlitch block size
uColorShiftfloatRGB shift amount
uScanlinesboolEnable scanlines
uBaseTexturesampler2DSource texture
import { glitchVertexShader, glitchFragmentShader } from '@strata-game-library/shaders';
const glitchMaterial = new THREE.ShaderMaterial({
vertexShader: glitchVertexShader,
fragmentShader: glitchFragmentShader,
uniforms: {
uTime: { value: 0 },
uIntensity: { value: 0.5 },
uBlockSize: { value: 30 },
uColorShift: { value: 0.02 },
uScanlines: { value: true },
uBaseTexture: { value: texture },
},
});
float toonShade(vec3 normal, vec3 lightDir, int bands) {
float NdotL = dot(normal, lightDir);
float shade = (NdotL * 0.5 + 0.5);
shade = floor(shade * float(bands)) / float(bands);
return shade;
}
float scanlines(vec2 uv, float time, float count, float speed) {
float line = sin((uv.y + time * speed) * count * 3.14159);
return smoothstep(0.0, 0.5, line);
}
float dissolveEdge(float noise, float progress, float edgeWidth) {
float edge = smoothstep(progress - edgeWidth, progress, noise);
edge *= smoothstep(progress + edgeWidth, progress, noise);
return edge;
}
float fresnel(vec3 viewDir, vec3 normal, float power) {
return pow(1.0 - max(dot(viewDir, normal), 0.0), power);
}