// Reverse Julia, Evgeny Demidov, 1 June 2003 import java.awt.*; import java.awt.image.*; import java.awt.event.*; import java.util.StringTokenizer; public class RJulia extends java.applet.Applet implements MouseListener, MouseMotionListener{ double Ymid, Xmid, DelX=3., Cr, Ci, R = 1., sin[],cos[],Ri[],Ii[]; int MaxIt = 1000, N=0, w,h,w2,h2, pixArr[], xP[],yP[]; boolean showXY = true, painted = false; Image img; IndexColorModel iColor; Color[] Col = {new Color(0f,.7f,0f), Color.red, Color.magenta, new Color(0f,.8f,.8f), new Color(.9f,.9f,0f)}; TextField tfXY; public void init() { String s=getParameter("XYmidDel"); if (s != null) { StringTokenizer st = new StringTokenizer(s); Xmid = Double.valueOf(st.nextToken()).doubleValue(); Ymid = Double.valueOf(st.nextToken()).doubleValue(); DelX = Double.valueOf(st.nextToken()).doubleValue(); Cr = Double.valueOf(st.nextToken()).doubleValue(); Ci = Double.valueOf(st.nextToken()).doubleValue();} s=getParameter("R"); if (s != null) R=Double.valueOf(s).doubleValue(); s=getParameter("MaxIt"); if (s != null) MaxIt=Integer.parseInt(s); s=getParameter("N"); if (s != null) N=Integer.parseInt(s); byte rColor[] = new byte[2], bColor[] = new byte[2], gColor[] = new byte[2]; rColor[0] = gColor[0] = bColor[0] = (byte)255; rColor[1] = gColor[1] = bColor[1] = (byte)0; iColor = new IndexColorModel( 8, 2, rColor,gColor,bColor); w = getSize().width; h = getSize().height; s=getParameter("showXY"); if ( (s != null) && (s.equalsIgnoreCase("N")) ) showXY = false; else{ setLayout(new BorderLayout()); if (Ymid < 0.) s = ""+Xmid+" "+Ymid+"*i; "+(float)DelX; else s = ""+Xmid+" +"+Ymid+"*i; "+(float)DelX; tfXY = new TextField( s ); add("South", tfXY); h -= tfXY.getPreferredSize().height;} h2 = h/2; w2 = w/2; pixArr = new int[w*h]; sin = new double[50]; cos = new double[50]; Ri = new double[50]; Ii = new double[50]; xP = new int[51]; yP = new int[51]; for (int i=0; i < 50; i++){ double f = i*Math.PI/49; sin[i] = Math.sin(f); cos[i] = Math.cos(f);} addMouseListener(this); addMouseMotionListener(this); } public void destroy() { removeMouseListener(this); removeMouseMotionListener(this); } public void mouseClicked(MouseEvent e) {} //1.1 event handling public void mousePressed(MouseEvent e) {} public void mouseEntered(MouseEvent e) {} public void mouseExited(MouseEvent e) {} public void mouseReleased(MouseEvent e) { if ( (e.isAltDown() )||(e.isControlDown() ) ){ painted = false; Xmid = Xmid+(e.getX()-w/2)*DelX/w; Ymid = Ymid-(e.getY()-h/2)*DelX/w; if ( e.isControlDown() ) { if ( e.isShiftDown() ) DelX *=4.; else DelX *=2.;} else { if ( e.isShiftDown() ) DelX /=4.; else DelX /=2.;} if (showXY) { if (Ymid < 0.) tfXY.setText( ""+(float)Xmid+" "+(float)Ymid+"*i; " +(float)DelX); else tfXY.setText( ""+(float)Xmid+" +"+(float)Ymid+"*i; " +(float)DelX);}; repaint();} } public void mouseMoved(MouseEvent e){} //1.1 event handling public void mouseDragged(MouseEvent e) { int x = e.getX(), y = h - e.getY(); double dy = Ymid-(e.getY()-h/2)*DelX/w, dx = Xmid+(e.getX()-w/2)*DelX/w; R = Math.sqrt(dx*dx + dy*dy); repaint(); } public void paint(Graphics g) { if ( !painted ) Draw(); g.drawImage(img, 0, 0, this); if (DelX > 0.1) drawLabel(g); showStatus( "R=" + (float)R ); } public void drawLabel(Graphics gra) { double StZ=DelX/w; gra.setColor(Color.black); int ix,iy; String s=getParameter("sqrRID"); if (s != null) { StringTokenizer st = new StringTokenizer(s); double sqrRmid = Double.valueOf(st.nextToken()).doubleValue(), sqrImid = Double.valueOf(st.nextToken()).doubleValue(); int sqr = (int)(Double.valueOf(st.nextToken()).doubleValue()/StZ); ix = (w - sqr)/2 + (int)((sqrRmid-Xmid)/StZ); iy = (h - sqr)/2 + (int)((Ymid - sqrImid) /StZ); gra.drawRect(ix,iy, sqr,sqr);} gra.setFont( new Font( gra.getFont().getName(), Font.BOLD, 15 ) ); int maxLabel=0; while (true) { s=getParameter("lb"+maxLabel); if (s == null) break; StringTokenizer st = new StringTokenizer(s); double x=(Double.valueOf(st.nextToken()).doubleValue()-Xmid)/StZ, y=(Ymid-Double.valueOf(st.nextToken()).doubleValue())/StZ; if ( (Math.abs(x) 0){ int ir = (int)(R/StZ); double Re,Ro, Im; ix = -(int)(Xmid/StZ) - ir + w2; iy = (int)(Ymid/StZ) - ir + h2; gra.setColor(Color.blue); gra.drawOval(ix,iy, 2*ir,2*ir); for (int i=0; i<50; i++){ Ri[i] = R*cos[i]; Ii[i] = R*sin[i];} for (int it=0; it < N; it++){ for (int i=0; i < 50; i++){ Re = Ro = Ri[i]; Im = Ii[i]; Re = Re*Re - Im*Im +Cr; Im = 2.*Im*Ro + Ci; Ri[i] = Re; Ii[i] = Im; xP[i] = (int)((Re - Xmid)/StZ) + w2; yP[i] = -(int)((Im - Ymid)/StZ) + h2;} xP[50] = xP[0]; yP[50] = yP[0]; gra.setColor(Col[it % 5]); gra.drawPolygon(xP,yP, 51);}} } public void Draw(){ double Re,Im,Io,A, St = DelX/w; int ix,iy; Re = 1.; Im = 0.; for (int it=0; it < w*h; it++) pixArr[it] = 0; for (int it=0; it <= MaxIt; it++){ Re -= Cr; Im -= Ci; Io = Im; A = Math.sqrt(Re*Re+Im*Im); Im = Math.sqrt(.5*(A-Re)); Re = Math.sqrt(.5*(A+Re)); if (Io < 0.) Im = -Im; if (Math.random() < .5){ Re = -Re; Im = -Im;} ix = (int)((Re - Xmid)/St) + w2; iy = -(int)((Im - Ymid)/St) + h2; if ((ix >= 0)&&(ix < w)&&(iy >= 0)&&(iy < h)) pixArr[ix+iy*w] = 1; ix = (int)((-Re - Xmid)/St) + w2; iy = (int)((Im + Ymid)/St) + h2; if ((ix >= 0)&&(ix < w)&&(iy >= 0)&&(iy < h)) pixArr[ix+iy*w] = 1; } img = createImage(new MemoryImageSource(w, h, iColor, pixArr, 0, w)); painted = true; } }