import java.applet.Applet; import java.awt.*; import java.util.*; public class mandelbrot extends Applet { int Ybordersize = 30, accuracy; double xrange, yrange, xoffset, yoffset; int Xwindowsize, Ywindowsize; int Xdrawsize, Ydrawsize, dragx, dragy; static int x1, y1, x2, y2; String raise_accuracy_text = "Accuracy X2", reset_button_text = "Reset"; String constrain_ratio_text = "Maintain Aspect Ratio"; boolean constrain_ratio = true; Checkbox constrain_checkbox; boolean mouseReleased = true; public void init(){ Button increase_accuracy, reset; reset = new Button (reset_button_text); increase_accuracy = new Button (raise_accuracy_text); constrain_checkbox = new Checkbox (constrain_ratio_text, null, true); /** Later use object.reshape(x, y, xsize, ysize); **/ add(reset); add(increase_accuracy); add(constrain_checkbox); initialize_values(); Xwindowsize = size().width; Ywindowsize = size().height; Xdrawsize = Xwindowsize; Ydrawsize = Ywindowsize - Ybordersize; } public void initialize_values() { accuracy = 256; xrange = 4; yrange = 4; xoffset = -2; yoffset = -2; } public void paint(Graphics g){ if(!mouseReleased){ /* if(constrain_ratio){ if(dragx - x1 > dragy - y1){ g.drawRect(x1, y1 + Ybordersize, dragx - x1, y1 + (dragx - x1) - Ybordersize); }else{ g.drawRect(x1, y1 + Ybordersize, x1 + (dragy - y1), dragy - y1 - Ybordersize); } }else */ g.drawRect(x1, y1 + Ybordersize, dragx - x1, dragy - y1 - Ybordersize); }else{ render_image(g); } } public void update(Graphics g) { if(mouseReleased) render_image(g); else{ g.drawRect(x1, y1 + Ybordersize, dragx - x1, dragy - y1 - Ybordersize); } //g.drawLine(x1, y1, dragx, dragy); } public boolean mouseDrag(Event evt, int x, int y){ dragx = x - 1; dragy = y - 2; repaint(); return true; } public boolean mouseDown (Event evt, int x, int y) { mouseReleased = false; x1 = x - 1; y1 = y - 2 - Ybordersize; return (true); } public boolean mouseUp (Event evt, int x, int y) { int deltax, deltay; mouseReleased = true; x2 = x; y2 = y - Ybordersize; if(x2 < x1){ x2 ^= x1; x1 ^= x2; x2 ^= x1; } if(y2 < y1){ y2 ^= y1; y1 ^= y2; y2 ^= y1; } if(constrain_ratio){ deltax = x2 - x1; deltay = y2 - y1; if(deltax > deltay) y2 = y1 + deltax; else if(deltay > deltax) x2 = x1 + deltay; } if(x2 - x1 != 0 && y2 - y1 != 0){ xoffset += xrange * (double)x1 / (double)Xdrawsize; yoffset += yrange * (double)y1 / (double)Ydrawsize; xrange *= (double)(x2 - x1) / (double)Xdrawsize; yrange *= (double)(y2 - y1) / (double)Ydrawsize; repaint(); } return (true); } private void render_image(Graphics g){ int x, y; Color c; for(x = 0; x < Xdrawsize; x++){ for(y = 0; y < Ydrawsize; y++){ c = calc_colour(x, y); g.setColor(c); g.drawLine(x, y + Ybordersize, x, y + Ybordersize); } } } private Color calc_colour(int x, int y){ Color returnval; double c = (xrange / (double)Xdrawsize) * (double)x + (double)xoffset; double ci = (yrange / (double)Ydrawsize) * (double)y + (double)yoffset; int count = 0; double z = 0, zi = 0, zsq = 0; double zisq = 0, nz = 0, nzi = 0; while((count <= accuracy) && ((zsq + zisq) < 4.)){ nz = zsq - zisq; nzi = (z * zi) * 2.; z = nz + c; zi = nzi + ci; zsq = z * z; zisq = zi * zi; count++; } if(count > accuracy) returnval = new Color(0, 0, 0); else returnval = new Color( 128 - (int)(128. * Math.sin((float)count / 20.)), 128 - (int)(128. * Math.cos((float)count / 20.)), 128 + (int)(128. * Math.sin((float)count / 20.)) ); return returnval; } public boolean handleEvent(Event evt) { Rectangle rect; rect = constrain_checkbox.bounds(); if((evt.id == Event.ACTION_EVENT) && (evt.arg == raise_accuracy_text)){ accuracy *= 2; repaint(); }else if((evt.id == Event.ACTION_EVENT) && (evt.arg == reset_button_text)){ initialize_values(); repaint(); }else if((evt.id == Event.ACTION_EVENT) && (evt.x == rect.x) && (evt.y == rect.y)){ constrain_ratio = !constrain_ratio; } return super.handleEvent(evt); } }