SimpleMortgageCalculator() {
super();
this.setUndecorated(true);
//this is where the settings from the last use are retrieved
try{
applicationProperties.load(new FileInputStream(CALCULATOR_CONFIG_FILE));
}
catch(Exception ex){
System.out.println("problem loading properties
file on startup "+ex.toString());
}
// Add the window listener
addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent evt) {
dispose();
System.exit(0);
}});
addMouseListener(this);
addMouseMotionListener(this);
//don't want this resizable, as it makes the background look odd
this.setResizable(false);
buttons=new Button[4];//calculate, skins, languages, quit
fields=new TextField[4];//Amount, Interest Term, Length in years, Results
labels=new Label[4];//Amount, Interest Term, Length in years, Results
buttons[CALCULATE]=new Button("");//calculate
buttons[SKINS]=new Button("");//skins
buttons[LANGUAGES]=new Button("");//languages
buttons[QUIT]=new Button("");//quit
buttons[CALCULATE].addActionListener(this);
buttons[SKINS].addActionListener(this);
buttons[LANGUAGES].addActionListener(this);
buttons[QUIT].addActionListener(this);
this.add(buttons[CALCULATE]);
this.add(buttons[SKINS]);
this.add(buttons[LANGUAGES]);
this.add(buttons[QUIT]);
fields[AMOUNT]=new TextField(15);//amount
fields[INTEREST]=new TextField(6);//interest
fields[TERM]=new TextField(4);//term in years
fields[RESULTS]=new TextField(10);//results
this.add(fields[AMOUNT]);
this.add(fields[INTEREST]);
this.add(fields[TERM]);
this.add(fields[RESULTS]);
labels[AMOUNT]=new Label("");//amount
labels[INTEREST]=new Label("");//interest
labels[TERM]=new Label("");//terms
labels[RESULTS]=new Label("");//results
this.add(labels[AMOUNT]);
this.add(labels[INTEREST]);
this.add(labels[TERM]);
this.add(labels[RESULTS]);
//this is where the last skin and language are reloaded
String lastSkin=applicationProperties.getProperty(LAST_SKIN_PROPERTY);
String lastLanguage=
applicationProperties.getProperty(LAST_LANGUAGE_PROPERTY);
if(lastSkin==null) lastSkin="downtown.jar";
if(lastLanguage==null) lastLanguage="english.properties";
SkinLoader.getInstance().loadNewSkin(lastSkin);
LanguageLoader.getInstance().loadNewLanguage(this, lastLanguage);
Dimension d=SkinLoader.getInstance().getSize();
setSize((int)d.getWidth(), (int)d.getHeight());
//Center the window
Dimension screenDim = Toolkit.getDefaultToolkit().getScreenSize();
Rectangle winDim = getBounds();
setLocation((screenDim.width - winDim.width) / 2,
(screenDim.height - winDim.height) / 2);
setVisible(true);
//need a visible window to render the image onto.
backgroundImage = SkinLoader.getInstance().getImage(this);
SkinLoader.getInstance().addWidgets(this, buttons, fields, labels);
}
Listing One: SimpleMortgageCalculator.
public void actionPerformed(ActionEvent e){
if(e.getSource()==buttons[CALCULATE]){//calculate button
double dResult=Calculate.crunch(fields[AMOUNT].getText(),
fields[INTEREST].getText(), fields[TERM].getText());
if(dResult>0.0){
fields[RESULTS].setText(""+(int)dResult);
}
else{
fields[RESULTS].setText(LanguageLoader.
getInstance().lookUpString("badresult"));
}
}
else if(e.getSource()==buttons[SKINS]){//skins button
SkinLoader.getInstance().chooseSkin(this);
//size is in the skin
Dimension d=SkinLoader.getInstance().getSize();
setSize((int)d.getWidth(), (int)d.getHeight());
//as is the image
backgroundImage = SkinLoader.getInstance().getImage(this);
//and the display area
this.paint(this.getGraphics());
//add controls
SkinLoader.getInstance().addWidgets(this, buttons, fields, labels);
}
else if(e.getSource()==buttons[LANGUAGES]){//languages
LanguageLoader.getInstance().chooseLanguage(this);
}
else if(e.getSource()==buttons[QUIT]){//quit button
try{
//remember what the last skin and language were
String lastSkin=SkinLoader.getInstance().getCurrentSkin();
String lastLanguage=LanguageLoader.getInstance().getCurrentLanguage();
applicationProperties.setProperty(LAST_SKIN_PROPERTY, lastSkin);
applicationProperties.setProperty(LAST_LANGUAGE_PROPERTY, lastLanguage);
applicationProperties.
store(new FileOutputStream(CALCULATOR_CONFIG_FILE),
"SimpleMortageCaculator properties file");
}
catch(Exception ex){
System.out.println("problem storing properties
file on shutdown "+ex.toString());
}
//write out the configuration file, then quit
exit();
}
}
Listing Two: actionPerformed method.
public void loadComponent(String skinFile){
try{
URL u = new URL("jar:file:skins/"+skinFile+"!/");
int index=skinFile.indexOf(".jar");
String thisClass=skinFile.substring(0, index);
String strClass="skins."+thisClass;//jar and main class files match
ucl = new URLClassLoader(new URL[] { u });
c= (Class) Class.forName(strClass, true, ucl);
m = c.getMethod(SKIN_METHOD, SKIN_METHOD_ARGS);
currentSkin=skinFile;
image=null;
}
catch(Exception ex){
System.out.println("exception in SkinLoader.loadComponent()
"+ex.toString());
}
}
Listing Three: loadComponent method.
//bundling a dimension for a call to the skin to get the dimension
Object oa[]=new Object[1];
oa[0]=new Dimension();
Integer IReturn=(Integer)m.invoke(c, new Object[] {oa, new Integer(1), new Integer(1) });
d=(Dimension)oa[0];
Listing Four: Bundling in SkinsLoader.
//fragment from the skinMethod in the skin where arguments are unbundled
public static Integer skinMethod(Object [] args, Integer callType, Integer callerVersion){
int type=callType.intValue();
switch(type){
case 1://call for size of the window
return new Integer(getSize((Dimension)args[0]));
//The getSize method in the skin sets the dimensions and then returns OK.
private static int getSize(Dimension d){
d.setSize(500, 300);
return OK;
}
Listing Five: Unbundling in the skin.
//code called in LanguageLoader to load the current language
public static void loadNewLanguage(String languageFile){
languageChangedFlag=true;
properties.clear();
try{
properties.load(new FileInputStream("languages/"+languageFile));
}
catch(IOException ioe){
System.out.println("problem loading language file "+ioe.toString());
}
frame.paint(frame.getGraphics());
}
Listing Six: loadNewLanguage method.
if (e.getSource()==list) {
// When the user double-clicks on a component, try to load it
if (e.getID() == Event.ACTION_EVENT) {
String strFile=list.getSelectedItem();
ComponentInfo ci=(ComponentInfo)hashComponents.get(strFile);
//if the component is not yet on the file system, download it
if(!ci.getDownloaded()){
this.setTitle("Downloading "+ci.getFileName());
RemoteComponentLoader.requestComponent(ci.getLocation(),
directory+"/"+ci.getFileName());
}
loader.loadComponent(strFile);
this.dispose();
}
}
Listing Seven: Loading a component.