/* part of Stereographic Projection applet, copyright 1996 John M Sullivan */ import java.awt.*; import java.lang.*; public class SterPanel extends Panel { double zoom = 5.125; double prsp = 0; Tform sphere = new Tform(), world = new Tform(), incr; Tform camera; Tform proj = new Tform(2,0,0,0, 0,2,0,0, 0,0,1,-1, 0,0,-1,1); int chopping = 20; Image sph_img; String errmsg; Image back; Graphics bg; Dimension bsize = size(); boolean rotsphere = true; boolean busy = false; Color str_col = new Color(0.f,.4f,.6f), sph_col = new Color(.4f,0.f,.2f), prj_col = new Color(.7f,.5f,0.f); Vect polyh=Poly.cube, chopped; double lastx, lasty; public boolean drawstr=true, drawsph=true, drawsol=true, drawpln=true; SterPanel(Image s) { sph_img = s; } public void init(String p) { setpoly(p); } public void reset() { sphere = new Tform(); world = new Tform(); repaint(); } public void setrot(boolean r) { rotsphere = r; } public boolean mouseDown(Event e, int x, int y) { lastx = x; lasty = y; return true; } public boolean mouseDrag(Event e, int x, int y) { double thx = (x-lastx) * 6. / size().width; double thy = (y-lasty) * 6. / size().height; Tform incr = Tform.xrot(thy).compose(Tform.yrot(thx)); if (rotsphere) sphere = world.transpose().compose(incr). compose(world).compose(sphere); else world = incr.compose(world); repaint(); lastx = x; lasty = y; return true; } public boolean setpoly(String p) { boolean ok = true; polyh = Poly.cube; if (p==null) ok = false; //No polyhedron specified; using cube else if (p.equals("Cube")) polyh = Poly.cube; else if (p.equals("Octahedron")) polyh = Poly.oct; else if (p.equals("Tetrahedron")) polyh = Poly.tetr; else if (p.equals("Icosahedron")) polyh = Poly.icos; else if (p.equals("Dodecahedron")) polyh = Poly.dodec; else ok = false; //Bad polyhedron specified; using cube polyh.tosphere(); chopped = polyh.chop(chopping); chopped.tosphere(); return ok; } public void update(Graphics g) { if (!busy) { busy = true; paint(g); } } public void paint(Graphics g) { if (back == null || bsize.width!=size().width || bsize.height!=size().height) { back = createImage(size().width, size().height); bsize = size(); bg = back.getGraphics(); setcamera(); } if (back != null) { dopaint(bg); g.drawImage(back,0,0,this); } else dopaint(g); done(); } public void setcamera() { double s = size().width/zoom; camera = Tform.trans(size().width/2,size().height/2,0). compose(Tform.scale(s,s,1)). compose(Tform.scale(1,-1,1)). compose(Tform.perspective(prsp)); } public void setzoom(int slide) { zoom = slide*slide/800. + 2; setcamera(); repaint(); } public void setprsp(int slide) { prsp = slide/100.; setcamera(); repaint(); } public void dopaint(Graphics g) { Tform t1 = camera.compose(world); Tform t2 = t1.compose(sphere); g.setColor(Color.white); g.fillRect(0,0,size().width,size().height); if (world.e[2][2]>0 && drawpln) { g.setColor(prj_col); t1.compose(proj).compose(sphere).apply(chopped).paint(g); } if (drawsph) { g.setColor(sph_col); t2.apply(chopped).paint_back(g,prsp/(1-prsp*prsp)); } if (drawstr) { g.setColor(str_col); t2.apply(polyh).paint(g); } if (drawsol && prsp<1) { int sphsize = (int)(size().width/zoom/Math.sqrt(1-prsp*prsp)); g.drawImage(sph_img,size().width/2-sphsize,size().height/2-sphsize, 2*sphsize,2*sphsize,this); } if (drawsph) { g.setColor(sph_col); t2.apply(chopped).paint_front(g,prsp/(1-prsp*prsp)); } if (world.e[2][2]<=0 && drawpln) { g.setColor(prj_col); t1.compose(proj).compose(sphere).apply(chopped).paint(g); } } private synchronized void done() { busy = false; notifyAll(); } }