// ****** The Java AWT Pendulum Annimation Applet ***** // **** Version 2 uses image double-buffering and time correction ***** import java.awt.Image; import java.awt.Button; import java.awt.Event; import java.awt.FlowLayout; import java.awt.TextField; import java.awt.Graphics; import java.awt.Insets; import java.awt.Label; import java.awt.Font; import java.awt.Color; import java.awt.Rectangle; import java.awt.FontMetrics; public class penduldb extends java.applet.Applet implements Runnable { Image offscreenIm; Graphics offscreenGr; Thread runner; final float pi = 3.141592653f ; int xtie, xp, yp, xold, yold; //width and height of plot. int pendWrite = 110; //vertical height of pendulum region to paint. int wApp, hApp, dispDelay; public float grav, leng, omega, phase, thetao=pi/10; // pendulum parameters. String inParm; Color bgnd = Color.white; String slabel = "Length = "; Label l1; long timeNow, tRef; public void init() { // get speed parameter from html file. wApp = this.size().width; hApp = this.size().height; offscreenIm = createImage(wApp, pendWrite); offscreenGr = offscreenIm.getGraphics(); Font f = new Font("TimesRoman", Font.PLAIN, 10); FontMetrics fm = getFontMetrics(f); setFont(f) ; inParm=getParameter("gravity") ; if (inParm==null) // if no user input in html file. grav=9.80f; // m/sec^2 else grav = Float.valueOf(inParm).floatValue(); inParm=getParameter("length") ; if (inParm==null) // if no user input in html file. leng=1.0f; // meters. else leng = Float.valueOf(inParm).floatValue(); inParm=getParameter("displayDelay") ; if (inParm==null) // if no user input in html file. dispDelay=500; //half a second default. else dispDelay = Integer.parseInt(inParm); setLayout(new FlowLayout()); Button fast = new Button("Faster"); Button slow = new Button("Slower"); l1 = new Label(slabel+(int)(leng*100)+"cm"); add(l1); add(slow); add(fast); } // end of init. public Insets insets() { return new Insets(pendWrite+2,2,2,2); } public void start() { if (runner == null) { runner = new Thread(this); runner.start(); } } public void stop() { if (runner != null) { runner.stop(); runner = null; } } public void pause(long time) { try { Thread.sleep(time);} // wait for time milliseconds. catch (InterruptedException e) { } } public void run() { omega =(float) (1E-3*Math.sqrt(grav/leng) ); // System.out.println("\n-------- Applet Data --------"); // System.out.println("Applet Width = "+wApp); // System.out.println("Applet Height = "+hApp); // System.out.println("-------- Pendulum Data --------"); // System.out.println("Pendulum Length = " + leng + " meters"); // System.out.println("Gravity = " + grav + " m/sec^2"); // System.out.println("Expected period = " + 2*pi/(omega*1000) +" secs"); xtie=wApp/2 ; // center applet tie point. timeNow = tRef = System.currentTimeMillis(); //start time. while (true) { omega =(float) (1E-3*Math.sqrt(grav/leng) ); phase = (float) (thetao*Math.sin(omega*(timeNow-tRef)) ); xp =(int) (xtie - 100*Math.sin(phase) ); //current values yp =(int) ( 100*Math.cos(phase) ); repaint(); timeNow += dispDelay ; pause(Math.max(0, timeNow - System.currentTimeMillis())); //System.out.println("Time: " +System.currentTimeMillis()) ; } } public void update(Graphics g) { //override update method. paint(g); } public void paint(Graphics g) { if (timeNow > dispDelay) { //don't draw at start time. offscreenGr.setColor(bgnd); offscreenGr.fillRect(0,0,wApp,pendWrite); // remove anything from other interrupts. offscreenGr.setColor(Color.black) ; offscreenGr.drawLine(xtie,0,xp,yp) ; offscreenGr.setColor(Color.red) ; offscreenGr.fillOval(xp-5, yp-5, 10, 10) ; //draw circle centered at end point of pendulum. } else { offscreenGr.setColor(bgnd); //for viewers that don't automatically set the backgnd. offscreenGr.fillRect(0,0,wApp,pendWrite); } g.drawImage(offscreenIm,0,0,this); //write buffered image to screen. } public boolean action(Event evt, Object arg) { //intercept AWT action. if (evt.target instanceof Button) adjustSpeed((String)arg); return true; } // ------------ Handler for Button Press ---------------- void adjustSpeed( String buttonName) { if (buttonName.equals("Faster")){ leng = leng/1.5f; //increase speed by 50% each click. if (leng*1000<1) leng = 1; // set shortest pendulum. l1.setText(slabel + (int)(leng*100)+"cm"); // display in cm. } if (buttonName.equals("Slower")) { leng =leng*1.5f; l1.setText(slabel +(int)(leng*100)+"cm"); } } public String getAppletInfo() { return "Copyright 1996 Michel I. Gallant"; } }