As this flowchart of the program details, it is designed to create a loan amoritization table based on either user defined terms, or presets. It can even load new presets from a CSV file. CSV was chosen because it is a simple format supported by even the most basic spreadsheet programs.
And the Payment Loop:
This is the code for the project. Project guidelines required the code to be in a single file, so it may seem a little long and disorganized.
/**********************************************************************
* Program: Mortgage Payment
* Purpose: Week 3 Individual Assignment
* Programmer: Dylan Sloboda
* Class: PRG/421
* Instructor: Vince Anderson
* Creation Date: March 5, 2012
***********************************************************************
* Program Summary:
* Amoritization Calculator for change request 5.
*
**********************************************************************/
import java.awt.BorderLayout;
import java.awt.Component;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.BoxLayout;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.text.DecimalFormat;
import java.util.StringTokenizer;
public class AmoritizationCalc extends JFrame implements ActionListener // class definition
{
/**
*
*/
private static final long serialVersionUID = 1L;
double [][] loanTIA;{
loanTIA = new double[3][2]; //This array holds 2 arrays consisting of the loan terms and interest rates
loanTIA[0][0] = 84;
loanTIA[0][1] = 0.0535;
loanTIA[1][0] = 180;
loanTIA[1][1] = 0.055;
loanTIA[2][0] = 360;
loanTIA[2][1] = 0.0575;}
JTextField principleTxt = new JTextField(7);
JTextField termTxt = new JTextField(3);
JTextField interestTxt = new JTextField(4);
JCheckBox optionOne = new JCheckBox("7 Years at 5.35%");
JCheckBox optionTwo = new JCheckBox("15 Years at 5.5%");
JCheckBox optionThree = new JCheckBox("30 Years at 5.75%");
JButton calcButton = new JButton("Calculate");
JButton loadOpt = new JButton("Load terms from file");
JTextArea pymntAmtTxt = new JTextArea("Monthly payment");
JPanel principle = new JPanel();
JPanel term = new JPanel();
JPanel interest = new JPanel();
JPanel loanOptions = new JPanel();
JPanel loanTerms = new JPanel();
JScrollPane scrollingResult = new JScrollPane(pymntAmtTxt);
JPanel bottomPanel = new JPanel();
JPanel topPanel = new JPanel();
JPanel wholePane = new JPanel();
public AmoritizationCalc() // constructor
{
principle.add(principleTxt);
principle.add(new JLabel("Principle"), BorderLayout.WEST);
term.add(termTxt);
term.add(new JLabel("Loan Term (months)"), BorderLayout.WEST);
interest.add(interestTxt);
interest.add(new JLabel("Interest rate(as decimal)"), BorderLayout.WEST);
loanOptions.add(optionOne);
loanOptions.add(optionTwo);
loanOptions.add(optionThree);
loanOptions.add(loadOpt, BorderLayout.SOUTH);
loanOptions.setLayout(new BoxLayout(loanOptions, BoxLayout.PAGE_AXIS));
bottomPanel.setLayout(new BoxLayout(bottomPanel, BoxLayout.PAGE_AXIS));
bottomPanel.add(scrollingResult, BorderLayout.SOUTH);
loanTerms.add(principle, BorderLayout.LINE_START);
loanTerms.add(term, BorderLayout.LINE_START);
loanTerms.add(interest, BorderLayout.LINE_START);
loanTerms.setLayout(new BoxLayout(loanTerms, BoxLayout.PAGE_AXIS));
topPanel.add(loanTerms, BorderLayout.WEST);
topPanel.add(loanOptions, BorderLayout.EAST);
wholePane.add(topPanel, BorderLayout.NORTH);
wholePane.add(calcButton);
calcButton.setAlignmentX(Component.CENTER_ALIGNMENT);
wholePane.add(bottomPanel, BorderLayout.SOUTH);
wholePane.setLayout(new BoxLayout(wholePane, BoxLayout.PAGE_AXIS)); // Box layout requires arguments
getContentPane().add(wholePane, BorderLayout.CENTER);
calcButton.addActionListener(this);
optionOne.addActionListener(this);
optionTwo.addActionListener(this);
optionThree.addActionListener(this);
loadOpt.addActionListener(this);
setDefaultCloseOperation(DISPOSE_ON_CLOSE);
setTitle("Amoritization Calculator");
}
public static void main(String[] args) // main thread
{
AmoritizationCalc amoritizationApp = new AmoritizationCalc();
amoritizationApp.setLocation(150, 100);
amoritizationApp.setSize(425, 350);
amoritizationApp.setVisible(true);
amoritizationApp.setName("Amoritization Calculator");
}
public void actionPerformed(ActionEvent e) // event thread. This program is event driven.
{
boolean selected = false;
double princAmt = 0;
double numMon = 0;
double intRate = 0;
DecimalFormat money = new DecimalFormat("$0.00");
if (e.getSource() == calcButton) {
try {
princAmt = Double.parseDouble(principleTxt.getText()); // these lines collect the data entered
numMon = Double.parseDouble(termTxt.getText());
intRate = (Double.parseDouble(interestTxt.getText()))/12; //interest rate per month
}
catch (NumberFormatException x) { // this code ensures that the data entered is the appropriate format
principleTxt.setText("");
termTxt.setText("");
interestTxt.setText("");
}
optionOne.setEnabled(true); // these clear the options and make the boxes editable again
optionOne.setSelected(false);
optionTwo.setEnabled(true);
optionTwo.setSelected(false);
optionThree.setEnabled(true);
optionThree.setSelected(false);
termTxt.setEditable(true);
interestTxt.setEditable(true);
double monPymt = 0; // the monthly payment
monPymt = (princAmt * (intRate * (Math.pow((1 + intRate), numMon)))/(Math.pow((1 + intRate), numMon) - 1)); // the amoritization formula for finding periodic payment amount
pymntAmtTxt.setText("Term: " + numMon + " Rate: " + intRate + " Monthly payment amount: " + money.format(monPymt));
double pymtInt=0;
double pymtPrinc=0;
double balance=princAmt;
for (int n=0; n<numMon ; n++) {
pymtInt=intRate * balance;
pymtPrinc=monPymt - pymtInt;
balance=balance-pymtPrinc;
pymntAmtTxt.append("\n");
pymntAmtTxt.append("Payment " + n + " : interest " + money.format(pymtInt) + ", principal " + money.format(pymtPrinc) + ", Balance " + money.format(balance));
}
}
else if (e.getSource() == optionOne) { //each one of these disables the other boxes and sets the term and interest
selected = optionOne.isSelected();
if (selected) {
optionTwo.setEnabled(false);
optionThree.setEnabled(false);
termTxt.setText("" + loanTIA[0][0]);
interestTxt.setText("" + loanTIA[0][1]);
termTxt.setEditable(false);
interestTxt.setEditable(false);
}
else {
optionOne.setEnabled(true); // these clear the options and make the boxes editable again
optionOne.setSelected(false);
optionTwo.setEnabled(true);
optionTwo.setSelected(false);
optionThree.setEnabled(true);
optionThree.setSelected(false);
termTxt.setEditable(true);
interestTxt.setEditable(true);
}
}
else if (e.getSource() == optionTwo) {
selected = optionTwo.isSelected();
if (selected) {
optionOne.setEnabled(false);
optionThree.setEnabled(false);
termTxt.setText("" + loanTIA[1][0]);
interestTxt.setText("" + loanTIA[1][1]);
termTxt.setEditable(false);
interestTxt.setEditable(false); }
else {
optionOne.setEnabled(true); // these clear the options and make the boxes editable again
optionOne.setSelected(false);
optionTwo.setEnabled(true);
optionTwo.setSelected(false);
optionThree.setEnabled(true);
optionThree.setSelected(false);
termTxt.setEditable(true);
interestTxt.setEditable(true);
}
}
else if (e.getSource() == optionThree) {
selected = optionThree.isSelected();
if (selected) {
optionTwo.setEnabled(false);
optionOne.setEnabled(false);
termTxt.setText("" + loanTIA[2][0]);
interestTxt.setText("" + loanTIA[2][1]);
termTxt.setEditable(false);
interestTxt.setEditable(false); }
else {
optionOne.setEnabled(true); // these clear the options and make the boxes editable again
optionOne.setSelected(false);
optionTwo.setEnabled(true);
optionTwo.setSelected(false);
optionThree.setEnabled(true);
optionThree.setSelected(false);
termTxt.setEditable(true);
interestTxt.setEditable(true);
}
}
else if (e.getSource() == loadOpt) { // this button event opens a jfile chooser to read CSV files with 3 rows and 2 columns
JFileChooser optLoad = new JFileChooser();
File selectedFile = null;
BufferedReader in;
FileReader fReader = null;
if (optLoad.showOpenDialog(this)==JFileChooser.APPROVE_OPTION)
{
selectedFile = optLoad.getSelectedFile();
}
try {
fReader = new FileReader(selectedFile);
} catch (FileNotFoundException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
}
in = new BufferedReader(fReader);
String[][] TempArray = new String[3][2]; // temporary string array for reading the data into
int row = 0;
int col = 0;
String strLine;
try {
while ((strLine = in.readLine()) != null && row < 3)
{
StringTokenizer st = new StringTokenizer(strLine,","); // divided as Comma Separated Values
while (st.hasMoreTokens())
{
TempArray[row][col] = st.nextToken();
col++;
}
col = 0;
row++;
}
} catch (IOException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
try {
in.close();
} catch (IOException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
for (int i=0; i < 3; i++)
{
for (int n=0; n<2; n++)
{
loanTIA[i][n] = Double.parseDouble(TempArray[i][n]); // parse each field from the temporary array as double for loanTIA array
}
}
optionOne.setText((loanTIA[0][0]/12)+" Years at "+(loanTIA[0][1]*100)+"%"); // assign new labels to match
optionTwo.setText((loanTIA[1][0]/12)+" Years at "+(loanTIA[1][1]*100)+"%");
optionThree.setText((loanTIA[2][0]/12)+" Years at "+(loanTIA[2][1]*100)+"%");
}
}
}