/////////////////////////////////////////////////////////////////////////////// // GetBumpedNormal function // Takes an object, the current normal value and the current texture // position. Uses the current texture position as the location in the object's // bump texture pointer to find the amount by which to perturb the current // normal. // N_bar = normal + D // D = (PuFv - PvFu) x N / ||N|| // // INPUT: // object: The object being drawn. // normal: The current normal. // texPos: The current texture position. /////////////////////////////////////////////////////////////////////////////// Vector3D GetBumpedNormal(Object &object, Vector3D &normal, Vector3D &texPos) { // Local var. to adjust and return. Vector3D bumped = normal; // Scale factor used for steepness float S = 0.001; // Get Pu & Pv Vector3D Pu(1,0,0); Vector3D Pv(0,1,0); // get values of u,v between 0..1 float u = texPos[U] / texPos[W_PRIME]; float v = texPos[V] / texPos[W_PRIME]; // Width and height of the bump map int width = object.bump->width-1; int height = object.bump->height-1; // Convert fraction value of u,v to ints for array of bump texture u *= width; v *= height; int i = static_cast(u); int j = static_cast(v); // Find values in bump at four points around u,v // Fi,j int bottomLeft = *(object.bump->byte(i,j,1)); // Fi+1,j int bottomRight = *(object.bump->byte(i+1,j,1)); // Fi,j+1 int topLeft = *(object.bump->byte(i,j+1,1)); // Fi+1,j+1 int topRight = *(object.bump->byte(i+1,j+1,1)); // vars used to blend those values float U0 = i + 1 - u; float U1 = u - i; float V0 = j + 1 - v; float V1 = v - j; // Get Fu & Fv float Fu = V0 * ( bottomRight - bottomLeft ) + V1 * ( topRight - topLeft ); Fu *= S; float Fv = U0 * ( topLeft - bottomLeft ) + U1 * ( topRight - bottomRight ); Fv *= S; // D = (PuFv - PvFu) x N Pu *= Fv; Pv *= Fu; Vector3D D = (Pu - Pv); // D = () X N D = Cross(D,normal); // N_bar = normal + D bumped += D; return bumped; }