Three.js car paint shader - recreating the Radeon 9700 demo

Recently while experimenting with three.js shader materials I stumbled across RenderMonkey . It is old software that is no longer supported and the description on the website says: "RenderMonkey is a rich shader development environment for both programmers and artists that facilitates the collaborative creation of real-time shader effects."

As I was going through the different shader examples that RenderMonkey comes with, I noticed a car paint shader which I remember was a demo when ATI released the Radeon 9700 back in 2002 (I actually had one of these video cards and the demo can be seen here ). As I have an interest in creating cars in Three.js, I thought it would be a good exercise to try to recreate the demo with a shader in Three.js.


  • I did not use the original model, I used a model available here as it was free and included a normal map which the original RenderMonkey shader used.
  • I computed normals form the normal map the same way as the PhongMaterial in three.js rather than the way it was done in the original shader.
  • The normal is quite rough, turn the normalScale down to see the effect with a more smooth surface.
  • I used a different environment map with a brightly lit floor so the reflections will look different. You can turn on the cube map with the controls on the right.
  • I am in no way a GLSL expert, I am barely even a novice and have pathetic math skills so there are probably better ways to do it or there may be errors. It was really just a learning experience for me that I thought I would share.
  • I really hate writing long blog posts so wont be
  • ...

Three.js standard materials vertex and fragment shaders reference

When playing around and experimenting with Three.js ShaderMaterial I often want to take a look at how the standard Three.js materials are done. Looking through the code or constantly outputting the shaders in the javascript console is a pain in the arse. I though I would post them here for future reference and in case anyone else was interested. These were output from Three.js version 70.

MeshBasicMaterial Vertex Shader
 #if defined( USE_MAP ) || defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( USE_SPECULARMAP ) || defined( USE_ALPHAMAP ) 

varying vec2 vUv;
uniform vec4 offsetRepeat;



varying vec2 vUv2;

#if defined( USE_ENVMAP ) && ! defined( USE_BUMPMAP ) && ! defined( USE_NORMALMAP ) && ! defined( PHONG )

varying vec3 vReflect;

uniform float refractionRatio;


#ifdef USE_COLOR

varying vec3 vColor;



uniform float morphTargetInfluences[ 8 ];


uniform float morphTargetInfluences[ 4 ];



uniform mat4 bindMatrix;
uniform mat4 bindMatrixInverse;


uniform sampler2D boneTexture;
uniform int boneTextureWidth;
uniform int boneTextureHeight;

mat4 getBoneMatrix( const in float i ) {

float j = i * 4.0;
float x = mod( j, float( boneTextureWidth ) );
float y = floor( j / float( boneTextureWidth

Experimenting with Three.js shaders and the ShaderMaterial

Lately when using Three.js I have needed some very specific material qualities that the built in Three.js materials did not allow for so I have started experimenting with the Three.ShaderMaterial . This material allows you to write you own GLSL shaders for Three.js. My hope is that I can get a good understanding of GLSL and implement some of my own shaders and materials in Three.js even with my limited math skills and no prior experience with GLSL.

On this page I will link to some of my own Three.ShaderMaterial experiments and try to update it as I learn more.

You may also want to take a look at my implementation of a three.js car paint shader (a recreartion of the Radeon 9700 demo).

NOTE: these examples are using R70 of THREE.js and material implementation seems to have changed a bit since the R70 release, so some of these may not work on the current release of THREE.js

Custom Mesh Shader Materials

On most of my experiments there are buttons under "Source" to view both the vertex shader source and the fragment shader source.

  • Basic color

    basic color shader

    This is the most basic of shaders, simple applying a color via the fragment shader.

  • Vertex position color

    Vertex position color shader

    Takes the fragment color from the vertex position. Simple experiment trying to understand how to send varyings from the vertex shader to the fragment shader

  • Uv position color

    Uv position color shader

    Takes the fragment color from the uv position. Again trying to understand how to send varyings from the vertex shader to the fragment shader

  • ...