Test Program | Simulation interface | ControlFrame | ControlMenu |
Table | Plot | WorldGraphics | SimFormat |
The simphy package is designed to implement some basic tasks that are useful in many simulations of physical systems. Objects can be created from the classes in this package without knowing the details of how the classes are written. However, we also list the classes below for interested users who may wish to modify or extend them. Any class that uses the simphy package must include the statement import simphy.*; at the beginning of the file containing the class. In the following we list the classes and describe what they do and how they can be used. If you are using Metrowerks CodeWarrior then the simphy package jar file must be added to your project.
ControlFrameString Blist[] = {"start", "stop", "reset"}; String Llist[] = {"Temperature", "Lattice Size"}; double Tlist[] = {2.2,64}; ControlFrame cf = new ControlFrame(S, Llist, Tlist, Blist);This example creates three buttons and two TextFields with Labels below them. When a button is pressed or a TextField changed, another object needs to know. To accomplish this communication, the object S must implement the interface Simulation. Why do we use an interface? Why not just write a class with the necessary methods? The answer is that the interface lets ControlFrame have an instantiation of any class as an argument as long as that class implements the Simulation interface. Any class that implements Simulation must include the methods shown in the following example.
public class Example implements Simulation { public void buttonAction(int k) { // respond to Buttons numbered from 0 to number of Buttons - 1 } public void textAction(int k, double x) { // respond to TextFields numbered from 0 to number of TextFields - 1 } public void menuAction(int k) { // respond to Menus that perform actions numbered from 0 to number of Menu items - 1 } public void dialogAction(int k, double x) { // respond to Menus that call up dialog boxes numbered from 0 to number of Menu items - 1 } }This interface is used with ControlMenu also. In method textAction and dialogAction, the double x is the value entered into a TextField by the user.
ControlMenu
This class has the same functionality as ControlFrame. Two Menus
are created, one called "Actions" and one called "Parameters" which play the same role as the
Buttons and TextFields, respectively. The constructor for ControlMenu works in the same way as
the constructor for ControlFrame. Before using the ControlMenu you must first attach
the menubar to a frame:
fr.setMenuBar(cm.sBar); // fr = Frame object , cm = ControlMenu object
Table
This class displays a table of formated numbers separated by tabs in a Frame. The
constructor arguments are the TableName and a String array of table headings for the columns. The
class contains methods for setting formats for the entries to the table, adding entries to a row (one at
a time or up to the first 5 entries at once), and displaying a row. The Table can be copied from the
Frame and pasted directly into a spreadsheet or plotting program. Below we show an example.
"String h[] = {"Column A","Column B","Column C"}; Table tb = new Table("Example Table",h); String pattern[] = {"#.0000", "#.00","#.000"}; tb.setFormat(pattern,10); // width of each column is 10 characters tb.setEntry(0,3.173); // set zeroth element of row tb.setEntry(1,999.9173); // set first element of row tb.setEntry(2,3891.73); // set second element of row tb.displayEntries(); // display first row tb.setEntries(3317.3,99.173,817.3); // set all three elements of row at once tb.displayEntries(); // display second rowThe result of the above code is to produce a table that looks like the following:
Column A Column B Column C 3.1730 999.91 3891.730 3317.3000 99.17 817.300In some cases you may wish to show the entire table all at once to avoid flicker as each row is shown. To do this use the constructor Table(String TableName, String h[],int FieldSize, boolean visibility) with visibility set equal to false. When all the entries to the table have been displayed, then call showTable() to see the table on the screen. Plot
public Plot(String title, String xLabel, String yLabel, int nAxes, double xmin,double xmax, double ymin, double ymax, int symbolSize, String symbolType int xsize, int ysize, int xloc, int yloc) /* nAxes = 1, one bottom horizontal axis, ymin should = 0 nAxes = 2, one left vertical axis, one bottom horizontal axis, xmin and ymin should = 0 nAxes = 3, one center vertical axis, one bottom horizontal axis, xmin should = -xmax, ymin should = 0 nAxes = 4, crossed axes, xmin should = -xmax and ymin should = -ymax nAxes = 5, crossed axes, only x > 0, xmin should = 0 and ymin should = -ymax nAxes = anything else, no axes drawn. symbolType = "fillsquare" or "opensquare" or "opencircle" or "fillcircle" symbolSize = 1 for point (default), otherwise gives size in pixels */ public void plotPoints(double x[], double y[]); public void plotPoint(double x, double y); // Plot one point public void plotCurve(double x[], double y[]); public void clear(); // clears frame on buffer public void clearPoints(); // clears frame and replots axes public void setColor(String s);WorldGraphics
public WorldGraphics(String title, double xmin,double xmax, double ymin, double ymax, int size, int xLoc, int yLoc)
The offscreen buffer can be used to do animation and speed up graphics. To do this call the method setToScreen(false), which will cause all subsequent drawing methods to draw only to the offscreen buffer and not to the screen. Then to draw the buffer to the screen, call drawBuffer(). Animation can be achieved for an image moving from one place to another by clearing the old location of the image using clearRect(x,y,dx,dy), drawing the image at the new location, and then calling drawBuffer().
SimFormatSimFormat.dformat(33.12765,3); // returns 33.127 SimFormat.eformat(-0.00364); // returns -3.640 E-3 SimFormat.aformat(-3078.6,2,1.0,10.0); // returns -3.07 E3 SimFormat.aformat(-3078.6); // returns -3.078 E3 // default values are min = 0.001, max = 100, d = 3Test Program
A test program showing how these classes are instantiated and used is shown below. Try running this program and testing the Buttons, TextFields, and menu items. Find the code in the program for the things you see on the screen.
import simphy.*; public class Test implements Simulation { ControlFrame cf; ControlMenu cm ; WorldGraphics wg; public static void main(String args[]) { Test u = new Test(); } public Test() { String h[] = {"zero","first","second"}; Table tb = new Table("test",h); String pattern[] = {"#.0000", "#.00","#.000"}; tb.setFormat(pattern,10); tb.setEntry(0,3.173); tb.setEntry(1,999.9173); tb.setEntry(2,3891.73); tb.displayEntries(); tb.setEntries(3317.3,99.173,817.3); tb.displayEntries(); String lString[] = {"zero", "one", "two","three", "four", "five","six", "seven", "eight"}; String bString[] = {"A", "B", "C","D", "E", "F","G", "H", "I"}; double initialP[] = { 1,2,3,4,5,6,7,8,9}; ControlFrame cf = new ControlFrame(this,lString,initialP,bString); ControlMenu cm = new ControlMenu(this,lString,initialP,bString); WorldGraphics wg = new WorldGraphics("Visualization",0,10,0,10, 500, 200,200); wg.setMenuBar(cm.sBar); } public void buttonAction(int k) { double x[] = {0,1,2,3,4}; double y[] = {0,1,2,3,4}; switch(k) { case 0: Plot p = new Plot("y vs x","xxxx","yyyy",1,-5,5,0,5);p.plotPoints(x,y);break; case 1: Plot p1 = new Plot("y vs x","xxxx","yyyy",2,-5,5,0,5);p1.plotPoints(x,y);break; case 2: Plot p2 = new Plot("y vs x","xxxx","yyyy",3,-5,5,0,5);p2.plotPoints(x,y);break; case 3: Plot p3 = new Plot("y vs x","xxxx","yyyy",4,-5,5,0,5);p3.plotPoints(x,y);break; } } public void textAction(int k, double x) { System.out.println(x); cf.setText(0,x); cf.setText(1,(int) x); cf.setText(2,"hello " + String.valueOf(k)); } public void menuAction(int k) { switch(k) { case 0: wg.drawRect(5,5,4,4.0); break; case 1: wg.drawString("good job", 7.0,2.0);break; case 2: wg.drawLine(0,0,10,10);break; case 3: wg.drawRect(200,200,100,100);break; case 4: wg.drawCircle(5,5,3);break; case 5: wg.clearRect(0,0,10,10);break; case 6: wg.setColor("yellow");break; case 7: wg.setColor("green");break; case 8: wg.setColor("random");break; } cf.texts[1].setText(String.valueOf(k)); // shows which menu selected in a TextField } public void dialogAction(int k, double x) { System.out.println(x); } }
package simphy; public interface Simulation { // used with ControlFrame or ControlMenu public void buttonAction(int k); public void textAction(int k, double x); public void menuAction(int k); public void dialogAction(int k, double x); }
ControlFrame
package simphy; import java.awt.*; import java.awt.event.*; public class ControlFrame extends Frame { public TextField texts[]; Label labels[]; Button buttons[]; Simulation S; String lString[], bString[]; double x[]; public ControlFrame(Simulation S, String lString[], String bString[]) { this.S = S; this.lString = lString; this.bString = bString; int nT = lString.length; x = new double[nT]; for(int i = 0; i < nT;i++) x[i] = 0.0; setUpFrame(); } public ControlFrame(Simulation S, String lString[], double x[], String bString[]) { this.S = S; this.lString = lString; this.bString = bString; this.x = x; setUpFrame(); } public void setUpFrame() { int ix = 20, iy = 20,bxT = 100,by = 20, ysep = 80, lsep = 20; int fSize = 0, bx; int nT = lString.length; // number of textfields int nB = bString.length; // number of buttons for (int i = 0; i < nB; i++) fSize += 20 + max(bString[i].length()*10,bxT); for (int i = 0; i < nT; i++) fSize += 20 + max(lString[i].length()*10,bxT); if(fSize < 500) setSize(fSize, ysep); else { setSize(500, (2 + fSize/500)*ysep); fSize = 500; } setTitle("Controls"); this.S = S; setLayout(null); texts = new TextField[nT]; // new array of textfields labels = new Label[nT]; // new array of labels buttons = new Button[nB]; // new array of buttons for(int i = 0; i < nB;i++) { bx = max(bString[i].length()*10,bxT); // button size if(ix + bx + 20 > fSize) { ix = 20; iy += ysep; } buttons[i] = new Button(bString[i]); // new button buttons[i].addActionListener(new B(i)); // add listener buttons[i].setSize(bx,by); buttons[i].setLocation(ix,iy); add(buttons[i]); // add button ix += bx + 20; } for(int i = 0; i < nT;i++) { bx = max(lString[i].length()*10,bxT); // label size if(ix + bx + 20 > fSize) { ix = 20; iy += ysep; } labels[i]= new Label(lString[i]); // new label for textfield labels[i].setSize(bx,by); labels[i].setLocation(ix,iy+lsep); add(labels[i]); // add label if( (int) x[i] == x[i]) texts[i]= new TextField(String.valueOf( (int) x[i])); // new textfield else texts[i]= new TextField(String.valueOf(x[i])); // new textfield texts[i].addActionListener( new T(i)); // add listener texts[i].setSize(bxT,by); texts[i].setLocation(ix,iy); add(texts[i]); // add textfield ix += bx + 20; } setVisible(true); } private int max(int a, int b) { if ( a > b) return a; else return b; } public void setText(int k, String s) { texts[k].setText(s); } public void setText(int k, int x) { texts[k].setText(String.valueOf(x)); } public void setText(int k, double x) { texts[k].setText(String.valueOf(x)); } // Inner classes class B implements ActionListener { int k; // kth button public B(int k) { this.k = k; } public void actionPerformed(ActionEvent e) { S.buttonAction(k); } } class T implements ActionListener { int k; // kth TextField public T(int k) { this.k = k; } public void actionPerformed(ActionEvent e) { Double R = new Double(texts[k].getText().trim()); S.textAction(k,R.doubleValue()); } } }
ControlMenu
package simphy; import java.awt.*; import java.awt.event.*; public class ControlMenu { public MenuBar sBar; // declare menubar Menu bMenu,tMenu; // declare two menus MenuItem bItems[]; // declare array of menu items MenuItem tItems[]; // declare array of menu items Simulation S; String lString[], bString[]; public double x[]; public ControlMenu(Simulation S, String lString[], String bString[]) { this.S = S; this.lString = lString; this.bString = bString; int nT = lString.length; x = new double[nT]; for(int i = 0; i < nT;i++) x[i] = 0.0; setUpMenu(); } public ControlMenu(Simulation S, String lString[], double x[], String bString[]) { this.S = S; this.lString = lString; this.bString = bString; this.x = x; setUpMenu(); } public void setUpMenu() { sBar = new MenuBar(); // assign menubar bMenu = new Menu("Actions"); // assign menu tMenu = new Menu("Parameters"); // assign menu sBar.add(bMenu); // add menu to menubar sBar.add(tMenu); // add menu to menubar int nB = bString.length; bItems = new MenuItem[nB]; // assign array of menu items int nT = lString.length; tItems = new MenuItem[nT]; // assign array of menu items for(int i = 0; i < nT;i++) { tItems[i] = new MenuItem(lString[i]); // assign menu item to array element tItems[i].addActionListener( new T(i)); tMenu.add(tItems[i]); } // add menu item to menu for(int i = 0; i < nB;i++) { bItems[i] = new MenuItem(bString[i]); // assign menu item to array element bItems[i].addActionListener( new B(i)); bMenu.add(bItems[i]); // add menu item to menu } } class B implements ActionListener { int k; public B(int k) { this.k = k; } public void actionPerformed(ActionEvent e) { S.menuAction(k); } } class T implements ActionListener { int k; public T(int k) { this.k = k; } public void actionPerformed(ActionEvent e) { InputDialog d = new InputDialog(S,k,lString[k],x); } } } package simphy; import java.awt.*; import java.awt.event.*; class InputDialog extends Frame // Used with ControlMenu { TextField newValueText; double x[]; public InputDialog(Simulation S,int k, String lString, double x[]) { this.x = x; setTitle("Dialog Box"); setSize(250,250); setLocation(50,50); setLayout(null); Label label = new Label("Enter new " + lString); label.setSize(150,20); label.setLocation(50,20); add(label); Button b1 = new Button("Okay"); b1.addActionListener( new OkayClass(k,S)); Button b2 = new Button("Cancel"); b2.addActionListener( new CancelClass()); b1.setLocation(30,80); b2.setLocation(150,80); b1.setSize(70,20); b2.setSize(70,20); add(b1); add(b2); newValueText = new TextField(String.valueOf(x[k])); newValueText.setSize(80,20); newValueText.setLocation(50,50); add(newValueText); setVisible(true); } class OkayClass implements ActionListener { int k; Simulation S; public OkayClass(int k, Simulation S) { this.k = k; this.S = S; } public void actionPerformed(ActionEvent e) { String s = newValueText.getText(); Double R = new Double(s.trim()); S.dialogAction(k,R.doubleValue()); x[k] = R.doubleValue(); setVisible(false); dispose(); } } class CancelClass implements ActionListener { public void actionPerformed(ActionEvent e) { setVisible(false); dispose(); } } }
Table
package simphy; import java.awt.*; import java.text.*; public class Table extends Frame { protected double entry[]; int n; public TextArea t; DecimalFormat number[]; int FieldSize = 10; public Table(String TableName, String h[],int FieldSize, boolean visibility) { this.FieldSize = FieldSize; n = h.length; entry = new double[n]; number = new DecimalFormat[n]; setTitle(TableName); setSize(90*n,500); t = new TextArea(); add(t); t.setEditable(true); setVisible(visibility); // set visibility to false and use showTable to show all at once setHeadings(h); String pattern[] = new String[n]; for(int i = 0; i < n ; i++) pattern[i] = "#.000"; setFormat(pattern,FieldSize); } public Table(String TableName, String h[]) { // sets up Table with default formats this(TableName,h,10,true); } public Table(String TableName, String h[], int FieldSize) { this(TableName,h,FieldSize,true); } public void showTable() { setVisible(true); } public void setHeadings(String h[]) { int len; setFont(new Font("Monospaced",Font.BOLD,10)); for(int i = 0; i < n ; i++) { len = h[i].length(); if(len < FieldSize) for(int j = 0; j < FieldSize-len;j++) h[i] = " " + h[i]; t.append(h[i] + "\t"); } t.append("\n" + "\n"); } public void println(String S) { t.append(S + "\n"); } public void setFormat(String pattern[],int FieldSize) { this.FieldSize = FieldSize; for(int i = 0; i < n ; i++) number[i] = new DecimalFormat(pattern[i]); } public void displayEntries() { int len,Eloc; String s; setFont(new Font("Monospaced",Font.PLAIN,10)); for(int i = 0; i < n ; i++) { if(Math.abs(entry[i]) < 1.0E7) { s = number[i].format(entry[i]); len = s.length(); } else{ s = String.valueOf(entry[i]); len = s.length(); Eloc = len; for(int j = 0; j < len;j++) if ( s.substring(j,j+1).equalsIgnoreCase("E"))Eloc = j; s = s.substring(0,4) + s.substring(Eloc,len); len = s.length(); } if(len < FieldSize) for(int j = 0; j < FieldSize-len;j++) s = " " + s; t.append(s + "\t"); } t.append("\n"); } public void setEntry(int i, double x) { entry[i] = x; } public void setEntries(double x0, double x1) { entry[0] = x0; entry[1] = x1; } public void setEntries(double x0, double x1, double x2) { setEntries(x0,x1); entry[2] = x2; } public void setEntries(double x0, double x1, double x2, double x3) { setEntries(x0,x1,x2); entry[3] = x3; } public void setEntries(double x0, double x1, double x2, double x3, double x4) { setEntries(x0,x1,x2,x3); entry[4] = x4; } }
Plot
package simphy; import java.awt.*; public class Plot extends Frame{ double scalex,scaley,xmin,ymin,xmax,ymax; int nAxes; String xLabel,yLabel; int mg = 30; int width,height; int symbolSize; String symbolType; Image buffer; Graphics b; public Plot(String title, String xLabel, String yLabel, int nAxes, double xmin,double xmax, double ymin, double ymax, int symbolSize, String symbolType, int xsize, int ysize, int xloc, int yloc) { this.nAxes = nAxes; this.xLabel = xLabel; this.yLabel = yLabel; this.xmin = xmin; this.ymin = ymin; this.xmax = xmax; this.ymax = ymax; this.symbolSize = symbolSize; setTitle(title); setSize(xsize,ysize); width = getSize().width; height = getSize().height; setLocation(xloc,yloc); setVisible(true); setScale(); buffer = createImage(getSize().width,getSize().height); b = buffer.getGraphics(); setAxes(); } public Plot(String title, String xLabel, String yLabel, int nAxes, double xmin,double xmax, double ymin, double ymax, int symbolSize, String symbolType) { this(title, xLabel, yLabel,nAxes, xmin, xmax, ymin, ymax, symbolSize, symbolType, 400, 400,150,150); } public Plot(String title, String xLabel, String yLabel, int nAxes, double xmin,double xmax, double ymin, double ymax) { this(title,xLabel,yLabel,nAxes,xmin,xmax,ymin,ymax,1,"dot",400,400,150,150); } public Plot(String title,double xmin,double xmax, double ymin, double ymax, int xsize, int ysize) { this(title,"","",0,xmin,xmax,ymin,ymax,1,"dot",xsize,ysize,150,150); } public Plot(String title,double xmin,double xmax, double ymin, double ymax, int xsize, int ysize, int xloc, int yloc) { this(title,"","",0,xmin,xmax,ymin,ymax,1,"dot",xsize,ysize,xloc,yloc); } public Plot(int nAxes, double xmin,double xmax, double ymin, double ymax) { this("Plot","x","y",nAxes,xmin,xmax,ymin,ymax,1,"dot",400,400,150,150); } private void setScale() { if(xmax > xmin) scalex = (getSize().width-2*mg)/(xmax-xmin); else { System.out.println("Error xmax not greater than xmin"); return; } if(ymax > ymin) scaley = (getSize().height-2*mg)/(ymax-ymin); else { System.out.println("Error ymax not greater than ymin"); return; } } public void setAxes() { int mg = 30; int ix,iy; if(width != getSize().width || height != getSize().height) { width = getSize().width; height = getSize().height; setScale(); } b.clearRect(0,0,getSize().width,getSize().height); switch (nAxes) { // draw axes and axis labels case 1: b.drawLine(mg,size().height-mg,size().width-mg,size().height-mg); b.drawString(xLabel,getSize().width/2,getSize().height-10); break; case 2: b.drawLine(mg,getSize().height-mg,mg,mg); b.drawLine(mg,getSize().height-mg,getSize().width-mg,size().height-mg); b.drawString(xLabel,getSize().width-2*mg,getSize().height-10); b.drawString(yLabel,10,20); break; case 3: b.drawLine(mg,size().height-mg,size().width-mg,size().height-mg); b.drawLine(size().width/2,size().height-mg,size().width/2,mg); b.drawString(xLabel,getSize().width-2*mg,getSize().height-10); b.drawString(yLabel,getSize().width/2,20); break; case 4: b.drawLine(mg,getSize().height/2,getSize().width-mg,getSize().height/2); b.drawLine(getSize().width/2,size().height-mg,getSize().width/2,mg); b.drawString(xLabel,getSize().width-2*mg,getSize().height/2+20); b.drawString(yLabel,getSize().width/2,20); break; case 5: b.drawLine(mg,getSize().height/2,getSize().width-mg,getSize().height/2); b.drawLine(mg,mg,mg,getSize().height-mg); b.drawString(xLabel,getSize().width-2*mg,getSize().height/2+20); b.drawString(yLabel,mg,20); break; } Graphics g = getGraphics(); g.drawImage(buffer,0,0,this); // draw image onto screen } public void clearPoints() { b.clearRect(0,0,getSize().width,getSize().height); setAxes(); } public void clear() { b.clearRect(0,0,getSize().width,getSize().height); } public void plotPoints(double x[],double y[]) { int ix,iy; for(int i = 0; i < x.length; i++) { // plot points ix = (int)((x[i]-xmin)*scalex) +mg; iy = getSize().height - (int)((y[i]-ymin)*scaley) - mg; if(symbolSize > 1) { if(symbolType == "fillsquare") b.fillRect(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); else if(symbolType == "opensquare") b.drawRect(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); else if(symbolType == "opencircle") b.drawOval(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); else b.fillOval(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); } else b.drawLine(ix,iy,ix,iy); } Graphics g = getGraphics(); g.drawImage(buffer,0,0,this); // draw image onto screen } public void plotPoint(double x,double y) { int ix,iy; // plot point ix = (int)((x-xmin)*scalex) +mg; iy = getSize().height - (int)((y-ymin)*scaley) - mg; if(symbolSize > 1) { if(symbolType == "fillsquare") b.fillRect(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); else if(symbolType == "opensquare") b.drawRect(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); else if(symbolType == "opencircle") b.drawOval(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); else b.fillOval(ix-symbolSize/2,iy-symbolSize/2,symbolSize,symbolSize); } else b.drawLine(ix,iy,ix,iy); Graphics g = getGraphics(); g.drawImage(buffer,0,0,this); // draw image onto screen } public void plotCurve(double x[],double y[]) { int ix1,iy1,ix2,iy2; ix1 = (int)((x[0]-xmin)*scalex) +mg; iy1 = size().height - (int)((y[0]-ymin)*scaley) - mg; for(int i = 1; i < x.length; i++) { // plot points ix2 = (int)((x[i]-xmin)*scalex) +mg; iy2 = size().height - (int)((y[i]-ymin)*scaley) - mg; b.drawLine(ix1,iy1,ix2,iy2); ix1 = ix2; iy1 = iy2; } Graphics g = getGraphics(); g.drawImage(buffer,0,0,this); // draw image onto screen } public void setColor(String s) { Color c = Color.black; if(s == "red") c = Color.red; else if(s == "blue") c = Color.blue; else if(s == "black") c = Color.black; else if(s == "green") c = Color.green; else if(s == "yellow") c = Color.yellow; else if(s == "white") c = Color.white; else if(s == "magenta") c = Color.magenta; else if(s == "cyan") c = Color.cyan; else if(s == "orange") c = Color.orange; else if(s == "pink") c = Color.pink; else if(s == "random") c = new Color((int) (Math.random()*255), (int) (Math.random()*255), (int) (Math.random()*255)); b.setColor(c); } public void paint(Graphics g) { if(getSize().width != width || getSize().height != height) { width = getSize().width; height = getSize().height; setScale(); buffer = createImage(getSize().width,getSize().height); b = buffer.getGraphics(); } g.drawImage(buffer,0,0,this); // draw image onto screen } }
WorldGraphics
package simphy; /* Creates Frame for drawing on using world coordinates. y increases as you move up, x increases as you move right. Unless otherwise specified methods use world coordinates. */ import java.awt.*; public class WorldGraphics extends Frame { double scalex,scaley,xmin,ymin,xmax,ymax; int width,height; Image buffer; Graphics b; Color c = Color.black; boolean toScreen = true; // draw to screen as well as buffer public WorldGraphics(String title, double xmin,double xmax, double ymin, double ymax, int size, int xLoc, int yLoc) { this.xmin = xmin; this.ymin = ymin; this.xmax = xmax; this.ymax = ymax; double f = (ymax-ymin)/(xmax-xmin); setTitle(title); setSize(size,(int)(size*f)); width = getSize().width; height = getSize().height; setScale(); setLocation(xLoc,yLoc); setVisible(true); buffer = createImage(getSize().width,getSize().height); b = buffer.getGraphics(); } public WorldGraphics(String title, double xmin,double xmax, double ymin, double ymax) { // old version this.xmin = xmin; this.ymin = ymin; this.xmax = xmax; this.ymax = ymax; double f = (ymax-ymin)/(xmax-xmin); setTitle(title); setSize(360,(int)(360*f)); width = getSize().width; height = getSize().height; setScale(); setLocation(200,100); setVisible(true); buffer = createImage(getSize().width,getSize().height); b = buffer.getGraphics(); } public void setScale() { if(xmax > xmin) { scalex = (getSize().width)/(xmax-xmin); } else { System.out.println("Error xmax not greater than xmin"); return; } if(ymax > ymin) { scaley = (getSize().height)/(ymax-ymin); } else { System.out.println("Error ymax not greater than ymin"); return; } } private int scrX(double x) { return (int)((x-xmin)*scalex); } private int scrY(double y) { return getSize().height - (int)((y-ymin)*scaley); } private int scrDX(double dx) { return (int)(dx*scalex); } private int scrDY(double dy) { return (int)(dy*scaley); } public void setToScreen(boolean toScreen) { this.toScreen = toScreen; } public void drawLine(double x1, double y1, double x2, double y2) { b.drawLine(scrX(x1),scrY(y1),scrX(x2),scrY(y2)); if (toScreen) repaint(); } public void drawPoint(double x1, double y1) { b.drawLine(scrX(x1),scrY(y1),scrX(x1),scrY(y1)); if (toScreen) repaint(); } public void fillRect(double x, double y, double dx, double dy) { b.fillRect(scrX(x),scrY(y)-scrDY(dy),scrDX(dx),scrDY(dy)); if (toScreen) repaint(); } public void drawRect(double x, double y, double dx, double dy) { b.drawRect(scrX(x),scrY(y)-scrDY(dy),scrDX(dx),scrDY(dy)); if (toScreen) repaint(); } public void drawRect(int x, int y, int dx, int dy) { // uses screen coordinates b.drawRect(x,y,dx,dy); if (toScreen) repaint(); } public void fillRect(int x, int y, int dx, int dy) { // uses screen coordinates b.fillRect(x,y,dx,dy); if (toScreen) repaint(); } public void fillOval(double x, double y, double dx, double dy) { b.fillOval(scrX(x),scrY(y)-scrDY(dy),scrDX(dx),scrDY(dy)); if (toScreen) repaint(); } public void drawOval(double x, double y, double dx, double dy) { b.drawOval(scrX(x),scrY(y)-scrDY(dy),scrDX(dx),scrDY(dy)); if (toScreen) repaint(); } public void drawCircle(double x, double y, double r) { b.drawOval(scrX(x)-scrDX(r),scrY(y)-scrDY(r),scrDX(2*r),scrDY(2*r)); if (toScreen) repaint(); } public void fillCircle(double x, double y, double r) { b.fillOval(scrX(x)-scrDX(r),scrY(y)-scrDY(r),scrDX(2*r),scrDY(2*r)); if (toScreen) repaint(); } public void clearRect(double x, double y, double dx, double dy) { b.clearRect(scrX(x),scrY(y)-scrDY(dy),scrDX(dx),scrDY(dy)); if (toScreen) repaint(); } public void clearBuffer() { b.clearRect(scrX(xmin),scrY(ymin)-scrDY(ymax-ymin),scrDX(xmax-xmin),scrDY(ymax-ymin)); } public void clearLine(double x1, double y1, double x2, double y2) { // erase line Color cSave = c; b.setColor(getBackground()); drawLine(x1,y1,x2,y2); b.setColor(cSave); } public void drawString(String s, double x, double y) { b.drawString(s, scrX(x),scrY(y)); if (toScreen) repaint(); } public void drawString(String s, int x, int y) { //uses screen coordinates b.drawString(s,x,y); if (toScreen) repaint(); } public void setColor(int red, int green, int blue) { c = new Color(red,green,blue); b.setColor(c); } public void setColor(String s) { if(s == "red") c = Color.red; else if(s == "blue") c = Color.blue; else if(s == "black") c = Color.black; else if(s == "green") c = Color.green; else if(s == "yellow") c = Color.yellow; else if(s == "white") c = Color.white; else if(s == "magenta") c = Color.magenta; else if(s == "cyan") c = Color.cyan; else if(s == "orange") c = Color.orange; else if(s == "pink") c = Color.pink; else if(s == "random") c = new Color((int) (Math.random()*255), (int) (Math.random()*255), (int) (Math.random()*255)); b.setColor(c); } public void drawBuffer() { Graphics g = getGraphics(); g.drawImage(buffer,0,0,this); // draw image onto screen, useful for animation } public void paint(Graphics g) { if(getSize().width != width || getSize().height != height) { width = getSize().width; height = getSize().height; setScale(); buffer = createImage(getSize().width,getSize().height); b = buffer.getGraphics(); } g.drawImage(buffer,0,0,this); // draw image onto screen } }
SimFormat
package simphy; import java.text.DecimalFormat; public abstract class SimFormat { public static String dformat(double x, int d) { DecimalFormat df = new DecimalFormat(); df.setMinimumIntegerDigits(1); df.setMaximumFractionDigits(d); df.setMinimumFractionDigits(d); df.setGroupingUsed(false); return df.format(x); } public static String dformat(double x) { return dformat(x,3); } public static String eformat(double x, int d) { if(x == 0) return "0"; if(x < 0) { double y = Math.log(-x)/Math.log(10); int p = (int) y; double dec = Math.pow(10,y-p); if(dec <= 1) return "-" + dformat(10*dec,d) + " E" + String.valueOf(p-1); else return "-" + dformat(dec,d) + " E" + String.valueOf(p); } else { double y = Math.log(x)/Math.log(10); int p = (int) y; double dec = Math.pow(10,y-p); if(dec <= 1) return dformat(10*dec,d) + " E" + String.valueOf(p-1); else return dformat(dec,d) + " E" + String.valueOf(p); } } public static String eformat(double x) { return eformat(x,3); } public static String aformat(double x, int d, double min, double max) { if(Math.abs(x) > max || Math.abs(x) < min) return eformat(x,d); else return dformat(x,d); } public static String aformat(double x, double min, double max) { return aformat(x,3,min,max); } public static String aformat(double x) { return aformat(x,3,0.001,100); } }
Updated 20 May 2000.