package graphics; public class Sphere { public Vector3 center; public double radius; //public int[] color = {0, 0, 0}; //shape's colors private double shininess; private int[] diffuseColor = {0,0,0}; private int[] specularColor = {0,0,0}; public void setDiffuse(int r, int g, int b) { diffuseColor[0] = r; diffuseColor[1] = g; diffuseColor[2] = b; } public void setSpecular(double s, int r, int g, int b) { shininess = s; specularColor[0] = r; specularColor[1] = g; specularColor[2] = b; } //takes a surface coordinate, array of lights, ambient component, and //returns color public int[] shade(double[] pos, Light[] lights, int[] ambient) { double nx = pos[0] - center.get(0), ny = pos[1] - center.get(1), nz = pos[2] - center.get(2); Vector3 eye = new Vector3(0, 0, 1); //eye/camera is at the origin looking at neg z //eye.normalize(); Vector3 normal = new Vector3(nx, ny, nz); normal.normalize(); //normal.scale(-1); //System.err.println("in shade()"); //System.err.println(nx+","+ny+","+nz); double r = 0, g = 0, b = 0; for (int li = 0; li < lights.length; li++) { //colors for this light double lr = 0, lg = 0, lb = 0; //diffuse shading // f is L dot N double fDiff = normal.dotProduct( lights[li].getDirectionVector() ); if (fDiff < 0) fDiff = 0; //System.err.println("fDiff = " + fDiff); lr += fDiff * diffuseColor[0]; lg += fDiff * diffuseColor[1]; lb += fDiff * diffuseColor[2]; //specular shading //R = 2*f*N - L //Ls = [rs,gs,bs]max(0, E ∙ R)^p Vector3 R = new Vector3(normal); //copy normal vector R.scale(-2 * fDiff); // r is now -2fN R.add( lights[li].getDirectionVector() ); //r is now L - 2fN R.scale(-1); R.normalize(); double fSpec = Math.pow(eye.dotProduct(R), shininess); //E ∙ R if (fSpec < 0) fSpec = 0; //System.err.println("fSpec = " + fSpec); lr += fSpec * specularColor[0]; lg += fSpec * specularColor[1]; lb += fSpec * specularColor[2]; //factor in light source, but //scale back down (compare 0.5 * 0.5 with (128 * 128)/256) lr *= lights[li].color[0] / 256.0; lg *= lights[li].color[1] / 256.0; lb *= lights[li].color[2] / 256.0; //add the light to object's light r += lr; g += lg; b += lb; } //add ambient component r += ambient[0]; g += ambient[1]; b += ambient[2]; if (r > 255) r = 255; if (g > 255) g = 255; if (b > 255) b = 255; //System.err.println(r+","+g+","+b); int[] rgb = {0,0,0}; //copy color info back into shape rgb[0] = (int)r; rgb[1] = (int)g; rgb[2] = (int)b; //System.err.println(rgb[0]+","+rgb[1]+","+rgb[2]); return rgb; } }